History

Merge tag 'wireless-next-2023-11-27' of git://git.kernel.org/pub/scm/linux/kernel/git/wireless/wireless-next

Kalle Valo says: ==================== wireless-next patches for v6.8 The first features pull request for v6.8. Not so big in number of commits but we removed quite a few ancient drivers: libertas 16-bit PCMCIA support, atmel, hostap, zd1201, orinoco, ray_cs, wl3501 and rndis_wlan. Major changes: cfg80211/mac80211 - extend support for scanning while Multi-Link Operation (MLO) connected * tag 'wireless-next-2023-11-27' of git://git.kernel.org/pub/scm/linux/kernel/git/wireless/wireless-next: (68 commits) wifi: nl80211: Documentation update for NL80211_CMD_PORT_AUTHORIZED event wifi: mac80211: Extend support for scanning while MLO connected wifi: cfg80211: Extend support for scanning while MLO connected wifi: ieee80211: fix PV1 frame control field name rfkill: return ENOTTY on invalid ioctl MAINTAINERS: update iwlwifi maintainers wifi: rtw89: 8922a: read efuse content from physical map wifi: rtw89: 8922a: read efuse content via efuse map struct from logic map wifi: rtw89: 8852c: read RX gain offset from efuse for 6GHz channels wifi: rtw89: mac: add to access efuse for WiFi 7 chips wifi: rtw89: mac: use mac_gen pointer to access about efuse wifi: rtw89: 8922a: add 8922A basic chip info wifi: rtlwifi: drop unused const_amdpci_aspm wifi: mwifiex: mwifiex_process_sleep_confirm_resp(): remove unused priv variable wifi: rtw89: regd: update regulatory map to R65-R44 wifi: rtw89: regd: handle policy of 6 GHz according to BIOS wifi: rtw89: acpi: process 6 GHz band policy from DSM wifi: rtlwifi: simplify rtl_action_proc() and rtl_tx_agg_start() wifi: rtw89: pci: update interrupt mitigation register for 8922AE wifi: rtw89: pci: correct interrupt mitigation register for 8852CE ... ====================

Jakub Kicinski committed 2 years ago

Commit a2147242 parents 2df6bde 0cc3f50158 files · +3424 −58838Browse files

Unified · Split

158 files
  1. Documentation/networking/device_drivers/wifi/index.rst +0 −1
  2. Documentation/networking/device_drivers/wifi/ray_cs.rst +0 −165
  3. MAINTAINERS +1 −41
  4. drivers/net/wireless/Kconfig +0 −3
  5. drivers/net/wireless/Makefile +0 −2
  6. drivers/net/wireless/atmel/Kconfig +0 −35
  7. drivers/net/wireless/atmel/Makefile +0 −4
  8. drivers/net/wireless/atmel/atmel.c +0 −4452
  9. drivers/net/wireless/atmel/atmel.h +0 −31
  10. drivers/net/wireless/atmel/atmel_cs.c +0 −292
  11. drivers/net/wireless/atmel/atmel_pci.c +0 −65
  12. drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c +1 −1
  13. drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c +1 −1
  14. drivers/net/wireless/broadcom/brcm80211/brcmsmac/channel.c +3 −3
  15. drivers/net/wireless/broadcom/brcm80211/brcmsmac/dma.c +1 −2
  16. drivers/net/wireless/broadcom/brcm80211/brcmsmac/main.c +2 −2
  17. drivers/net/wireless/cisco/Kconfig +0 −59
  18. drivers/net/wireless/cisco/Makefile +0 −3
  19. drivers/net/wireless/cisco/airo.c +0 −8288
  20. drivers/net/wireless/cisco/airo.h +0 −10
  21. drivers/net/wireless/cisco/airo_cs.c +0 −218
  22. drivers/net/wireless/intel/iwlegacy/4965-mac.c +0 −6
  23. drivers/net/wireless/intersil/Kconfig +0 −2
  24. drivers/net/wireless/intersil/Makefile +0 −2
  25. drivers/net/wireless/intersil/hostap/Kconfig +0 −95
  26. drivers/net/wireless/intersil/hostap/Makefile +0 −8
  27. drivers/net/wireless/intersil/hostap/hostap.h +0 −98
  28. drivers/net/wireless/intersil/hostap/hostap_80211.h +0 −97
  29. drivers/net/wireless/intersil/hostap/hostap_80211_rx.c +0 −1116
  30. drivers/net/wireless/intersil/hostap/hostap_80211_tx.c +0 −554
  31. drivers/net/wireless/intersil/hostap/hostap_ap.c +0 −3277
  32. drivers/net/wireless/intersil/hostap/hostap_ap.h +0 −264
  33. drivers/net/wireless/intersil/hostap/hostap_common.h +0 −420
  34. drivers/net/wireless/intersil/hostap/hostap_config.h +0 −49
  35. drivers/net/wireless/intersil/hostap/hostap_cs.c +0 −710
  36. drivers/net/wireless/intersil/hostap/hostap_download.c +0 −810
  37. drivers/net/wireless/intersil/hostap/hostap_hw.c +0 −3387
  38. drivers/net/wireless/intersil/hostap/hostap_info.c +0 −509
  39. drivers/net/wireless/intersil/hostap/hostap_ioctl.c +0 −3847
  40. drivers/net/wireless/intersil/hostap/hostap_main.c +0 −1123
  41. drivers/net/wireless/intersil/hostap/hostap_pci.c +0 −445
  42. drivers/net/wireless/intersil/hostap/hostap_plx.c +0 −617
  43. drivers/net/wireless/intersil/hostap/hostap_proc.c +0 −411
  44. drivers/net/wireless/intersil/hostap/hostap_wlan.h +0 −1051
  45. drivers/net/wireless/intersil/orinoco/Kconfig +0 −143
  46. drivers/net/wireless/intersil/orinoco/Makefile +0 −15
  47. drivers/net/wireless/intersil/orinoco/airport.c +0 −268
  48. drivers/net/wireless/intersil/orinoco/cfg.c +0 −291
  49. drivers/net/wireless/intersil/orinoco/cfg.h +0 −15
  50. drivers/net/wireless/intersil/orinoco/fw.c +0 −387
  51. drivers/net/wireless/intersil/orinoco/fw.h +0 −21
  52. drivers/net/wireless/intersil/orinoco/hermes.c +0 −778
  53. drivers/net/wireless/intersil/orinoco/hermes.h +0 −534
  54. drivers/net/wireless/intersil/orinoco/hermes_dld.c +0 −477
  55. drivers/net/wireless/intersil/orinoco/hermes_dld.h +0 −52
  56. drivers/net/wireless/intersil/orinoco/hermes_rid.h +0 −165
  57. drivers/net/wireless/intersil/orinoco/hw.c +0 −1362
  58. drivers/net/wireless/intersil/orinoco/hw.h +0 −60
  59. drivers/net/wireless/intersil/orinoco/main.c +0 −2414
  60. drivers/net/wireless/intersil/orinoco/main.h +0 −50
  61. drivers/net/wireless/intersil/orinoco/mic.c +0 −89
  62. drivers/net/wireless/intersil/orinoco/mic.h +0 −23
  63. drivers/net/wireless/intersil/orinoco/orinoco.h +0 −251
  64. drivers/net/wireless/intersil/orinoco/orinoco_cs.c +0 −350
  65. drivers/net/wireless/intersil/orinoco/orinoco_nortel.c +0 −314
  66. drivers/net/wireless/intersil/orinoco/orinoco_pci.c +0 −257
  67. drivers/net/wireless/intersil/orinoco/orinoco_pci.h +0 −54
  68. drivers/net/wireless/intersil/orinoco/orinoco_plx.c +0 −362
  69. drivers/net/wireless/intersil/orinoco/orinoco_tmd.c +0 −237
  70. drivers/net/wireless/intersil/orinoco/orinoco_usb.c +0 −1787
  71. drivers/net/wireless/intersil/orinoco/scan.c +0 −259
  72. drivers/net/wireless/intersil/orinoco/scan.h +0 −21
  73. drivers/net/wireless/intersil/orinoco/spectrum_cs.c +0 −328
  74. drivers/net/wireless/intersil/orinoco/wext.c +0 −1428
  75. drivers/net/wireless/intersil/orinoco/wext.h +0 −13
  76. drivers/net/wireless/legacy/Kconfig +0 −55
  77. drivers/net/wireless/legacy/Makefile +0 −6
  78. drivers/net/wireless/legacy/ray_cs.c +0 −2824
  79. drivers/net/wireless/legacy/ray_cs.h +0 −74
  80. drivers/net/wireless/legacy/rayctl.h +0 −734
  81. drivers/net/wireless/legacy/rndis_wlan.c +0 −3760
  82. drivers/net/wireless/legacy/wl3501.h +0 −615
  83. drivers/net/wireless/legacy/wl3501_cs.c +0 −2036
  84. drivers/net/wireless/marvell/libertas/Kconfig +1 −8
  85. drivers/net/wireless/marvell/libertas/Makefile +0 −1
  86. drivers/net/wireless/marvell/libertas/if_cs.c +0 −957
  87. drivers/net/wireless/marvell/mwifiex/cmdevt.c +0 −8
  88. drivers/net/wireless/microchip/wilc1000/cfg80211.c +9 −15
  89. drivers/net/wireless/microchip/wilc1000/hif.c +23 −23
  90. drivers/net/wireless/microchip/wilc1000/hif.h +22 −20
  91. drivers/net/wireless/microchip/wilc1000/sdio.c +5 −4
  92. drivers/net/wireless/purelifi/plfxlc/usb.c +4 −1
  93. drivers/net/wireless/ralink/rt2x00/rt2800.h +4 −0
  94. drivers/net/wireless/ralink/rt2x00/rt2800lib.c +69 −14
  95. drivers/net/wireless/ralink/rt2x00/rt2x00.h +3 −0
  96. drivers/net/wireless/ralink/rt2x00/rt2x00dev.c +3 −0
  97. drivers/net/wireless/ralink/rt2x00/rt2x00mac.c +11 −0
  98. drivers/net/wireless/realtek/rtlwifi/base.c +0 −8
  99. drivers/net/wireless/realtek/rtlwifi/pci.c +0 −1
  100. drivers/net/wireless/realtek/rtlwifi/pci.h +0 −1
  101. drivers/net/wireless/realtek/rtlwifi/rtl8188ee/sw.c +0 −3
  102. drivers/net/wireless/realtek/rtlwifi/rtl8192c/phy_common.c +0 −4
  103. drivers/net/wireless/realtek/rtlwifi/rtl8192ce/sw.c +0 −3
  104. drivers/net/wireless/realtek/rtlwifi/rtl8192de/sw.c +0 −3
  105. drivers/net/wireless/realtek/rtlwifi/rtl8192ee/dm.c +2 −9
  106. drivers/net/wireless/realtek/rtlwifi/rtl8192ee/hw.c +0 −1
  107. drivers/net/wireless/realtek/rtlwifi/rtl8192ee/sw.c +0 −3
  108. drivers/net/wireless/realtek/rtlwifi/rtl8192se/sw.c +0 −3
  109. drivers/net/wireless/realtek/rtlwifi/rtl8723ae/sw.c +0 −3
  110. drivers/net/wireless/realtek/rtlwifi/rtl8723be/sw.c +0 −3
  111. drivers/net/wireless/realtek/rtlwifi/rtl8821ae/sw.c +0 −3
  112. drivers/net/wireless/realtek/rtlwifi/wifi.h +0 −17
  113. drivers/net/wireless/realtek/rtw88/mac80211.c +2 −2
  114. drivers/net/wireless/realtek/rtw88/tx.c +1 −2
  115. drivers/net/wireless/realtek/rtw89/acpi.c +66 −15
  116. drivers/net/wireless/realtek/rtw89/acpi.h +31 −1
  117. drivers/net/wireless/realtek/rtw89/cam.c +15 −1
  118. drivers/net/wireless/realtek/rtw89/coex.c +2 −2
  119. drivers/net/wireless/realtek/rtw89/core.c +79 −16
  120. drivers/net/wireless/realtek/rtw89/core.h +38 −2
  121. drivers/net/wireless/realtek/rtw89/debug.h +1 −0
  122. drivers/net/wireless/realtek/rtw89/efuse.c +8 −3
  123. drivers/net/wireless/realtek/rtw89/efuse.h +15 −2
  124. drivers/net/wireless/realtek/rtw89/efuse_be.c +420 −0
  125. drivers/net/wireless/realtek/rtw89/mac.c +13 −3
  126. drivers/net/wireless/realtek/rtw89/mac.h +4 −0
  127. drivers/net/wireless/realtek/rtw89/mac_be.c +4 −0
  128. drivers/net/wireless/realtek/rtw89/pci.c +240 −83
  129. drivers/net/wireless/realtek/rtw89/pci.h +515 −0
  130. drivers/net/wireless/realtek/rtw89/pci_be.c +509 −0
  131. drivers/net/wireless/realtek/rtw89/phy.h +16 −0
  132. drivers/net/wireless/realtek/rtw89/reg.h +437 −0
  133. drivers/net/wireless/realtek/rtw89/regd.c +168 −7
  134. drivers/net/wireless/realtek/rtw89/rtw8851b.c +4 −1
  135. drivers/net/wireless/realtek/rtw89/rtw8851be.c +3 −0
  136. drivers/net/wireless/realtek/rtw89/rtw8852a.c +4 −1
  137. drivers/net/wireless/realtek/rtw89/rtw8852ae.c +4 −0
  138. drivers/net/wireless/realtek/rtw89/rtw8852b.c +4 −1
  139. drivers/net/wireless/realtek/rtw89/rtw8852be.c +4 −0
  140. drivers/net/wireless/realtek/rtw89/rtw8852c.c +28 −1
  141. drivers/net/wireless/realtek/rtw89/rtw8852c.h +18 −2
  142. drivers/net/wireless/realtek/rtw89/rtw8852ce.c +4 −0
  143. drivers/net/wireless/realtek/rtw89/rtw8922a.c +363 −0
  144. drivers/net/wireless/realtek/rtw89/rtw8922a.h +73 −0
  145. drivers/net/wireless/realtek/rtw89/rtw8922ae.c +88 −0
  146. drivers/net/wireless/realtek/rtw89/sar.c +3 −1
  147. drivers/net/wireless/realtek/rtw89/ser.c +6 −0
  148. drivers/net/wireless/realtek/rtw89/txrx.h +4 −0
  149. drivers/net/wireless/zydas/Kconfig +0 −19
  150. drivers/net/wireless/zydas/Makefile +0 −2
  151. drivers/net/wireless/zydas/zd1201.c +0 −1909
  152. drivers/net/wireless/zydas/zd1201.h +0 −144
  153. include/linux/ieee80211.h +2 −2
  154. include/net/cfg80211.h +3 −0
  155. include/uapi/linux/nl80211.h +14 −8
  156. net/mac80211/scan.c +43 −5
  157. net/rfkill/core.c +2 −2
  158. net/wireless/nl80211.c +1 −0
Documentation/networking/device_drivers/wifi/index.rst+0−1
@@ -10,7 +10,6 @@ Contents: · 9 unmodified lines
10 10
11 intel/ipw210011 intel/ipw2100
12 intel/ipw220012 intel/ipw2200
13 ray_cs
14 13
15.. only:: subproject and html14.. only:: subproject and html
16 15
Documentation/networking/device_drivers/wifi/ray_cs.rst+0−165
@@ -1,165 +0,0 @@
1.. SPDX-License-Identifier: GPL-2.0
2
3.. include:: <isonum.txt>
4
5=========================
6Raylink wireless LAN card
7=========================
8
9September 21, 1999
10
11Copyright |copy| 1998 Corey Thomas (corey@world.std.com)
12
13This file is the documentation for the Raylink Wireless LAN card driver for
14Linux. The Raylink wireless LAN card is a PCMCIA card which provides IEEE
15802.11 compatible wireless network connectivity at 1 and 2 megabits/second.
16See http://www.raytheon.com/micro/raylink/ for more information on the Raylink
17card. This driver is in early development and does have bugs. See the known
18bugs and limitations at the end of this document for more information.
19This driver also works with WebGear's Aviator 2.4 and Aviator Pro
20wireless LAN cards.
21
22As of kernel 2.3.18, the ray_cs driver is part of the Linux kernel
23source. My web page for the development of ray_cs is at
24http://web.ralinktech.com/ralink/Home/Support/Linux.html
25and I can be emailed at corey@world.std.com
26
27The kernel driver is based on ray_cs-1.62.tgz
28
29The driver at my web page is intended to be used as an add on to
30David Hinds pcmcia package. All the command line parameters are
31available when compiled as a module. When built into the kernel, only
32the essid= string parameter is available via the kernel command line.
33This will change after the method of sorting out parameters for all
34the PCMCIA drivers is agreed upon. If you must have a built in driver
35with nondefault parameters, they can be edited in
36/usr/src/linux/drivers/net/pcmcia/ray_cs.c. Searching for module_param
37will find them all.
38
39Information on card services is available at:
40
41 http://pcmcia-cs.sourceforge.net/
42
43
44Card services user programs are still required for PCMCIA devices.
45pcmcia-cs-3.1.1 or greater is required for the kernel version of
46the driver.
47
48Currently, ray_cs is not part of David Hinds card services package,
49so the following magic is required.
50
51At the end of the /etc/pcmcia/config.opts file, add the line:
52source ./ray_cs.opts
53This will make card services read the ray_cs.opts file
54when starting. Create the file /etc/pcmcia/ray_cs.opts containing the
55following::
56
57 #### start of /etc/pcmcia/ray_cs.opts ###################
58 # Configuration options for Raylink Wireless LAN PCMCIA card
59 device "ray_cs"
60 class "network" module "misc/ray_cs"
61
62 card "RayLink PC Card WLAN Adapter"
63 manfid 0x01a6, 0x0000
64 bind "ray_cs"
65
66 module "misc/ray_cs" opts ""
67 #### end of /etc/pcmcia/ray_cs.opts #####################
68
69
70To join an existing network with
71different parameters, contact the network administrator for the
72configuration information, and edit /etc/pcmcia/ray_cs.opts.
73Add the parameters below between the empty quotes.
74
75Parameters for ray_cs driver which may be specified in ray_cs.opts:
76
77=============== =============== =============================================
78bc integer 0 = normal mode (802.11 timing),
79 1 = slow down inter frame timing to allow
80 operation with older breezecom access
81 points.
82
83beacon_period integer beacon period in Kilo-microseconds,
84
85 legal values = must be integer multiple
86 of hop dwell
87
88 default = 256
89
90country integer 1 = USA (default),
91 2 = Europe,
92 3 = Japan,
93 4 = Korea,
94 5 = Spain,
95 6 = France,
96 7 = Israel,
97 8 = Australia
98
99essid string ESS ID - network name to join
100
101 string with maximum length of 32 chars
102 default value = "ADHOC_ESSID"
103
104hop_dwell integer hop dwell time in Kilo-microseconds
105
106 legal values = 16,32,64,128(default),256
107
108irq_mask integer linux standard 16 bit value 1bit/IRQ
109
110 lsb is IRQ 0, bit 1 is IRQ 1 etc.
111 Used to restrict choice of IRQ's to use.
112 Recommended method for controlling
113 interrupts is in /etc/pcmcia/config.opts
114
115net_type integer 0 (default) = adhoc network,
116 1 = infrastructure
117
118phy_addr string string containing new MAC address in
119 hex, must start with x eg
120 x00008f123456
121
122psm integer 0 = continuously active,
123 1 = power save mode (not useful yet)
124
125pc_debug integer (0-5) larger values for more verbose
126 logging. Replaces ray_debug.
127
128ray_debug integer Replaced with pc_debug
129
130ray_mem_speed integer defaults to 500
131
132sniffer integer 0 = not sniffer (default),
133 1 = sniffer which can be used to record all
134 network traffic using tcpdump or similar,
135 but no normal network use is allowed.
136
137translate integer 0 = no translation (encapsulate frames),
138 1 = translation (RFC1042/802.1)
139=============== =============== =============================================
140
141More on sniffer mode:
142
143tcpdump does not understand 802.11 headers, so it can't
144interpret the contents, but it can record to a file. This is only
145useful for debugging 802.11 lowlevel protocols that are not visible to
146linux. If you want to watch ftp xfers, or do similar things, you
147don't need to use sniffer mode. Also, some packet types are never
148sent up by the card, so you will never see them (ack, rts, cts, probe
149etc.) There is a simple program (showcap) included in the ray_cs
150package which parses the 802.11 headers.
151
152Known Problems and missing features
153
154 Does not work with non x86
155
156 Does not work with SMP
157
158 Support for defragmenting frames is not yet debugged, and in
159 fact is known to not work. I have never encountered a net set
160 up to fragment, but still, it should be fixed.
161
162 The ioctl support is incomplete. The hardware address cannot be set
163 using ifconfig yet. If a different hardware address is needed, it may
164 be set using the phy_addr parameter in ray_cs.opts. This requires
165 a card insertion to take effect.
MAINTAINERS+1−41
@@ -2405,7 +2405,6 @@ F: drivers/memory/atmel* · 2404 unmodified lines
2405F: drivers/watchdog/sama5d4_wdt.c2405F: drivers/watchdog/sama5d4_wdt.c
2406F: include/soc/at91/2406F: include/soc/at91/
2407X: drivers/input/touchscreen/atmel_mxt_ts.c2407X: drivers/input/touchscreen/atmel_mxt_ts.c
2408X: drivers/net/wireless/atmel/
2409N: at912408N: at91
2410N: atmel2409N: atmel
2411 2410
@@ -3309,13 +3308,6 @@ T: git git://github.com/ndyer/linux.git · 897 unmodified lines
3309F: Documentation/devicetree/bindings/input/atmel,maxtouch.yaml3308F: Documentation/devicetree/bindings/input/atmel,maxtouch.yaml
3310F: drivers/input/touchscreen/atmel_mxt_ts.c3309F: drivers/input/touchscreen/atmel_mxt_ts.c
3311 3310
3312ATMEL WIRELESS DRIVER
3313L: linux-wireless@vger.kernel.org
3314S: Orphan
3315W: http://www.thekelleys.org.uk/atmel
3316W: http://atmelwlandriver.sourceforge.net/
3317F: drivers/net/wireless/atmel/atmel*
3318
3319ATOMIC INFRASTRUCTURE3311ATOMIC INFRASTRUCTURE
3320M: Will Deacon <will@kernel.org>3312M: Will Deacon <will@kernel.org>
3321M: Peter Zijlstra <peterz@infradead.org>3313M: Peter Zijlstra <peterz@infradead.org>
@@ -9709,11 +9701,6 @@ S: Maintained · 6387 unmodified lines
9709F: Documentation/devicetree/bindings/iio/pressure/honeywell,mprls0025pa.yaml9701F: Documentation/devicetree/bindings/iio/pressure/honeywell,mprls0025pa.yaml
9710F: drivers/iio/pressure/mprls0025pa.c9702F: drivers/iio/pressure/mprls0025pa.c
9711 9703
9712HOST AP DRIVER
9713L: linux-wireless@vger.kernel.org
9714S: Obsolete
9715F: drivers/net/wireless/intersil/hostap/
9716
9717HP BIOSCFG DRIVER9704HP BIOSCFG DRIVER
9718M: Jorge Lopez <jorge.lopez2@hp.com>9705M: Jorge Lopez <jorge.lopez2@hp.com>
9719L: platform-driver-x86@vger.kernel.org9706L: platform-driver-x86@vger.kernel.org
@@ -11017,6 +11004,7 @@ F: drivers/net/wireless/intel/iwlegacy/ · 1297 unmodified lines
11017 11004
11018INTEL WIRELESS WIFI LINK (iwlwifi)11005INTEL WIRELESS WIFI LINK (iwlwifi)
11019M: Gregory Greenman <gregory.greenman@intel.com>11006M: Gregory Greenman <gregory.greenman@intel.com>
11007M: Miri Korenblit <miriam.rachel.korenblit@intel.com>
11020L: linux-wireless@vger.kernel.org11008L: linux-wireless@vger.kernel.org
11021S: Supported11009S: Supported
11022W: https://wireless.wiki.kernel.org/en/users/drivers/iwlwifi11010W: https://wireless.wiki.kernel.org/en/users/drivers/iwlwifi
@@ -16269,13 +16257,6 @@ T: git git://git.kernel.org/pub/scm/linux/kernel/git/hubcap/linux.git · 5246 unmodified lines
16269F: Documentation/filesystems/orangefs.rst16257F: Documentation/filesystems/orangefs.rst
16270F: fs/orangefs/16258F: fs/orangefs/
16271 16259
16272ORINOCO DRIVER
16273L: linux-wireless@vger.kernel.org
16274S: Orphan
16275W: https://wireless.wiki.kernel.org/en/users/Drivers/orinoco
16276W: http://www.nongnu.org/orinoco/
16277F: drivers/net/wireless/intersil/orinoco/
16278
16279OV2659 OMNIVISION SENSOR DRIVER16260OV2659 OMNIVISION SENSOR DRIVER
16280M: "Lad, Prabhakar" <prabhakar.csengg@gmail.com>16261M: "Lad, Prabhakar" <prabhakar.csengg@gmail.com>
16281L: linux-media@vger.kernel.org16262L: linux-media@vger.kernel.org
@@ -18169,11 +18150,6 @@ F: drivers/ras/ · 1887 unmodified lines
18169F: include/linux/ras.h18150F: include/linux/ras.h
18170F: include/ras/ras_event.h18151F: include/ras/ras_event.h
18171 18152
18172RAYLINK/WEBGEAR 802.11 WIRELESS LAN DRIVER
18173L: linux-wireless@vger.kernel.org
18174S: Orphan
18175F: drivers/net/wireless/legacy/ray*
18176
18177RC-CORE / LIRC FRAMEWORK18153RC-CORE / LIRC FRAMEWORK
18178M: Sean Young <sean@mess.org>18154M: Sean Young <sean@mess.org>
18179L: linux-media@vger.kernel.org18155L: linux-media@vger.kernel.org
@@ -22680,11 +22656,6 @@ F: drivers/usb/gadget/function/*uvc* · 4500 unmodified lines
22680F: drivers/usb/gadget/legacy/webcam.c22656F: drivers/usb/gadget/legacy/webcam.c
22681F: include/uapi/linux/usb/g_uvc.h22657F: include/uapi/linux/usb/g_uvc.h
22682 22658
22683USB WIRELESS RNDIS DRIVER (rndis_wlan)
22684L: linux-wireless@vger.kernel.org
22685S: Orphan
22686F: drivers/net/wireless/legacy/rndis_wlan.c
22687
22688USB XHCI DRIVER22659USB XHCI DRIVER
22689M: Mathias Nyman <mathias.nyman@intel.com>22660M: Mathias Nyman <mathias.nyman@intel.com>
22690L: linux-usb@vger.kernel.org22661L: linux-usb@vger.kernel.org
@@ -22692,12 +22663,6 @@ S: Supported · 1 unmodified line
22692F: drivers/usb/host/pci-quirks*22663F: drivers/usb/host/pci-quirks*
22693F: drivers/usb/host/xhci*22664F: drivers/usb/host/xhci*
22694 22665
22695USB ZD1201 DRIVER
22696L: linux-wireless@vger.kernel.org
22697S: Orphan
22698W: http://linux-lc100020.sourceforge.net
22699F: drivers/net/wireless/zydas/zd1201.*
22700
22701USER DATAGRAM PROTOCOL (UDP)22666USER DATAGRAM PROTOCOL (UDP)
22702M: Willem de Bruijn <willemdebruijn.kernel@gmail.com>22667M: Willem de Bruijn <willemdebruijn.kernel@gmail.com>
22703S: Maintained22668S: Maintained
@@ -23499,11 +23464,6 @@ M: Miloslav Trmac <mitr@volny.cz> · 795 unmodified lines
23499S: Maintained23464S: Maintained
23500F: drivers/input/misc/wistron_btns.c23465F: drivers/input/misc/wistron_btns.c
23501 23466
23502WL3501 WIRELESS PCMCIA CARD DRIVER
23503L: linux-wireless@vger.kernel.org
23504S: Orphan
23505F: drivers/net/wireless/legacy/wl3501*
23506
23507WMI BINARY MOF DRIVER23467WMI BINARY MOF DRIVER
23508M: Armin Wolf <W_Armin@gmx.de>23468M: Armin Wolf <W_Armin@gmx.de>
23509R: Thomas Weißschuh <linux@weissschuh.net>23469R: Thomas Weißschuh <linux@weissschuh.net>
drivers/net/wireless/Kconfig+0−3
@@ -22,7 +22,6 @@ source "drivers/net/wireless/admtek/Kconfig" · 21 unmodified lines
22source "drivers/net/wireless/ath/Kconfig"22source "drivers/net/wireless/ath/Kconfig"
23source "drivers/net/wireless/atmel/Kconfig"23source "drivers/net/wireless/atmel/Kconfig"
24source "drivers/net/wireless/broadcom/Kconfig"24source "drivers/net/wireless/broadcom/Kconfig"
25source "drivers/net/wireless/cisco/Kconfig"
26source "drivers/net/wireless/intel/Kconfig"25source "drivers/net/wireless/intel/Kconfig"
27source "drivers/net/wireless/intersil/Kconfig"26source "drivers/net/wireless/intersil/Kconfig"
28source "drivers/net/wireless/marvell/Kconfig"27source "drivers/net/wireless/marvell/Kconfig"
@@ -38,8 +37,6 @@ source "drivers/net/wireless/ti/Kconfig" · 9 unmodified lines
38source "drivers/net/wireless/zydas/Kconfig"37source "drivers/net/wireless/zydas/Kconfig"
39source "drivers/net/wireless/quantenna/Kconfig"38source "drivers/net/wireless/quantenna/Kconfig"
40 39
41source "drivers/net/wireless/legacy/Kconfig"
42
43source "drivers/net/wireless/virtual/Kconfig"40source "drivers/net/wireless/virtual/Kconfig"
44 41
45endif # WLAN42endif # WLAN
drivers/net/wireless/Makefile+0−2
@@ -7,7 +7,6 @@ obj-$(CONFIG_WLAN_VENDOR_ADMTEK) += admtek/ · 6 unmodified lines
7obj-$(CONFIG_WLAN_VENDOR_ATH) += ath/7obj-$(CONFIG_WLAN_VENDOR_ATH) += ath/
8obj-$(CONFIG_WLAN_VENDOR_ATMEL) += atmel/8obj-$(CONFIG_WLAN_VENDOR_ATMEL) += atmel/
9obj-$(CONFIG_WLAN_VENDOR_BROADCOM) += broadcom/9obj-$(CONFIG_WLAN_VENDOR_BROADCOM) += broadcom/
10obj-$(CONFIG_WLAN_VENDOR_CISCO) += cisco/
11obj-$(CONFIG_WLAN_VENDOR_INTEL) += intel/10obj-$(CONFIG_WLAN_VENDOR_INTEL) += intel/
12obj-$(CONFIG_WLAN_VENDOR_INTERSIL) += intersil/11obj-$(CONFIG_WLAN_VENDOR_INTERSIL) += intersil/
13obj-$(CONFIG_WLAN_VENDOR_MARVELL) += marvell/12obj-$(CONFIG_WLAN_VENDOR_MARVELL) += marvell/
@@ -23,5 +22,4 @@ obj-$(CONFIG_WLAN_VENDOR_ST) += st/ · 9 unmodified lines
23obj-$(CONFIG_WLAN_VENDOR_TI) += ti/22obj-$(CONFIG_WLAN_VENDOR_TI) += ti/
24obj-$(CONFIG_WLAN_VENDOR_ZYDAS) += zydas/23obj-$(CONFIG_WLAN_VENDOR_ZYDAS) += zydas/
25 24
26obj-$(CONFIG_WLAN) += legacy/
27obj-$(CONFIG_WLAN) += virtual/25obj-$(CONFIG_WLAN) += virtual/
drivers/net/wireless/atmel/Kconfig+0−35
@@ -12,41 +12,6 @@ config WLAN_VENDOR_ATMEL · 11 unmodified lines
12 12
13if WLAN_VENDOR_ATMEL13if WLAN_VENDOR_ATMEL
14 14
15config ATMEL
16 tristate "Atmel at76c50x chipset 802.11b support"
17 depends on CFG80211 && (PCI || PCMCIA) && HAS_IOPORT
18 select WIRELESS_EXT
19 select WEXT_PRIV
20 select FW_LOADER
21 select CRC32
22 help
23 A driver 802.11b wireless cards based on the Atmel fast-vnet
24 chips. This driver supports standard Linux wireless extensions.
25
26 Many cards based on this chipset do not have flash memory
27 and need their firmware loaded at start-up. If yours is
28 one of these, you will need to provide a firmware image
29 to be loaded into the card by the driver. The Atmel
30 firmware package can be downloaded from
31 <http://www.thekelleys.org.uk/atmel>
32
33config PCI_ATMEL
34 tristate "Atmel at76c506 PCI cards"
35 depends on ATMEL && PCI
36 help
37 Enable support for PCI and mini-PCI cards containing the
38 Atmel at76c506 chip.
39
40config PCMCIA_ATMEL
41 tristate "Atmel at76c502/at76c504 PCMCIA cards"
42 depends on ATMEL && PCMCIA
43 select WIRELESS_EXT
44 select FW_LOADER
45 select CRC32
46 help
47 Enable support for PCMCIA cards containing the
48 Atmel at76c502 and at76c504 chips.
49
50config AT76C50X_USB15config AT76C50X_USB
51 tristate "Atmel at76c503/at76c505/at76c505a USB cards"16 tristate "Atmel at76c503/at76c505/at76c505a USB cards"
52 depends on MAC80211 && USB17 depends on MAC80211 && USB
drivers/net/wireless/atmel/Makefile+0−4
@@ -1,6 +1,2 @@
1# SPDX-License-Identifier: GPL-2.0-only1# SPDX-License-Identifier: GPL-2.0-only
2obj-$(CONFIG_ATMEL) += atmel.o
3obj-$(CONFIG_PCI_ATMEL) += atmel_pci.o
4obj-$(CONFIG_PCMCIA_ATMEL) += atmel_cs.o
5
6obj-$(CONFIG_AT76C50X_USB) += at76c50x-usb.o2obj-$(CONFIG_AT76C50X_USB) += at76c50x-usb.o
drivers/net/wireless/atmel/atmel.c+0−4452
@@ -1,4452 +0,0 @@
1/*** -*- linux-c -*- **********************************************************
2
3 Driver for Atmel at76c502 at76c504 and at76c506 wireless cards.
4
5 Copyright 2000-2001 ATMEL Corporation.
6 Copyright 2003-2004 Simon Kelley.
7
8 This code was developed from version 2.1.1 of the Atmel drivers,
9 released by Atmel corp. under the GPL in December 2002. It also
10 includes code from the Linux aironet drivers (C) Benjamin Reed,
11 and the Linux PCMCIA package, (C) David Hinds and the Linux wireless
12 extensions, (C) Jean Tourrilhes.
13
14 The firmware module for reading the MAC address of the card comes from
15 net.russotto.AtmelMACFW, written by Matthew T. Russotto and copyright
16 by him. net.russotto.AtmelMACFW is used under the GPL license version 2.
17 This file contains the module in binary form and, under the terms
18 of the GPL, in source form. The source is located at the end of the file.
19
20 This program is free software; you can redistribute it and/or modify
21 it under the terms of the GNU General Public License as published by
22 the Free Software Foundation; either version 2 of the License, or
23 (at your option) any later version.
24
25 This software is distributed in the hope that it will be useful,
26 but WITHOUT ANY WARRANTY; without even the implied warranty of
27 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
28 GNU General Public License for more details.
29
30 You should have received a copy of the GNU General Public License
31 along with Atmel wireless lan drivers; if not, see
32 <http://www.gnu.org/licenses/>.
33
34 For all queries about this code, please contact the current author,
35 Simon Kelley <simon@thekelleys.org.uk> and not Atmel Corporation.
36
37 Credit is due to HP UK and Cambridge Online Systems Ltd for supplying
38 hardware used during development of this driver.
39
40******************************************************************************/
41
42#include <linux/interrupt.h>
43
44#include <linux/kernel.h>
45#include <linux/ptrace.h>
46#include <linux/slab.h>
47#include <linux/string.h>
48#include <linux/timer.h>
49#include <asm/byteorder.h>
50#include <asm/io.h>
51#include <linux/uaccess.h>
52#include <linux/module.h>
53#include <linux/netdevice.h>
54#include <linux/etherdevice.h>
55#include <linux/skbuff.h>
56#include <linux/if_arp.h>
57#include <linux/ioport.h>
58#include <linux/fcntl.h>
59#include <linux/delay.h>
60#include <linux/wireless.h>
61#include <net/iw_handler.h>
62#include <linux/crc32.h>
63#include <linux/proc_fs.h>
64#include <linux/seq_file.h>
65#include <linux/device.h>
66#include <linux/moduleparam.h>
67#include <linux/firmware.h>
68#include <linux/jiffies.h>
69#include <net/cfg80211.h>
70#include "atmel.h"
71
72#define DRIVER_MAJOR 0
73#define DRIVER_MINOR 98
74
75MODULE_AUTHOR("Simon Kelley");
76MODULE_DESCRIPTION("Support for Atmel at76c50x 802.11 wireless ethernet cards.");
77MODULE_LICENSE("GPL");
78
79/* The name of the firmware file to be loaded
80 over-rides any automatic selection */
81static char *firmware = NULL;
82module_param(firmware, charp, 0);
83
84/* table of firmware file names */
85static struct {
86 AtmelFWType fw_type;
87 const char *fw_file;
88 const char *fw_file_ext;
89} fw_table[] = {
90 { ATMEL_FW_TYPE_502, "atmel_at76c502", "bin" },
91 { ATMEL_FW_TYPE_502D, "atmel_at76c502d", "bin" },
92 { ATMEL_FW_TYPE_502E, "atmel_at76c502e", "bin" },
93 { ATMEL_FW_TYPE_502_3COM, "atmel_at76c502_3com", "bin" },
94 { ATMEL_FW_TYPE_504, "atmel_at76c504", "bin" },
95 { ATMEL_FW_TYPE_504_2958, "atmel_at76c504_2958", "bin" },
96 { ATMEL_FW_TYPE_504A_2958, "atmel_at76c504a_2958", "bin" },
97 { ATMEL_FW_TYPE_506, "atmel_at76c506", "bin" },
98 { ATMEL_FW_TYPE_NONE, NULL, NULL }
99};
100MODULE_FIRMWARE("atmel_at76c502-wpa.bin");
101MODULE_FIRMWARE("atmel_at76c502.bin");
102MODULE_FIRMWARE("atmel_at76c502d-wpa.bin");
103MODULE_FIRMWARE("atmel_at76c502d.bin");
104MODULE_FIRMWARE("atmel_at76c502e-wpa.bin");
105MODULE_FIRMWARE("atmel_at76c502e.bin");
106MODULE_FIRMWARE("atmel_at76c502_3com-wpa.bin");
107MODULE_FIRMWARE("atmel_at76c502_3com.bin");
108MODULE_FIRMWARE("atmel_at76c504-wpa.bin");
109MODULE_FIRMWARE("atmel_at76c504.bin");
110MODULE_FIRMWARE("atmel_at76c504_2958-wpa.bin");
111MODULE_FIRMWARE("atmel_at76c504_2958.bin");
112MODULE_FIRMWARE("atmel_at76c504a_2958-wpa.bin");
113MODULE_FIRMWARE("atmel_at76c504a_2958.bin");
114MODULE_FIRMWARE("atmel_at76c506-wpa.bin");
115MODULE_FIRMWARE("atmel_at76c506.bin");
116
117#define MAX_SSID_LENGTH 32
118#define MGMT_JIFFIES (256 * HZ / 100)
119
120#define MAX_BSS_ENTRIES 64
121
122/* registers */
123#define GCR 0x00 /* (SIR0) General Configuration Register */
124#define BSR 0x02 /* (SIR1) Bank Switching Select Register */
125#define AR 0x04
126#define DR 0x08
127#define MR1 0x12 /* Mirror Register 1 */
128#define MR2 0x14 /* Mirror Register 2 */
129#define MR3 0x16 /* Mirror Register 3 */
130#define MR4 0x18 /* Mirror Register 4 */
131
132#define GPR1 0x0c
133#define GPR2 0x0e
134#define GPR3 0x10
135/*
136 * Constants for the GCR register.
137 */
138#define GCR_REMAP 0x0400 /* Remap internal SRAM to 0 */
139#define GCR_SWRES 0x0080 /* BIU reset (ARM and PAI are NOT reset) */
140#define GCR_CORES 0x0060 /* Core Reset (ARM and PAI are reset) */
141#define GCR_ENINT 0x0002 /* Enable Interrupts */
142#define GCR_ACKINT 0x0008 /* Acknowledge Interrupts */
143
144#define BSS_SRAM 0x0200 /* AMBA module selection --> SRAM */
145#define BSS_IRAM 0x0100 /* AMBA module selection --> IRAM */
146/*
147 *Constants for the MR registers.
148 */
149#define MAC_INIT_COMPLETE 0x0001 /* MAC init has been completed */
150#define MAC_BOOT_COMPLETE 0x0010 /* MAC boot has been completed */
151#define MAC_INIT_OK 0x0002 /* MAC boot has been completed */
152
153#define MIB_MAX_DATA_BYTES 212
154#define MIB_HEADER_SIZE 4 /* first four fields */
155
156struct get_set_mib {
157 u8 type;
158 u8 size;
159 u8 index;
160 u8 reserved;
161 u8 data[MIB_MAX_DATA_BYTES];
162};
163
164struct rx_desc {
165 u32 Next;
166 u16 MsduPos;
167 u16 MsduSize;
168
169 u8 State;
170 u8 Status;
171 u8 Rate;
172 u8 Rssi;
173 u8 LinkQuality;
174 u8 PreambleType;
175 u16 Duration;
176 u32 RxTime;
177};
178
179#define RX_DESC_FLAG_VALID 0x80
180#define RX_DESC_FLAG_CONSUMED 0x40
181#define RX_DESC_FLAG_IDLE 0x00
182
183#define RX_STATUS_SUCCESS 0x00
184
185#define RX_DESC_MSDU_POS_OFFSET 4
186#define RX_DESC_MSDU_SIZE_OFFSET 6
187#define RX_DESC_FLAGS_OFFSET 8
188#define RX_DESC_STATUS_OFFSET 9
189#define RX_DESC_RSSI_OFFSET 11
190#define RX_DESC_LINK_QUALITY_OFFSET 12
191#define RX_DESC_PREAMBLE_TYPE_OFFSET 13
192#define RX_DESC_DURATION_OFFSET 14
193#define RX_DESC_RX_TIME_OFFSET 16
194
195struct tx_desc {
196 u32 NextDescriptor;
197 u16 TxStartOfFrame;
198 u16 TxLength;
199
200 u8 TxState;
201 u8 TxStatus;
202 u8 RetryCount;
203
204 u8 TxRate;
205
206 u8 KeyIndex;
207 u8 ChiperType;
208 u8 ChipreLength;
209 u8 Reserved1;
210
211 u8 Reserved;
212 u8 PacketType;
213 u16 HostTxLength;
214};
215
216#define TX_DESC_NEXT_OFFSET 0
217#define TX_DESC_POS_OFFSET 4
218#define TX_DESC_SIZE_OFFSET 6
219#define TX_DESC_FLAGS_OFFSET 8
220#define TX_DESC_STATUS_OFFSET 9
221#define TX_DESC_RETRY_OFFSET 10
222#define TX_DESC_RATE_OFFSET 11
223#define TX_DESC_KEY_INDEX_OFFSET 12
224#define TX_DESC_CIPHER_TYPE_OFFSET 13
225#define TX_DESC_CIPHER_LENGTH_OFFSET 14
226#define TX_DESC_PACKET_TYPE_OFFSET 17
227#define TX_DESC_HOST_LENGTH_OFFSET 18
228
229/*
230 * Host-MAC interface
231 */
232
233#define TX_STATUS_SUCCESS 0x00
234
235#define TX_FIRM_OWN 0x80
236#define TX_DONE 0x40
237
238#define TX_ERROR 0x01
239
240#define TX_PACKET_TYPE_DATA 0x01
241#define TX_PACKET_TYPE_MGMT 0x02
242
243#define ISR_EMPTY 0x00 /* no bits set in ISR */
244#define ISR_TxCOMPLETE 0x01 /* packet transmitted */
245#define ISR_RxCOMPLETE 0x02 /* packet received */
246#define ISR_RxFRAMELOST 0x04 /* Rx Frame lost */
247#define ISR_FATAL_ERROR 0x08 /* Fatal error */
248#define ISR_COMMAND_COMPLETE 0x10 /* command completed */
249#define ISR_OUT_OF_RANGE 0x20 /* command completed */
250#define ISR_IBSS_MERGE 0x40 /* (4.1.2.30): IBSS merge */
251#define ISR_GENERIC_IRQ 0x80
252
253#define Local_Mib_Type 0x01
254#define Mac_Address_Mib_Type 0x02
255#define Mac_Mib_Type 0x03
256#define Statistics_Mib_Type 0x04
257#define Mac_Mgmt_Mib_Type 0x05
258#define Mac_Wep_Mib_Type 0x06
259#define Phy_Mib_Type 0x07
260#define Multi_Domain_MIB 0x08
261
262#define MAC_MGMT_MIB_CUR_BSSID_POS 14
263#define MAC_MIB_FRAG_THRESHOLD_POS 8
264#define MAC_MIB_RTS_THRESHOLD_POS 10
265#define MAC_MIB_SHORT_RETRY_POS 16
266#define MAC_MIB_LONG_RETRY_POS 17
267#define MAC_MIB_SHORT_RETRY_LIMIT_POS 16
268#define MAC_MGMT_MIB_BEACON_PER_POS 0
269#define MAC_MGMT_MIB_STATION_ID_POS 6
270#define MAC_MGMT_MIB_CUR_PRIVACY_POS 11
271#define MAC_MGMT_MIB_CUR_BSSID_POS 14
272#define MAC_MGMT_MIB_PS_MODE_POS 53
273#define MAC_MGMT_MIB_LISTEN_INTERVAL_POS 54
274#define MAC_MGMT_MIB_MULTI_DOMAIN_IMPLEMENTED 56
275#define MAC_MGMT_MIB_MULTI_DOMAIN_ENABLED 57
276#define PHY_MIB_CHANNEL_POS 14
277#define PHY_MIB_RATE_SET_POS 20
278#define PHY_MIB_REG_DOMAIN_POS 26
279#define LOCAL_MIB_AUTO_TX_RATE_POS 3
280#define LOCAL_MIB_SSID_SIZE 5
281#define LOCAL_MIB_TX_PROMISCUOUS_POS 6
282#define LOCAL_MIB_TX_MGMT_RATE_POS 7
283#define LOCAL_MIB_TX_CONTROL_RATE_POS 8
284#define LOCAL_MIB_PREAMBLE_TYPE 9
285#define MAC_ADDR_MIB_MAC_ADDR_POS 0
286
287#define CMD_Set_MIB_Vars 0x01
288#define CMD_Get_MIB_Vars 0x02
289#define CMD_Scan 0x03
290#define CMD_Join 0x04
291#define CMD_Start 0x05
292#define CMD_EnableRadio 0x06
293#define CMD_DisableRadio 0x07
294#define CMD_SiteSurvey 0x0B
295
296#define CMD_STATUS_IDLE 0x00
297#define CMD_STATUS_COMPLETE 0x01
298#define CMD_STATUS_UNKNOWN 0x02
299#define CMD_STATUS_INVALID_PARAMETER 0x03
300#define CMD_STATUS_FUNCTION_NOT_SUPPORTED 0x04
301#define CMD_STATUS_TIME_OUT 0x07
302#define CMD_STATUS_IN_PROGRESS 0x08
303#define CMD_STATUS_REJECTED_RADIO_OFF 0x09
304#define CMD_STATUS_HOST_ERROR 0xFF
305#define CMD_STATUS_BUSY 0xFE
306
307#define CMD_BLOCK_COMMAND_OFFSET 0
308#define CMD_BLOCK_STATUS_OFFSET 1
309#define CMD_BLOCK_PARAMETERS_OFFSET 4
310
311#define SCAN_OPTIONS_SITE_SURVEY 0x80
312
313#define MGMT_FRAME_BODY_OFFSET 24
314#define MAX_AUTHENTICATION_RETRIES 3
315#define MAX_ASSOCIATION_RETRIES 3
316
317#define AUTHENTICATION_RESPONSE_TIME_OUT 1000
318
319#define MAX_WIRELESS_BODY 2316 /* mtu is 2312, CRC is 4 */
320#define LOOP_RETRY_LIMIT 500000
321
322#define ACTIVE_MODE 1
323#define PS_MODE 2
324
325#define MAX_ENCRYPTION_KEYS 4
326#define MAX_ENCRYPTION_KEY_SIZE 40
327
328/*
329 * 802.11 related definitions
330 */
331
332/*
333 * Regulatory Domains
334 */
335
336#define REG_DOMAIN_FCC 0x10 /* Channels 1-11 USA */
337#define REG_DOMAIN_DOC 0x20 /* Channel 1-11 Canada */
338#define REG_DOMAIN_ETSI 0x30 /* Channel 1-13 Europe (ex Spain/France) */
339#define REG_DOMAIN_SPAIN 0x31 /* Channel 10-11 Spain */
340#define REG_DOMAIN_FRANCE 0x32 /* Channel 10-13 France */
341#define REG_DOMAIN_MKK 0x40 /* Channel 14 Japan */
342#define REG_DOMAIN_MKK1 0x41 /* Channel 1-14 Japan(MKK1) */
343#define REG_DOMAIN_ISRAEL 0x50 /* Channel 3-9 ISRAEL */
344
345#define BSS_TYPE_AD_HOC 1
346#define BSS_TYPE_INFRASTRUCTURE 2
347
348#define SCAN_TYPE_ACTIVE 0
349#define SCAN_TYPE_PASSIVE 1
350
351#define LONG_PREAMBLE 0
352#define SHORT_PREAMBLE 1
353#define AUTO_PREAMBLE 2
354
355#define DATA_FRAME_WS_HEADER_SIZE 30
356
357/* promiscuous mode control */
358#define PROM_MODE_OFF 0x0
359#define PROM_MODE_UNKNOWN 0x1
360#define PROM_MODE_CRC_FAILED 0x2
361#define PROM_MODE_DUPLICATED 0x4
362#define PROM_MODE_MGMT 0x8
363#define PROM_MODE_CTRL 0x10
364#define PROM_MODE_BAD_PROTOCOL 0x20
365
366#define IFACE_INT_STATUS_OFFSET 0
367#define IFACE_INT_MASK_OFFSET 1
368#define IFACE_LOCKOUT_HOST_OFFSET 2
369#define IFACE_LOCKOUT_MAC_OFFSET 3
370#define IFACE_FUNC_CTRL_OFFSET 28
371#define IFACE_MAC_STAT_OFFSET 30
372#define IFACE_GENERIC_INT_TYPE_OFFSET 32
373
374#define CIPHER_SUITE_NONE 0
375#define CIPHER_SUITE_WEP_64 1
376#define CIPHER_SUITE_TKIP 2
377#define CIPHER_SUITE_AES 3
378#define CIPHER_SUITE_CCX 4
379#define CIPHER_SUITE_WEP_128 5
380
381/*
382 * IFACE MACROS & definitions
383 */
384
385/*
386 * FuncCtrl field:
387 */
388#define FUNC_CTRL_TxENABLE 0x10
389#define FUNC_CTRL_RxENABLE 0x20
390#define FUNC_CTRL_INIT_COMPLETE 0x01
391
392/* A stub firmware image which reads the MAC address from NVRAM on the card.
393 For copyright information and source see the end of this file. */
394static u8 mac_reader[] = {
395 0x06, 0x00, 0x00, 0xea, 0x04, 0x00, 0x00, 0xea, 0x03, 0x00, 0x00, 0xea, 0x02, 0x00, 0x00, 0xea,
396 0x01, 0x00, 0x00, 0xea, 0x00, 0x00, 0x00, 0xea, 0xff, 0xff, 0xff, 0xea, 0xfe, 0xff, 0xff, 0xea,
397 0xd3, 0x00, 0xa0, 0xe3, 0x00, 0xf0, 0x21, 0xe1, 0x0e, 0x04, 0xa0, 0xe3, 0x00, 0x10, 0xa0, 0xe3,
398 0x81, 0x11, 0xa0, 0xe1, 0x00, 0x10, 0x81, 0xe3, 0x00, 0x10, 0x80, 0xe5, 0x1c, 0x10, 0x90, 0xe5,
399 0x10, 0x10, 0xc1, 0xe3, 0x1c, 0x10, 0x80, 0xe5, 0x01, 0x10, 0xa0, 0xe3, 0x08, 0x10, 0x80, 0xe5,
400 0x02, 0x03, 0xa0, 0xe3, 0x00, 0x10, 0xa0, 0xe3, 0xb0, 0x10, 0xc0, 0xe1, 0xb4, 0x10, 0xc0, 0xe1,
401 0xb8, 0x10, 0xc0, 0xe1, 0xbc, 0x10, 0xc0, 0xe1, 0x56, 0xdc, 0xa0, 0xe3, 0x21, 0x00, 0x00, 0xeb,
402 0x0a, 0x00, 0xa0, 0xe3, 0x1a, 0x00, 0x00, 0xeb, 0x10, 0x00, 0x00, 0xeb, 0x07, 0x00, 0x00, 0xeb,
403 0x02, 0x03, 0xa0, 0xe3, 0x02, 0x14, 0xa0, 0xe3, 0xb4, 0x10, 0xc0, 0xe1, 0x4c, 0x10, 0x9f, 0xe5,
404 0xbc, 0x10, 0xc0, 0xe1, 0x10, 0x10, 0xa0, 0xe3, 0xb8, 0x10, 0xc0, 0xe1, 0xfe, 0xff, 0xff, 0xea,
405 0x00, 0x40, 0x2d, 0xe9, 0x00, 0x20, 0xa0, 0xe3, 0x02, 0x3c, 0xa0, 0xe3, 0x00, 0x10, 0xa0, 0xe3,
406 0x28, 0x00, 0x9f, 0xe5, 0x37, 0x00, 0x00, 0xeb, 0x00, 0x40, 0xbd, 0xe8, 0x1e, 0xff, 0x2f, 0xe1,
407 0x00, 0x40, 0x2d, 0xe9, 0x12, 0x2e, 0xa0, 0xe3, 0x06, 0x30, 0xa0, 0xe3, 0x00, 0x10, 0xa0, 0xe3,
408 0x02, 0x04, 0xa0, 0xe3, 0x2f, 0x00, 0x00, 0xeb, 0x00, 0x40, 0xbd, 0xe8, 0x1e, 0xff, 0x2f, 0xe1,
409 0x00, 0x02, 0x00, 0x02, 0x80, 0x01, 0x90, 0xe0, 0x01, 0x00, 0x00, 0x0a, 0x01, 0x00, 0x50, 0xe2,
410 0xfc, 0xff, 0xff, 0xea, 0x1e, 0xff, 0x2f, 0xe1, 0x80, 0x10, 0xa0, 0xe3, 0xf3, 0x06, 0xa0, 0xe3,
411 0x00, 0x10, 0x80, 0xe5, 0x00, 0x10, 0xa0, 0xe3, 0x00, 0x10, 0x80, 0xe5, 0x01, 0x10, 0xa0, 0xe3,
412 0x04, 0x10, 0x80, 0xe5, 0x00, 0x10, 0x80, 0xe5, 0x0e, 0x34, 0xa0, 0xe3, 0x1c, 0x10, 0x93, 0xe5,
413 0x02, 0x1a, 0x81, 0xe3, 0x1c, 0x10, 0x83, 0xe5, 0x58, 0x11, 0x9f, 0xe5, 0x30, 0x10, 0x80, 0xe5,
414 0x54, 0x11, 0x9f, 0xe5, 0x34, 0x10, 0x80, 0xe5, 0x38, 0x10, 0x80, 0xe5, 0x3c, 0x10, 0x80, 0xe5,
415 0x10, 0x10, 0x90, 0xe5, 0x08, 0x00, 0x90, 0xe5, 0x1e, 0xff, 0x2f, 0xe1, 0xf3, 0x16, 0xa0, 0xe3,
416 0x08, 0x00, 0x91, 0xe5, 0x05, 0x00, 0xa0, 0xe3, 0x0c, 0x00, 0x81, 0xe5, 0x10, 0x00, 0x91, 0xe5,
417 0x02, 0x00, 0x10, 0xe3, 0xfc, 0xff, 0xff, 0x0a, 0xff, 0x00, 0xa0, 0xe3, 0x0c, 0x00, 0x81, 0xe5,
418 0x10, 0x00, 0x91, 0xe5, 0x02, 0x00, 0x10, 0xe3, 0xfc, 0xff, 0xff, 0x0a, 0x08, 0x00, 0x91, 0xe5,
419 0x10, 0x00, 0x91, 0xe5, 0x01, 0x00, 0x10, 0xe3, 0xfc, 0xff, 0xff, 0x0a, 0x08, 0x00, 0x91, 0xe5,
420 0xff, 0x00, 0x00, 0xe2, 0x1e, 0xff, 0x2f, 0xe1, 0x30, 0x40, 0x2d, 0xe9, 0x00, 0x50, 0xa0, 0xe1,
421 0x03, 0x40, 0xa0, 0xe1, 0xa2, 0x02, 0xa0, 0xe1, 0x08, 0x00, 0x00, 0xe2, 0x03, 0x00, 0x80, 0xe2,
422 0xd8, 0x10, 0x9f, 0xe5, 0x00, 0x00, 0xc1, 0xe5, 0x01, 0x20, 0xc1, 0xe5, 0xe2, 0xff, 0xff, 0xeb,
423 0x01, 0x00, 0x10, 0xe3, 0xfc, 0xff, 0xff, 0x1a, 0x14, 0x00, 0xa0, 0xe3, 0xc4, 0xff, 0xff, 0xeb,
424 0x04, 0x20, 0xa0, 0xe1, 0x05, 0x10, 0xa0, 0xe1, 0x02, 0x00, 0xa0, 0xe3, 0x01, 0x00, 0x00, 0xeb,
425 0x30, 0x40, 0xbd, 0xe8, 0x1e, 0xff, 0x2f, 0xe1, 0x70, 0x40, 0x2d, 0xe9, 0xf3, 0x46, 0xa0, 0xe3,
426 0x00, 0x30, 0xa0, 0xe3, 0x00, 0x00, 0x50, 0xe3, 0x08, 0x00, 0x00, 0x9a, 0x8c, 0x50, 0x9f, 0xe5,
427 0x03, 0x60, 0xd5, 0xe7, 0x0c, 0x60, 0x84, 0xe5, 0x10, 0x60, 0x94, 0xe5, 0x02, 0x00, 0x16, 0xe3,
428 0xfc, 0xff, 0xff, 0x0a, 0x01, 0x30, 0x83, 0xe2, 0x00, 0x00, 0x53, 0xe1, 0xf7, 0xff, 0xff, 0x3a,
429 0xff, 0x30, 0xa0, 0xe3, 0x0c, 0x30, 0x84, 0xe5, 0x08, 0x00, 0x94, 0xe5, 0x10, 0x00, 0x94, 0xe5,
430 0x01, 0x00, 0x10, 0xe3, 0xfc, 0xff, 0xff, 0x0a, 0x08, 0x00, 0x94, 0xe5, 0x00, 0x00, 0xa0, 0xe3,
431 0x00, 0x00, 0x52, 0xe3, 0x0b, 0x00, 0x00, 0x9a, 0x10, 0x50, 0x94, 0xe5, 0x02, 0x00, 0x15, 0xe3,
432 0xfc, 0xff, 0xff, 0x0a, 0x0c, 0x30, 0x84, 0xe5, 0x10, 0x50, 0x94, 0xe5, 0x01, 0x00, 0x15, 0xe3,
433 0xfc, 0xff, 0xff, 0x0a, 0x08, 0x50, 0x94, 0xe5, 0x01, 0x50, 0xc1, 0xe4, 0x01, 0x00, 0x80, 0xe2,
434 0x02, 0x00, 0x50, 0xe1, 0xf3, 0xff, 0xff, 0x3a, 0xc8, 0x00, 0xa0, 0xe3, 0x98, 0xff, 0xff, 0xeb,
435 0x70, 0x40, 0xbd, 0xe8, 0x1e, 0xff, 0x2f, 0xe1, 0x01, 0x0c, 0x00, 0x02, 0x01, 0x02, 0x00, 0x02,
436 0x00, 0x01, 0x00, 0x02
437};
438
439struct atmel_private {
440 void *card; /* Bus dependent structure varies for PCcard */
441 int (*present_callback)(void *); /* And callback which uses it */
442 char firmware_id[32];
443 AtmelFWType firmware_type;
444 u8 *firmware;
445 int firmware_length;
446 struct timer_list management_timer;
447 struct net_device *dev;
448 struct device *sys_dev;
449 struct iw_statistics wstats;
450 spinlock_t irqlock, timerlock; /* spinlocks */
451 enum { BUS_TYPE_PCCARD, BUS_TYPE_PCI } bus_type;
452 enum {
453 CARD_TYPE_PARALLEL_FLASH,
454 CARD_TYPE_SPI_FLASH,
455 CARD_TYPE_EEPROM
456 } card_type;
457 int do_rx_crc; /* If we need to CRC incoming packets */
458 int probe_crc; /* set if we don't yet know */
459 int crc_ok_cnt, crc_ko_cnt; /* counters for probing */
460 u16 rx_desc_head;
461 u16 tx_desc_free, tx_desc_head, tx_desc_tail, tx_desc_previous;
462 u16 tx_free_mem, tx_buff_head, tx_buff_tail;
463
464 u16 frag_seq, frag_len, frag_no;
465 u8 frag_source[6];
466
467 u8 wep_is_on, default_key, exclude_unencrypted, encryption_level;
468 u8 group_cipher_suite, pairwise_cipher_suite;
469 u8 wep_keys[MAX_ENCRYPTION_KEYS][MAX_ENCRYPTION_KEY_SIZE];
470 int wep_key_len[MAX_ENCRYPTION_KEYS];
471 int use_wpa, radio_on_broken; /* firmware dependent stuff. */
472
473 u16 host_info_base;
474 struct host_info_struct {
475 /* NB this is matched to the hardware, don't change. */
476 u8 volatile int_status;
477 u8 volatile int_mask;
478 u8 volatile lockout_host;
479 u8 volatile lockout_mac;
480
481 u16 tx_buff_pos;
482 u16 tx_buff_size;
483 u16 tx_desc_pos;
484 u16 tx_desc_count;
485
486 u16 rx_buff_pos;
487 u16 rx_buff_size;
488 u16 rx_desc_pos;
489 u16 rx_desc_count;
490
491 u16 build_version;
492 u16 command_pos;
493
494 u16 major_version;
495 u16 minor_version;
496
497 u16 func_ctrl;
498 u16 mac_status;
499 u16 generic_IRQ_type;
500 u8 reserved[2];
501 } host_info;
502
503 enum {
504 STATION_STATE_SCANNING,
505 STATION_STATE_JOINNING,
506 STATION_STATE_AUTHENTICATING,
507 STATION_STATE_ASSOCIATING,
508 STATION_STATE_READY,
509 STATION_STATE_REASSOCIATING,
510 STATION_STATE_DOWN,
511 STATION_STATE_MGMT_ERROR
512 } station_state;
513
514 int operating_mode, power_mode;
515 unsigned long last_qual;
516 int beacons_this_sec;
517 int channel;
518 int reg_domain, config_reg_domain;
519 int tx_rate;
520 int auto_tx_rate;
521 int rts_threshold;
522 int frag_threshold;
523 int long_retry, short_retry;
524 int preamble;
525 int default_beacon_period, beacon_period, listen_interval;
526 int CurrentAuthentTransactionSeqNum, ExpectedAuthentTransactionSeqNum;
527 int AuthenticationRequestRetryCnt, AssociationRequestRetryCnt, ReAssociationRequestRetryCnt;
528 enum {
529 SITE_SURVEY_IDLE,
530 SITE_SURVEY_IN_PROGRESS,
531 SITE_SURVEY_COMPLETED
532 } site_survey_state;
533 unsigned long last_survey;
534
535 int station_was_associated, station_is_associated;
536 int fast_scan;
537
538 struct bss_info {
539 int channel;
540 int SSIDsize;
541 int RSSI;
542 int UsingWEP;
543 int preamble;
544 int beacon_period;
545 int BSStype;
546 u8 BSSID[6];
547 u8 SSID[MAX_SSID_LENGTH];
548 } BSSinfo[MAX_BSS_ENTRIES];
549 int BSS_list_entries, current_BSS;
550 int connect_to_any_BSS;
551 int SSID_size, new_SSID_size;
552 u8 CurrentBSSID[6], BSSID[6];
553 u8 SSID[MAX_SSID_LENGTH], new_SSID[MAX_SSID_LENGTH];
554 u64 last_beacon_timestamp;
555 u8 rx_buf[MAX_WIRELESS_BODY];
556};
557
558static u8 atmel_basic_rates[4] = {0x82, 0x84, 0x0b, 0x16};
559
560static const struct {
561 int reg_domain;
562 int min, max;
563 char *name;
564} channel_table[] = { { REG_DOMAIN_FCC, 1, 11, "USA" },
565 { REG_DOMAIN_DOC, 1, 11, "Canada" },
566 { REG_DOMAIN_ETSI, 1, 13, "Europe" },
567 { REG_DOMAIN_SPAIN, 10, 11, "Spain" },
568 { REG_DOMAIN_FRANCE, 10, 13, "France" },
569 { REG_DOMAIN_MKK, 14, 14, "MKK" },
570 { REG_DOMAIN_MKK1, 1, 14, "MKK1" },
571 { REG_DOMAIN_ISRAEL, 3, 9, "Israel"} };
572
573static void build_wpa_mib(struct atmel_private *priv);
574static void atmel_copy_to_card(struct net_device *dev, u16 dest,
575 const unsigned char *src, u16 len);
576static void atmel_copy_to_host(struct net_device *dev, unsigned char *dest,
577 u16 src, u16 len);
578static void atmel_set_gcr(struct net_device *dev, u16 mask);
579static void atmel_clear_gcr(struct net_device *dev, u16 mask);
580static int atmel_lock_mac(struct atmel_private *priv);
581static void atmel_wmem32(struct atmel_private *priv, u16 pos, u32 data);
582static void atmel_command_irq(struct atmel_private *priv);
583static int atmel_validate_channel(struct atmel_private *priv, int channel);
584static void atmel_management_frame(struct atmel_private *priv,
585 struct ieee80211_hdr *header,
586 u16 frame_len, u8 rssi);
587static void atmel_management_timer(struct timer_list *t);
588static void atmel_send_command(struct atmel_private *priv, int command,
589 void *cmd, int cmd_size);
590static int atmel_send_command_wait(struct atmel_private *priv, int command,
591 void *cmd, int cmd_size);
592static void atmel_transmit_management_frame(struct atmel_private *priv,
593 struct ieee80211_hdr *header,
594 u8 *body, int body_len);
595
596static u8 atmel_get_mib8(struct atmel_private *priv, u8 type, u8 index);
597static void atmel_set_mib8(struct atmel_private *priv, u8 type, u8 index,
598 u8 data);
599static void atmel_set_mib16(struct atmel_private *priv, u8 type, u8 index,
600 u16 data);
601static void atmel_set_mib(struct atmel_private *priv, u8 type, u8 index,
602 const u8 *data, int data_len);
603static void atmel_get_mib(struct atmel_private *priv, u8 type, u8 index,
604 u8 *data, int data_len);
605static void atmel_scan(struct atmel_private *priv, int specific_ssid);
606static void atmel_join_bss(struct atmel_private *priv, int bss_index);
607static void atmel_smooth_qual(struct atmel_private *priv);
608static void atmel_writeAR(struct net_device *dev, u16 data);
609static int probe_atmel_card(struct net_device *dev);
610static int reset_atmel_card(struct net_device *dev);
611static void atmel_enter_state(struct atmel_private *priv, int new_state);
612int atmel_open (struct net_device *dev);
613
614static inline u16 atmel_hi(struct atmel_private *priv, u16 offset)
615{
616 return priv->host_info_base + offset;
617}
618
619static inline u16 atmel_co(struct atmel_private *priv, u16 offset)
620{
621 return priv->host_info.command_pos + offset;
622}
623
624static inline u16 atmel_rx(struct atmel_private *priv, u16 offset, u16 desc)
625{
626 return priv->host_info.rx_desc_pos + (sizeof(struct rx_desc) * desc) + offset;
627}
628
629static inline u16 atmel_tx(struct atmel_private *priv, u16 offset, u16 desc)
630{
631 return priv->host_info.tx_desc_pos + (sizeof(struct tx_desc) * desc) + offset;
632}
633
634static inline u8 atmel_read8(struct net_device *dev, u16 offset)
635{
636 return inb(dev->base_addr + offset);
637}
638
639static inline void atmel_write8(struct net_device *dev, u16 offset, u8 data)
640{
641 outb(data, dev->base_addr + offset);
642}
643
644static inline u16 atmel_read16(struct net_device *dev, u16 offset)
645{
646 return inw(dev->base_addr + offset);
647}
648
649static inline void atmel_write16(struct net_device *dev, u16 offset, u16 data)
650{
651 outw(data, dev->base_addr + offset);
652}
653
654static inline u8 atmel_rmem8(struct atmel_private *priv, u16 pos)
655{
656 atmel_writeAR(priv->dev, pos);
657 return atmel_read8(priv->dev, DR);
658}
659
660static inline void atmel_wmem8(struct atmel_private *priv, u16 pos, u16 data)
661{
662 atmel_writeAR(priv->dev, pos);
663 atmel_write8(priv->dev, DR, data);
664}
665
666static inline u16 atmel_rmem16(struct atmel_private *priv, u16 pos)
667{
668 atmel_writeAR(priv->dev, pos);
669 return atmel_read16(priv->dev, DR);
670}
671
672static inline void atmel_wmem16(struct atmel_private *priv, u16 pos, u16 data)
673{
674 atmel_writeAR(priv->dev, pos);
675 atmel_write16(priv->dev, DR, data);
676}
677
678static const struct iw_handler_def atmel_handler_def;
679
680static void tx_done_irq(struct atmel_private *priv)
681{
682 int i;
683
684 for (i = 0;
685 atmel_rmem8(priv, atmel_tx(priv, TX_DESC_FLAGS_OFFSET, priv->tx_desc_head)) == TX_DONE &&
686 i < priv->host_info.tx_desc_count;
687 i++) {
688 u8 status = atmel_rmem8(priv, atmel_tx(priv, TX_DESC_STATUS_OFFSET, priv->tx_desc_head));
689 u16 msdu_size = atmel_rmem16(priv, atmel_tx(priv, TX_DESC_SIZE_OFFSET, priv->tx_desc_head));
690 u8 type = atmel_rmem8(priv, atmel_tx(priv, TX_DESC_PACKET_TYPE_OFFSET, priv->tx_desc_head));
691
692 atmel_wmem8(priv, atmel_tx(priv, TX_DESC_FLAGS_OFFSET, priv->tx_desc_head), 0);
693
694 priv->tx_free_mem += msdu_size;
695 priv->tx_desc_free++;
696
697 if (priv->tx_buff_head + msdu_size > (priv->host_info.tx_buff_pos + priv->host_info.tx_buff_size))
698 priv->tx_buff_head = 0;
699 else
700 priv->tx_buff_head += msdu_size;
701
702 if (priv->tx_desc_head < (priv->host_info.tx_desc_count - 1))
703 priv->tx_desc_head++ ;
704 else
705 priv->tx_desc_head = 0;
706
707 if (type == TX_PACKET_TYPE_DATA) {
708 if (status == TX_STATUS_SUCCESS)
709 priv->dev->stats.tx_packets++;
710 else
711 priv->dev->stats.tx_errors++;
712 netif_wake_queue(priv->dev);
713 }
714 }
715}
716
717static u16 find_tx_buff(struct atmel_private *priv, u16 len)
718{
719 u16 bottom_free = priv->host_info.tx_buff_size - priv->tx_buff_tail;
720
721 if (priv->tx_desc_free == 3 || priv->tx_free_mem < len)
722 return 0;
723
724 if (bottom_free >= len)
725 return priv->host_info.tx_buff_pos + priv->tx_buff_tail;
726
727 if (priv->tx_free_mem - bottom_free >= len) {
728 priv->tx_buff_tail = 0;
729 return priv->host_info.tx_buff_pos;
730 }
731
732 return 0;
733}
734
735static void tx_update_descriptor(struct atmel_private *priv, int is_bcast,
736 u16 len, u16 buff, u8 type)
737{
738 atmel_wmem16(priv, atmel_tx(priv, TX_DESC_POS_OFFSET, priv->tx_desc_tail), buff);
739 atmel_wmem16(priv, atmel_tx(priv, TX_DESC_SIZE_OFFSET, priv->tx_desc_tail), len);
740 if (!priv->use_wpa)
741 atmel_wmem16(priv, atmel_tx(priv, TX_DESC_HOST_LENGTH_OFFSET, priv->tx_desc_tail), len);
742 atmel_wmem8(priv, atmel_tx(priv, TX_DESC_PACKET_TYPE_OFFSET, priv->tx_desc_tail), type);
743 atmel_wmem8(priv, atmel_tx(priv, TX_DESC_RATE_OFFSET, priv->tx_desc_tail), priv->tx_rate);
744 atmel_wmem8(priv, atmel_tx(priv, TX_DESC_RETRY_OFFSET, priv->tx_desc_tail), 0);
745 if (priv->use_wpa) {
746 int cipher_type, cipher_length;
747 if (is_bcast) {
748 cipher_type = priv->group_cipher_suite;
749 if (cipher_type == CIPHER_SUITE_WEP_64 ||
750 cipher_type == CIPHER_SUITE_WEP_128)
751 cipher_length = 8;
752 else if (cipher_type == CIPHER_SUITE_TKIP)
753 cipher_length = 12;
754 else if (priv->pairwise_cipher_suite == CIPHER_SUITE_WEP_64 ||
755 priv->pairwise_cipher_suite == CIPHER_SUITE_WEP_128) {
756 cipher_type = priv->pairwise_cipher_suite;
757 cipher_length = 8;
758 } else {
759 cipher_type = CIPHER_SUITE_NONE;
760 cipher_length = 0;
761 }
762 } else {
763 cipher_type = priv->pairwise_cipher_suite;
764 if (cipher_type == CIPHER_SUITE_WEP_64 ||
765 cipher_type == CIPHER_SUITE_WEP_128)
766 cipher_length = 8;
767 else if (cipher_type == CIPHER_SUITE_TKIP)
768 cipher_length = 12;
769 else if (priv->group_cipher_suite == CIPHER_SUITE_WEP_64 ||
770 priv->group_cipher_suite == CIPHER_SUITE_WEP_128) {
771 cipher_type = priv->group_cipher_suite;
772 cipher_length = 8;
773 } else {
774 cipher_type = CIPHER_SUITE_NONE;
775 cipher_length = 0;
776 }
777 }
778
779 atmel_wmem8(priv, atmel_tx(priv, TX_DESC_CIPHER_TYPE_OFFSET, priv->tx_desc_tail),
780 cipher_type);
781 atmel_wmem8(priv, atmel_tx(priv, TX_DESC_CIPHER_LENGTH_OFFSET, priv->tx_desc_tail),
782 cipher_length);
783 }
784 atmel_wmem32(priv, atmel_tx(priv, TX_DESC_NEXT_OFFSET, priv->tx_desc_tail), 0x80000000L);
785 atmel_wmem8(priv, atmel_tx(priv, TX_DESC_FLAGS_OFFSET, priv->tx_desc_tail), TX_FIRM_OWN);
786 if (priv->tx_desc_previous != priv->tx_desc_tail)
787 atmel_wmem32(priv, atmel_tx(priv, TX_DESC_NEXT_OFFSET, priv->tx_desc_previous), 0);
788 priv->tx_desc_previous = priv->tx_desc_tail;
789 if (priv->tx_desc_tail < (priv->host_info.tx_desc_count - 1))
790 priv->tx_desc_tail++;
791 else
792 priv->tx_desc_tail = 0;
793 priv->tx_desc_free--;
794 priv->tx_free_mem -= len;
795}
796
797static netdev_tx_t start_tx(struct sk_buff *skb, struct net_device *dev)
798{
799 struct atmel_private *priv = netdev_priv(dev);
800 struct ieee80211_hdr header;
801 unsigned long flags;
802 u16 buff, frame_ctl, len = (ETH_ZLEN < skb->len) ? skb->len : ETH_ZLEN;
803
804 if (priv->card && priv->present_callback &&
805 !(*priv->present_callback)(priv->card)) {
806 dev->stats.tx_errors++;
807 dev_kfree_skb(skb);
808 return NETDEV_TX_OK;
809 }
810
811 if (priv->station_state != STATION_STATE_READY) {
812 dev->stats.tx_errors++;
813 dev_kfree_skb(skb);
814 return NETDEV_TX_OK;
815 }
816
817 /* first ensure the timer func cannot run */
818 spin_lock_bh(&priv->timerlock);
819 /* then stop the hardware ISR */
820 spin_lock_irqsave(&priv->irqlock, flags);
821 /* nb doing the above in the opposite order will deadlock */
822
823 /* The Wireless Header is 30 bytes. In the Ethernet packet we "cut" the
824 12 first bytes (containing DA/SA) and put them in the appropriate
825 fields of the Wireless Header. Thus the packet length is then the
826 initial + 18 (+30-12) */
827
828 if (!(buff = find_tx_buff(priv, len + 18))) {
829 dev->stats.tx_dropped++;
830 spin_unlock_irqrestore(&priv->irqlock, flags);
831 spin_unlock_bh(&priv->timerlock);
832 netif_stop_queue(dev);
833 return NETDEV_TX_BUSY;
834 }
835
836 frame_ctl = IEEE80211_FTYPE_DATA;
837 header.duration_id = 0;
838 header.seq_ctrl = 0;
839 if (priv->wep_is_on)
840 frame_ctl |= IEEE80211_FCTL_PROTECTED;
841 if (priv->operating_mode == IW_MODE_ADHOC) {
842 skb_copy_from_linear_data(skb, &header.addr1, ETH_ALEN);
843 memcpy(&header.addr2, dev->dev_addr, ETH_ALEN);
844 memcpy(&header.addr3, priv->BSSID, ETH_ALEN);
845 } else {
846 frame_ctl |= IEEE80211_FCTL_TODS;
847 memcpy(&header.addr1, priv->CurrentBSSID, ETH_ALEN);
848 memcpy(&header.addr2, dev->dev_addr, ETH_ALEN);
849 skb_copy_from_linear_data(skb, &header.addr3, ETH_ALEN);
850 }
851
852 if (priv->use_wpa)
853 memcpy(&header.addr4, rfc1042_header, ETH_ALEN);
854
855 header.frame_control = cpu_to_le16(frame_ctl);
856 /* Copy the wireless header into the card */
857 atmel_copy_to_card(dev, buff, (unsigned char *)&header, DATA_FRAME_WS_HEADER_SIZE);
858 /* Copy the packet sans its 802.3 header addresses which have been replaced */
859 atmel_copy_to_card(dev, buff + DATA_FRAME_WS_HEADER_SIZE, skb->data + 12, len - 12);
860 priv->tx_buff_tail += len - 12 + DATA_FRAME_WS_HEADER_SIZE;
861
862 /* low bit of first byte of destination tells us if broadcast */
863 tx_update_descriptor(priv, *(skb->data) & 0x01, len + 18, buff, TX_PACKET_TYPE_DATA);
864 dev->stats.tx_bytes += len;
865
866 spin_unlock_irqrestore(&priv->irqlock, flags);
867 spin_unlock_bh(&priv->timerlock);
868 dev_kfree_skb(skb);
869
870 return NETDEV_TX_OK;
871}
872
873static void atmel_transmit_management_frame(struct atmel_private *priv,
874 struct ieee80211_hdr *header,
875 u8 *body, int body_len)
876{
877 u16 buff;
878 int len = MGMT_FRAME_BODY_OFFSET + body_len;
879
880 if (!(buff = find_tx_buff(priv, len)))
881 return;
882
883 atmel_copy_to_card(priv->dev, buff, (u8 *)header, MGMT_FRAME_BODY_OFFSET);
884 atmel_copy_to_card(priv->dev, buff + MGMT_FRAME_BODY_OFFSET, body, body_len);
885 priv->tx_buff_tail += len;
886 tx_update_descriptor(priv, header->addr1[0] & 0x01, len, buff, TX_PACKET_TYPE_MGMT);
887}
888
889static void fast_rx_path(struct atmel_private *priv,
890 struct ieee80211_hdr *header,
891 u16 msdu_size, u16 rx_packet_loc, u32 crc)
892{
893 /* fast path: unfragmented packet copy directly into skbuf */
894 u8 mac4[6];
895 struct sk_buff *skb;
896 unsigned char *skbp;
897
898 /* get the final, mac 4 header field, this tells us encapsulation */
899 atmel_copy_to_host(priv->dev, mac4, rx_packet_loc + 24, 6);
900 msdu_size -= 6;
901
902 if (priv->do_rx_crc) {
903 crc = crc32_le(crc, mac4, 6);
904 msdu_size -= 4;
905 }
906
907 if (!(skb = dev_alloc_skb(msdu_size + 14))) {
908 priv->dev->stats.rx_dropped++;
909 return;
910 }
911
912 skb_reserve(skb, 2);
913 skbp = skb_put(skb, msdu_size + 12);
914 atmel_copy_to_host(priv->dev, skbp + 12, rx_packet_loc + 30, msdu_size);
915
916 if (priv->do_rx_crc) {
917 u32 netcrc;
918 crc = crc32_le(crc, skbp + 12, msdu_size);
919 atmel_copy_to_host(priv->dev, (void *)&netcrc, rx_packet_loc + 30 + msdu_size, 4);
920 if ((crc ^ 0xffffffff) != netcrc) {
921 priv->dev->stats.rx_crc_errors++;
922 dev_kfree_skb(skb);
923 return;
924 }
925 }
926
927 memcpy(skbp, header->addr1, ETH_ALEN); /* destination address */
928 if (le16_to_cpu(header->frame_control) & IEEE80211_FCTL_FROMDS)
929 memcpy(&skbp[ETH_ALEN], header->addr3, ETH_ALEN);
930 else
931 memcpy(&skbp[ETH_ALEN], header->addr2, ETH_ALEN); /* source address */
932
933 skb->protocol = eth_type_trans(skb, priv->dev);
934 skb->ip_summed = CHECKSUM_NONE;
935 netif_rx(skb);
936 priv->dev->stats.rx_bytes += 12 + msdu_size;
937 priv->dev->stats.rx_packets++;
938}
939
940/* Test to see if the packet in card memory at packet_loc has a valid CRC
941 It doesn't matter that this is slow: it is only used to proble the first few
942 packets. */
943static int probe_crc(struct atmel_private *priv, u16 packet_loc, u16 msdu_size)
944{
945 int i = msdu_size - 4;
946 u32 netcrc, crc = 0xffffffff;
947
948 if (msdu_size < 4)
949 return 0;
950
951 atmel_copy_to_host(priv->dev, (void *)&netcrc, packet_loc + i, 4);
952
953 atmel_writeAR(priv->dev, packet_loc);
954 while (i--) {
955 u8 octet = atmel_read8(priv->dev, DR);
956 crc = crc32_le(crc, &octet, 1);
957 }
958
959 return (crc ^ 0xffffffff) == netcrc;
960}
961
962static void frag_rx_path(struct atmel_private *priv,
963 struct ieee80211_hdr *header,
964 u16 msdu_size, u16 rx_packet_loc, u32 crc, u16 seq_no,
965 u8 frag_no, int more_frags)
966{
967 u8 mac4[ETH_ALEN];
968 u8 source[ETH_ALEN];
969 struct sk_buff *skb;
970
971 if (le16_to_cpu(header->frame_control) & IEEE80211_FCTL_FROMDS)
972 memcpy(source, header->addr3, ETH_ALEN);
973 else
974 memcpy(source, header->addr2, ETH_ALEN);
975
976 rx_packet_loc += 24; /* skip header */
977
978 if (priv->do_rx_crc)
979 msdu_size -= 4;
980
981 if (frag_no == 0) { /* first fragment */
982 atmel_copy_to_host(priv->dev, mac4, rx_packet_loc, ETH_ALEN);
983 msdu_size -= ETH_ALEN;
984 rx_packet_loc += ETH_ALEN;
985
986 if (priv->do_rx_crc)
987 crc = crc32_le(crc, mac4, 6);
988
989 priv->frag_seq = seq_no;
990 priv->frag_no = 1;
991 priv->frag_len = msdu_size;
992 memcpy(priv->frag_source, source, ETH_ALEN);
993 memcpy(&priv->rx_buf[ETH_ALEN], source, ETH_ALEN);
994 memcpy(priv->rx_buf, header->addr1, ETH_ALEN);
995
996 atmel_copy_to_host(priv->dev, &priv->rx_buf[12], rx_packet_loc, msdu_size);
997
998 if (priv->do_rx_crc) {
999 u32 netcrc;
1000 crc = crc32_le(crc, &priv->rx_buf[12], msdu_size);
1001 atmel_copy_to_host(priv->dev, (void *)&netcrc, rx_packet_loc + msdu_size, 4);
1002 if ((crc ^ 0xffffffff) != netcrc) {
1003 priv->dev->stats.rx_crc_errors++;
1004 eth_broadcast_addr(priv->frag_source);
1005 }
1006 }
1007
1008 } else if (priv->frag_no == frag_no &&
1009 priv->frag_seq == seq_no &&
1010 memcmp(priv->frag_source, source, ETH_ALEN) == 0) {
1011
1012 atmel_copy_to_host(priv->dev, &priv->rx_buf[12 + priv->frag_len],
1013 rx_packet_loc, msdu_size);
1014 if (priv->do_rx_crc) {
1015 u32 netcrc;
1016 crc = crc32_le(crc,
1017 &priv->rx_buf[12 + priv->frag_len],
1018 msdu_size);
1019 atmel_copy_to_host(priv->dev, (void *)&netcrc, rx_packet_loc + msdu_size, 4);
1020 if ((crc ^ 0xffffffff) != netcrc) {
1021 priv->dev->stats.rx_crc_errors++;
1022 eth_broadcast_addr(priv->frag_source);
1023 more_frags = 1; /* don't send broken assembly */
1024 }
1025 }
1026
1027 priv->frag_len += msdu_size;
1028 priv->frag_no++;
1029
1030 if (!more_frags) { /* last one */
1031 eth_broadcast_addr(priv->frag_source);
1032 if (!(skb = dev_alloc_skb(priv->frag_len + 14))) {
1033 priv->dev->stats.rx_dropped++;
1034 } else {
1035 skb_reserve(skb, 2);
1036 skb_put_data(skb, priv->rx_buf,
1037 priv->frag_len + 12);
1038 skb->protocol = eth_type_trans(skb, priv->dev);
1039 skb->ip_summed = CHECKSUM_NONE;
1040 netif_rx(skb);
1041 priv->dev->stats.rx_bytes += priv->frag_len + 12;
1042 priv->dev->stats.rx_packets++;
1043 }
1044 }
1045 } else
1046 priv->wstats.discard.fragment++;
1047}
1048
1049static void rx_done_irq(struct atmel_private *priv)
1050{
1051 int i;
1052 struct ieee80211_hdr header;
1053
1054 for (i = 0;
1055 atmel_rmem8(priv, atmel_rx(priv, RX_DESC_FLAGS_OFFSET, priv->rx_desc_head)) == RX_DESC_FLAG_VALID &&
1056 i < priv->host_info.rx_desc_count;
1057 i++) {
1058
1059 u16 msdu_size, rx_packet_loc, frame_ctl, seq_control;
1060 u8 status = atmel_rmem8(priv, atmel_rx(priv, RX_DESC_STATUS_OFFSET, priv->rx_desc_head));
1061 u32 crc = 0xffffffff;
1062
1063 if (status != RX_STATUS_SUCCESS) {
1064 if (status == 0xc1) /* determined by experiment */
1065 priv->wstats.discard.nwid++;
1066 else
1067 priv->dev->stats.rx_errors++;
1068 goto next;
1069 }
1070
1071 msdu_size = atmel_rmem16(priv, atmel_rx(priv, RX_DESC_MSDU_SIZE_OFFSET, priv->rx_desc_head));
1072 rx_packet_loc = atmel_rmem16(priv, atmel_rx(priv, RX_DESC_MSDU_POS_OFFSET, priv->rx_desc_head));
1073
1074 if (msdu_size < 30) {
1075 priv->dev->stats.rx_errors++;
1076 goto next;
1077 }
1078
1079 /* Get header as far as end of seq_ctrl */
1080 atmel_copy_to_host(priv->dev, (char *)&header, rx_packet_loc, 24);
1081 frame_ctl = le16_to_cpu(header.frame_control);
1082 seq_control = le16_to_cpu(header.seq_ctrl);
1083
1084 /* probe for CRC use here if needed once five packets have
1085 arrived with the same crc status, we assume we know what's
1086 happening and stop probing */
1087 if (priv->probe_crc) {
1088 if (!priv->wep_is_on || !(frame_ctl & IEEE80211_FCTL_PROTECTED)) {
1089 priv->do_rx_crc = probe_crc(priv, rx_packet_loc, msdu_size);
1090 } else {
1091 priv->do_rx_crc = probe_crc(priv, rx_packet_loc + 24, msdu_size - 24);
1092 }
1093 if (priv->do_rx_crc) {
1094 if (priv->crc_ok_cnt++ > 5)
1095 priv->probe_crc = 0;
1096 } else {
1097 if (priv->crc_ko_cnt++ > 5)
1098 priv->probe_crc = 0;
1099 }
1100 }
1101
1102 /* don't CRC header when WEP in use */
1103 if (priv->do_rx_crc && (!priv->wep_is_on || !(frame_ctl & IEEE80211_FCTL_PROTECTED))) {
1104 crc = crc32_le(0xffffffff, (unsigned char *)&header, 24);
1105 }
1106 msdu_size -= 24; /* header */
1107
1108 if ((frame_ctl & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_DATA) {
1109 int more_fragments = frame_ctl & IEEE80211_FCTL_MOREFRAGS;
1110 u8 packet_fragment_no = seq_control & IEEE80211_SCTL_FRAG;
1111 u16 packet_sequence_no = (seq_control & IEEE80211_SCTL_SEQ) >> 4;
1112
1113 if (!more_fragments && packet_fragment_no == 0) {
1114 fast_rx_path(priv, &header, msdu_size, rx_packet_loc, crc);
1115 } else {
1116 frag_rx_path(priv, &header, msdu_size, rx_packet_loc, crc,
1117 packet_sequence_no, packet_fragment_no, more_fragments);
1118 }
1119 }
1120
1121 if ((frame_ctl & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_MGMT) {
1122 /* copy rest of packet into buffer */
1123 atmel_copy_to_host(priv->dev, (unsigned char *)&priv->rx_buf, rx_packet_loc + 24, msdu_size);
1124
1125 /* we use the same buffer for frag reassembly and control packets */
1126 eth_broadcast_addr(priv->frag_source);
1127
1128 if (priv->do_rx_crc) {
1129 /* last 4 octets is crc */
1130 msdu_size -= 4;
1131 crc = crc32_le(crc, (unsigned char *)&priv->rx_buf, msdu_size);
1132 if ((crc ^ 0xffffffff) != (*((u32 *)&priv->rx_buf[msdu_size]))) {
1133 priv->dev->stats.rx_crc_errors++;
1134 goto next;
1135 }
1136 }
1137
1138 atmel_management_frame(priv, &header, msdu_size,
1139 atmel_rmem8(priv, atmel_rx(priv, RX_DESC_RSSI_OFFSET, priv->rx_desc_head)));
1140 }
1141
1142next:
1143 /* release descriptor */
1144 atmel_wmem8(priv, atmel_rx(priv, RX_DESC_FLAGS_OFFSET, priv->rx_desc_head), RX_DESC_FLAG_CONSUMED);
1145
1146 if (priv->rx_desc_head < (priv->host_info.rx_desc_count - 1))
1147 priv->rx_desc_head++;
1148 else
1149 priv->rx_desc_head = 0;
1150 }
1151}
1152
1153static irqreturn_t service_interrupt(int irq, void *dev_id)
1154{
1155 struct net_device *dev = (struct net_device *) dev_id;
1156 struct atmel_private *priv = netdev_priv(dev);
1157 u8 isr;
1158 int i = -1;
1159 static const u8 irq_order[] = {
1160 ISR_OUT_OF_RANGE,
1161 ISR_RxCOMPLETE,
1162 ISR_TxCOMPLETE,
1163 ISR_RxFRAMELOST,
1164 ISR_FATAL_ERROR,
1165 ISR_COMMAND_COMPLETE,
1166 ISR_IBSS_MERGE,
1167 ISR_GENERIC_IRQ
1168 };
1169
1170 if (priv->card && priv->present_callback &&
1171 !(*priv->present_callback)(priv->card))
1172 return IRQ_HANDLED;
1173
1174 /* In this state upper-level code assumes it can mess with
1175 the card unhampered by interrupts which may change register state.
1176 Note that even though the card shouldn't generate interrupts
1177 the inturrupt line may be shared. This allows card setup
1178 to go on without disabling interrupts for a long time. */
1179 if (priv->station_state == STATION_STATE_DOWN)
1180 return IRQ_NONE;
1181
1182 atmel_clear_gcr(dev, GCR_ENINT); /* disable interrupts */
1183
1184 while (1) {
1185 if (!atmel_lock_mac(priv)) {
1186 /* failed to contact card */
1187 printk(KERN_ALERT "%s: failed to contact MAC.\n", dev->name);
1188 return IRQ_HANDLED;
1189 }
1190
1191 isr = atmel_rmem8(priv, atmel_hi(priv, IFACE_INT_STATUS_OFFSET));
1192 atmel_wmem8(priv, atmel_hi(priv, IFACE_LOCKOUT_MAC_OFFSET), 0);
1193
1194 if (!isr) {
1195 atmel_set_gcr(dev, GCR_ENINT); /* enable interrupts */
1196 return i == -1 ? IRQ_NONE : IRQ_HANDLED;
1197 }
1198
1199 atmel_set_gcr(dev, GCR_ACKINT); /* acknowledge interrupt */
1200
1201 for (i = 0; i < ARRAY_SIZE(irq_order); i++)
1202 if (isr & irq_order[i])
1203 break;
1204
1205 if (!atmel_lock_mac(priv)) {
1206 /* failed to contact card */
1207 printk(KERN_ALERT "%s: failed to contact MAC.\n", dev->name);
1208 return IRQ_HANDLED;
1209 }
1210
1211 isr = atmel_rmem8(priv, atmel_hi(priv, IFACE_INT_STATUS_OFFSET));
1212 isr ^= irq_order[i];
1213 atmel_wmem8(priv, atmel_hi(priv, IFACE_INT_STATUS_OFFSET), isr);
1214 atmel_wmem8(priv, atmel_hi(priv, IFACE_LOCKOUT_MAC_OFFSET), 0);
1215
1216 switch (irq_order[i]) {
1217
1218 case ISR_OUT_OF_RANGE:
1219 if (priv->operating_mode == IW_MODE_INFRA &&
1220 priv->station_state == STATION_STATE_READY) {
1221 priv->station_is_associated = 0;
1222 atmel_scan(priv, 1);
1223 }
1224 break;
1225
1226 case ISR_RxFRAMELOST:
1227 priv->wstats.discard.misc++;
1228 fallthrough;
1229 case ISR_RxCOMPLETE:
1230 rx_done_irq(priv);
1231 break;
1232
1233 case ISR_TxCOMPLETE:
1234 tx_done_irq(priv);
1235 break;
1236
1237 case ISR_FATAL_ERROR:
1238 printk(KERN_ALERT "%s: *** FATAL error interrupt ***\n", dev->name);
1239 atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
1240 break;
1241
1242 case ISR_COMMAND_COMPLETE:
1243 atmel_command_irq(priv);
1244 break;
1245
1246 case ISR_IBSS_MERGE:
1247 atmel_get_mib(priv, Mac_Mgmt_Mib_Type, MAC_MGMT_MIB_CUR_BSSID_POS,
1248 priv->CurrentBSSID, 6);
1249 /* The WPA stuff cares about the current AP address */
1250 if (priv->use_wpa)
1251 build_wpa_mib(priv);
1252 break;
1253 case ISR_GENERIC_IRQ:
1254 printk(KERN_INFO "%s: Generic_irq received.\n", dev->name);
1255 break;
1256 }
1257 }
1258}
1259
1260static struct iw_statistics *atmel_get_wireless_stats(struct net_device *dev)
1261{
1262 struct atmel_private *priv = netdev_priv(dev);
1263
1264 /* update the link quality here in case we are seeing no beacons
1265 at all to drive the process */
1266 atmel_smooth_qual(priv);
1267
1268 priv->wstats.status = priv->station_state;
1269
1270 if (priv->operating_mode == IW_MODE_INFRA) {
1271 if (priv->station_state != STATION_STATE_READY) {
1272 priv->wstats.qual.qual = 0;
1273 priv->wstats.qual.level = 0;
1274 priv->wstats.qual.updated = (IW_QUAL_QUAL_INVALID
1275 | IW_QUAL_LEVEL_INVALID);
1276 }
1277 priv->wstats.qual.noise = 0;
1278 priv->wstats.qual.updated |= IW_QUAL_NOISE_INVALID;
1279 } else {
1280 /* Quality levels cannot be determined in ad-hoc mode,
1281 because we can 'hear' more that one remote station. */
1282 priv->wstats.qual.qual = 0;
1283 priv->wstats.qual.level = 0;
1284 priv->wstats.qual.noise = 0;
1285 priv->wstats.qual.updated = IW_QUAL_QUAL_INVALID
1286 | IW_QUAL_LEVEL_INVALID
1287 | IW_QUAL_NOISE_INVALID;
1288 priv->wstats.miss.beacon = 0;
1289 }
1290
1291 return &priv->wstats;
1292}
1293
1294static int atmel_set_mac_address(struct net_device *dev, void *p)
1295{
1296 struct sockaddr *addr = p;
1297
1298 eth_hw_addr_set(dev, addr->sa_data);
1299 return atmel_open(dev);
1300}
1301
1302EXPORT_SYMBOL(atmel_open);
1303
1304int atmel_open(struct net_device *dev)
1305{
1306 struct atmel_private *priv = netdev_priv(dev);
1307 int i, channel, err;
1308
1309 /* any scheduled timer is no longer needed and might screw things up.. */
1310 del_timer_sync(&priv->management_timer);
1311
1312 /* Interrupts will not touch the card once in this state... */
1313 priv->station_state = STATION_STATE_DOWN;
1314
1315 if (priv->new_SSID_size) {
1316 memcpy(priv->SSID, priv->new_SSID, priv->new_SSID_size);
1317 priv->SSID_size = priv->new_SSID_size;
1318 priv->new_SSID_size = 0;
1319 }
1320 priv->BSS_list_entries = 0;
1321
1322 priv->AuthenticationRequestRetryCnt = 0;
1323 priv->AssociationRequestRetryCnt = 0;
1324 priv->ReAssociationRequestRetryCnt = 0;
1325 priv->CurrentAuthentTransactionSeqNum = 0x0001;
1326 priv->ExpectedAuthentTransactionSeqNum = 0x0002;
1327
1328 priv->site_survey_state = SITE_SURVEY_IDLE;
1329 priv->station_is_associated = 0;
1330
1331 err = reset_atmel_card(dev);
1332 if (err)
1333 return err;
1334
1335 if (priv->config_reg_domain) {
1336 priv->reg_domain = priv->config_reg_domain;
1337 atmel_set_mib8(priv, Phy_Mib_Type, PHY_MIB_REG_DOMAIN_POS, priv->reg_domain);
1338 } else {
1339 priv->reg_domain = atmel_get_mib8(priv, Phy_Mib_Type, PHY_MIB_REG_DOMAIN_POS);
1340 for (i = 0; i < ARRAY_SIZE(channel_table); i++)
1341 if (priv->reg_domain == channel_table[i].reg_domain)
1342 break;
1343 if (i == ARRAY_SIZE(channel_table)) {
1344 priv->reg_domain = REG_DOMAIN_MKK1;
1345 printk(KERN_ALERT "%s: failed to get regulatory domain: assuming MKK1.\n", dev->name);
1346 }
1347 }
1348
1349 if ((channel = atmel_validate_channel(priv, priv->channel)))
1350 priv->channel = channel;
1351
1352 /* this moves station_state on.... */
1353 atmel_scan(priv, 1);
1354
1355 atmel_set_gcr(priv->dev, GCR_ENINT); /* enable interrupts */
1356 return 0;
1357}
1358
1359static int atmel_close(struct net_device *dev)
1360{
1361 struct atmel_private *priv = netdev_priv(dev);
1362
1363 /* Send event to userspace that we are disassociating */
1364 if (priv->station_state == STATION_STATE_READY) {
1365 union iwreq_data wrqu;
1366
1367 wrqu.data.length = 0;
1368 wrqu.data.flags = 0;
1369 wrqu.ap_addr.sa_family = ARPHRD_ETHER;
1370 eth_zero_addr(wrqu.ap_addr.sa_data);
1371 wireless_send_event(priv->dev, SIOCGIWAP, &wrqu, NULL);
1372 }
1373
1374 atmel_enter_state(priv, STATION_STATE_DOWN);
1375
1376 if (priv->bus_type == BUS_TYPE_PCCARD)
1377 atmel_write16(dev, GCR, 0x0060);
1378 atmel_write16(dev, GCR, 0x0040);
1379 return 0;
1380}
1381
1382static int atmel_validate_channel(struct atmel_private *priv, int channel)
1383{
1384 /* check that channel is OK, if so return zero,
1385 else return suitable default channel */
1386 int i;
1387
1388 for (i = 0; i < ARRAY_SIZE(channel_table); i++)
1389 if (priv->reg_domain == channel_table[i].reg_domain) {
1390 if (channel >= channel_table[i].min &&
1391 channel <= channel_table[i].max)
1392 return 0;
1393 else
1394 return channel_table[i].min;
1395 }
1396 return 0;
1397}
1398
1399#ifdef CONFIG_PROC_FS
1400static int atmel_proc_show(struct seq_file *m, void *v)
1401{
1402 struct atmel_private *priv = m->private;
1403 int i;
1404 char *s, *r, *c;
1405
1406 seq_printf(m, "Driver version:\t\t%d.%d\n", DRIVER_MAJOR, DRIVER_MINOR);
1407
1408 if (priv->station_state != STATION_STATE_DOWN) {
1409 seq_printf(m,
1410 "Firmware version:\t%d.%d build %d\n"
1411 "Firmware location:\t",
1412 priv->host_info.major_version,
1413 priv->host_info.minor_version,
1414 priv->host_info.build_version);
1415
1416 if (priv->card_type != CARD_TYPE_EEPROM)
1417 seq_puts(m, "on card\n");
1418 else if (priv->firmware)
1419 seq_printf(m, "%s loaded by host\n", priv->firmware_id);
1420 else
1421 seq_printf(m, "%s loaded by hotplug\n", priv->firmware_id);
1422
1423 switch (priv->card_type) {
1424 case CARD_TYPE_PARALLEL_FLASH:
1425 c = "Parallel flash";
1426 break;
1427 case CARD_TYPE_SPI_FLASH:
1428 c = "SPI flash\n";
1429 break;
1430 case CARD_TYPE_EEPROM:
1431 c = "EEPROM";
1432 break;
1433 default:
1434 c = "<unknown>";
1435 }
1436
1437 r = "<unknown>";
1438 for (i = 0; i < ARRAY_SIZE(channel_table); i++)
1439 if (priv->reg_domain == channel_table[i].reg_domain)
1440 r = channel_table[i].name;
1441
1442 seq_printf(m, "MAC memory type:\t%s\n", c);
1443 seq_printf(m, "Regulatory domain:\t%s\n", r);
1444 seq_printf(m, "Host CRC checking:\t%s\n",
1445 priv->do_rx_crc ? "On" : "Off");
1446 seq_printf(m, "WPA-capable firmware:\t%s\n",
1447 priv->use_wpa ? "Yes" : "No");
1448 }
1449
1450 switch (priv->station_state) {
1451 case STATION_STATE_SCANNING:
1452 s = "Scanning";
1453 break;
1454 case STATION_STATE_JOINNING:
1455 s = "Joining";
1456 break;
1457 case STATION_STATE_AUTHENTICATING:
1458 s = "Authenticating";
1459 break;
1460 case STATION_STATE_ASSOCIATING:
1461 s = "Associating";
1462 break;
1463 case STATION_STATE_READY:
1464 s = "Ready";
1465 break;
1466 case STATION_STATE_REASSOCIATING:
1467 s = "Reassociating";
1468 break;
1469 case STATION_STATE_MGMT_ERROR:
1470 s = "Management error";
1471 break;
1472 case STATION_STATE_DOWN:
1473 s = "Down";
1474 break;
1475 default:
1476 s = "<unknown>";
1477 }
1478
1479 seq_printf(m, "Current state:\t\t%s\n", s);
1480 return 0;
1481}
1482#endif
1483
1484static const struct net_device_ops atmel_netdev_ops = {
1485 .ndo_open = atmel_open,
1486 .ndo_stop = atmel_close,
1487 .ndo_set_mac_address = atmel_set_mac_address,
1488 .ndo_start_xmit = start_tx,
1489 .ndo_validate_addr = eth_validate_addr,
1490};
1491
1492struct net_device *init_atmel_card(unsigned short irq, unsigned long port,
1493 const AtmelFWType fw_type,
1494 struct device *sys_dev,
1495 int (*card_present)(void *), void *card)
1496{
1497 struct net_device *dev;
1498 struct atmel_private *priv;
1499 int rc;
1500
1501 /* Create the network device object. */
1502 dev = alloc_etherdev(sizeof(*priv));
1503 if (!dev)
1504 return NULL;
1505
1506 if (dev_alloc_name(dev, dev->name) < 0) {
1507 printk(KERN_ERR "atmel: Couldn't get name!\n");
1508 goto err_out_free;
1509 }
1510
1511 priv = netdev_priv(dev);
1512 priv->dev = dev;
1513 priv->sys_dev = sys_dev;
1514 priv->present_callback = card_present;
1515 priv->card = card;
1516 priv->firmware = NULL;
1517 priv->firmware_type = fw_type;
1518 if (firmware) /* module parameter */
1519 strscpy(priv->firmware_id, firmware, sizeof(priv->firmware_id));
1520 priv->bus_type = card_present ? BUS_TYPE_PCCARD : BUS_TYPE_PCI;
1521 priv->station_state = STATION_STATE_DOWN;
1522 priv->do_rx_crc = 0;
1523 /* For PCMCIA cards, some chips need CRC, some don't
1524 so we have to probe. */
1525 if (priv->bus_type == BUS_TYPE_PCCARD) {
1526 priv->probe_crc = 1;
1527 priv->crc_ok_cnt = priv->crc_ko_cnt = 0;
1528 } else
1529 priv->probe_crc = 0;
1530 priv->last_qual = jiffies;
1531 priv->last_beacon_timestamp = 0;
1532 memset(priv->frag_source, 0xff, sizeof(priv->frag_source));
1533 eth_zero_addr(priv->BSSID);
1534 priv->CurrentBSSID[0] = 0xFF; /* Initialize to something invalid.... */
1535 priv->station_was_associated = 0;
1536
1537 priv->last_survey = jiffies;
1538 priv->preamble = LONG_PREAMBLE;
1539 priv->operating_mode = IW_MODE_INFRA;
1540 priv->connect_to_any_BSS = 0;
1541 priv->config_reg_domain = 0;
1542 priv->reg_domain = 0;
1543 priv->tx_rate = 3;
1544 priv->auto_tx_rate = 1;
1545 priv->channel = 4;
1546 priv->power_mode = 0;
1547 priv->SSID[0] = '\0';
1548 priv->SSID_size = 0;
1549 priv->new_SSID_size = 0;
1550 priv->frag_threshold = 2346;
1551 priv->rts_threshold = 2347;
1552 priv->short_retry = 7;
1553 priv->long_retry = 4;
1554
1555 priv->wep_is_on = 0;
1556 priv->default_key = 0;
1557 priv->encryption_level = 0;
1558 priv->exclude_unencrypted = 0;
1559 priv->group_cipher_suite = priv->pairwise_cipher_suite = CIPHER_SUITE_NONE;
1560 priv->use_wpa = 0;
1561 memset(priv->wep_keys, 0, sizeof(priv->wep_keys));
1562 memset(priv->wep_key_len, 0, sizeof(priv->wep_key_len));
1563
1564 priv->default_beacon_period = priv->beacon_period = 100;
1565 priv->listen_interval = 1;
1566
1567 timer_setup(&priv->management_timer, atmel_management_timer, 0);
1568 spin_lock_init(&priv->irqlock);
1569 spin_lock_init(&priv->timerlock);
1570
1571 dev->netdev_ops = &atmel_netdev_ops;
1572 dev->wireless_handlers = &atmel_handler_def;
1573 dev->irq = irq;
1574 dev->base_addr = port;
1575
1576 /* MTU range: 68 - 2312 */
1577 dev->min_mtu = 68;
1578 dev->max_mtu = MAX_WIRELESS_BODY - ETH_FCS_LEN;
1579
1580 SET_NETDEV_DEV(dev, sys_dev);
1581
1582 if ((rc = request_irq(dev->irq, service_interrupt, IRQF_SHARED, dev->name, dev))) {
1583 printk(KERN_ERR "%s: register interrupt %d failed, rc %d\n", dev->name, irq, rc);
1584 goto err_out_free;
1585 }
1586
1587 if (!request_region(dev->base_addr, 32,
1588 priv->bus_type == BUS_TYPE_PCCARD ? "atmel_cs" : "atmel_pci")) {
1589 goto err_out_irq;
1590 }
1591
1592 if (register_netdev(dev))
1593 goto err_out_res;
1594
1595 if (!probe_atmel_card(dev)) {
1596 unregister_netdev(dev);
1597 goto err_out_res;
1598 }
1599
1600 netif_carrier_off(dev);
1601
1602 if (!proc_create_single_data("driver/atmel", 0, NULL, atmel_proc_show,
1603 priv))
1604 printk(KERN_WARNING "atmel: unable to create /proc entry.\n");
1605
1606 printk(KERN_INFO "%s: Atmel at76c50x. Version %d.%d. MAC %pM\n",
1607 dev->name, DRIVER_MAJOR, DRIVER_MINOR, dev->dev_addr);
1608
1609 return dev;
1610
1611err_out_res:
1612 release_region(dev->base_addr, 32);
1613err_out_irq:
1614 free_irq(dev->irq, dev);
1615err_out_free:
1616 free_netdev(dev);
1617 return NULL;
1618}
1619
1620EXPORT_SYMBOL(init_atmel_card);
1621
1622void stop_atmel_card(struct net_device *dev)
1623{
1624 struct atmel_private *priv = netdev_priv(dev);
1625
1626 /* put a brick on it... */
1627 if (priv->bus_type == BUS_TYPE_PCCARD)
1628 atmel_write16(dev, GCR, 0x0060);
1629 atmel_write16(dev, GCR, 0x0040);
1630
1631 del_timer_sync(&priv->management_timer);
1632 unregister_netdev(dev);
1633 remove_proc_entry("driver/atmel", NULL);
1634 free_irq(dev->irq, dev);
1635 kfree(priv->firmware);
1636 release_region(dev->base_addr, 32);
1637 free_netdev(dev);
1638}
1639
1640EXPORT_SYMBOL(stop_atmel_card);
1641
1642static int atmel_set_essid(struct net_device *dev,
1643 struct iw_request_info *info,
1644 union iwreq_data *wrqu,
1645 char *extra)
1646{
1647 struct iw_point *dwrq = &wrqu->essid;
1648 struct atmel_private *priv = netdev_priv(dev);
1649
1650 /* Check if we asked for `any' */
1651 if (dwrq->flags == 0) {
1652 priv->connect_to_any_BSS = 1;
1653 } else {
1654 int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
1655
1656 priv->connect_to_any_BSS = 0;
1657
1658 /* Check the size of the string */
1659 if (dwrq->length > MAX_SSID_LENGTH)
1660 return -E2BIG;
1661 if (index != 0)
1662 return -EINVAL;
1663
1664 memcpy(priv->new_SSID, extra, dwrq->length);
1665 priv->new_SSID_size = dwrq->length;
1666 }
1667
1668 return -EINPROGRESS;
1669}
1670
1671static int atmel_get_essid(struct net_device *dev,
1672 struct iw_request_info *info,
1673 union iwreq_data *wrqu,
1674 char *extra)
1675{
1676 struct iw_point *dwrq = &wrqu->essid;
1677 struct atmel_private *priv = netdev_priv(dev);
1678
1679 /* Get the current SSID */
1680 if (priv->new_SSID_size != 0) {
1681 memcpy(extra, priv->new_SSID, priv->new_SSID_size);
1682 dwrq->length = priv->new_SSID_size;
1683 } else {
1684 memcpy(extra, priv->SSID, priv->SSID_size);
1685 dwrq->length = priv->SSID_size;
1686 }
1687
1688 dwrq->flags = !priv->connect_to_any_BSS; /* active */
1689
1690 return 0;
1691}
1692
1693static int atmel_get_wap(struct net_device *dev,
1694 struct iw_request_info *info,
1695 union iwreq_data *wrqu,
1696 char *extra)
1697{
1698 struct sockaddr *awrq = &wrqu->ap_addr;
1699 struct atmel_private *priv = netdev_priv(dev);
1700 memcpy(awrq->sa_data, priv->CurrentBSSID, ETH_ALEN);
1701 awrq->sa_family = ARPHRD_ETHER;
1702
1703 return 0;
1704}
1705
1706static int atmel_set_encode(struct net_device *dev,
1707 struct iw_request_info *info,
1708 union iwreq_data *wrqu,
1709 char *extra)
1710{
1711 struct iw_point *dwrq = &wrqu->encoding;
1712 struct atmel_private *priv = netdev_priv(dev);
1713
1714 /* Basic checking: do we have a key to set ?
1715 * Note : with the new API, it's impossible to get a NULL pointer.
1716 * Therefore, we need to check a key size == 0 instead.
1717 * New version of iwconfig properly set the IW_ENCODE_NOKEY flag
1718 * when no key is present (only change flags), but older versions
1719 * don't do it. - Jean II */
1720 if (dwrq->length > 0) {
1721 int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
1722 int current_index = priv->default_key;
1723 /* Check the size of the key */
1724 if (dwrq->length > 13) {
1725 return -EINVAL;
1726 }
1727 /* Check the index (none -> use current) */
1728 if (index < 0 || index >= 4)
1729 index = current_index;
1730 else
1731 priv->default_key = index;
1732 /* Set the length */
1733 if (dwrq->length > 5)
1734 priv->wep_key_len[index] = 13;
1735 else
1736 if (dwrq->length > 0)
1737 priv->wep_key_len[index] = 5;
1738 else
1739 /* Disable the key */
1740 priv->wep_key_len[index] = 0;
1741 /* Check if the key is not marked as invalid */
1742 if (!(dwrq->flags & IW_ENCODE_NOKEY)) {
1743 /* Cleanup */
1744 memset(priv->wep_keys[index], 0, 13);
1745 /* Copy the key in the driver */
1746 memcpy(priv->wep_keys[index], extra, dwrq->length);
1747 }
1748 /* WE specify that if a valid key is set, encryption
1749 * should be enabled (user may turn it off later)
1750 * This is also how "iwconfig ethX key on" works */
1751 if (index == current_index &&
1752 priv->wep_key_len[index] > 0) {
1753 priv->wep_is_on = 1;
1754 priv->exclude_unencrypted = 1;
1755 if (priv->wep_key_len[index] > 5) {
1756 priv->pairwise_cipher_suite = CIPHER_SUITE_WEP_128;
1757 priv->encryption_level = 2;
1758 } else {
1759 priv->pairwise_cipher_suite = CIPHER_SUITE_WEP_64;
1760 priv->encryption_level = 1;
1761 }
1762 }
1763 } else {
1764 /* Do we want to just set the transmit key index ? */
1765 int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
1766 if (index >= 0 && index < 4) {
1767 priv->default_key = index;
1768 } else
1769 /* Don't complain if only change the mode */
1770 if (!(dwrq->flags & IW_ENCODE_MODE))
1771 return -EINVAL;
1772 }
1773 /* Read the flags */
1774 if (dwrq->flags & IW_ENCODE_DISABLED) {
1775 priv->wep_is_on = 0;
1776 priv->encryption_level = 0;
1777 priv->pairwise_cipher_suite = CIPHER_SUITE_NONE;
1778 } else {
1779 priv->wep_is_on = 1;
1780 if (priv->wep_key_len[priv->default_key] > 5) {
1781 priv->pairwise_cipher_suite = CIPHER_SUITE_WEP_128;
1782 priv->encryption_level = 2;
1783 } else {
1784 priv->pairwise_cipher_suite = CIPHER_SUITE_WEP_64;
1785 priv->encryption_level = 1;
1786 }
1787 }
1788 if (dwrq->flags & IW_ENCODE_RESTRICTED)
1789 priv->exclude_unencrypted = 1;
1790 if (dwrq->flags & IW_ENCODE_OPEN)
1791 priv->exclude_unencrypted = 0;
1792
1793 return -EINPROGRESS; /* Call commit handler */
1794}
1795
1796static int atmel_get_encode(struct net_device *dev,
1797 struct iw_request_info *info,
1798 union iwreq_data *wrqu,
1799 char *extra)
1800{
1801 struct iw_point *dwrq = &wrqu->encoding;
1802 struct atmel_private *priv = netdev_priv(dev);
1803 int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
1804
1805 if (!priv->wep_is_on)
1806 dwrq->flags = IW_ENCODE_DISABLED;
1807 else {
1808 if (priv->exclude_unencrypted)
1809 dwrq->flags = IW_ENCODE_RESTRICTED;
1810 else
1811 dwrq->flags = IW_ENCODE_OPEN;
1812 }
1813 /* Which key do we want ? -1 -> tx index */
1814 if (index < 0 || index >= 4)
1815 index = priv->default_key;
1816 dwrq->flags |= index + 1;
1817 /* Copy the key to the user buffer */
1818 dwrq->length = priv->wep_key_len[index];
1819 if (dwrq->length > 16) {
1820 dwrq->length = 0;
1821 } else {
1822 memset(extra, 0, 16);
1823 memcpy(extra, priv->wep_keys[index], dwrq->length);
1824 }
1825
1826 return 0;
1827}
1828
1829static int atmel_set_encodeext(struct net_device *dev,
1830 struct iw_request_info *info,
1831 union iwreq_data *wrqu,
1832 char *extra)
1833{
1834 struct atmel_private *priv = netdev_priv(dev);
1835 struct iw_point *encoding = &wrqu->encoding;
1836 struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
1837 int idx, key_len, alg = ext->alg, set_key = 1;
1838
1839 /* Determine and validate the key index */
1840 idx = encoding->flags & IW_ENCODE_INDEX;
1841 if (idx) {
1842 if (idx < 1 || idx > 4)
1843 return -EINVAL;
1844 idx--;
1845 } else
1846 idx = priv->default_key;
1847
1848 if (encoding->flags & IW_ENCODE_DISABLED)
1849 alg = IW_ENCODE_ALG_NONE;
1850
1851 if (ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY) {
1852 priv->default_key = idx;
1853 set_key = ext->key_len > 0 ? 1 : 0;
1854 }
1855
1856 if (set_key) {
1857 /* Set the requested key first */
1858 switch (alg) {
1859 case IW_ENCODE_ALG_NONE:
1860 priv->wep_is_on = 0;
1861 priv->encryption_level = 0;
1862 priv->pairwise_cipher_suite = CIPHER_SUITE_NONE;
1863 break;
1864 case IW_ENCODE_ALG_WEP:
1865 if (ext->key_len > 5) {
1866 priv->wep_key_len[idx] = 13;
1867 priv->pairwise_cipher_suite = CIPHER_SUITE_WEP_128;
1868 priv->encryption_level = 2;
1869 } else if (ext->key_len > 0) {
1870 priv->wep_key_len[idx] = 5;
1871 priv->pairwise_cipher_suite = CIPHER_SUITE_WEP_64;
1872 priv->encryption_level = 1;
1873 } else {
1874 return -EINVAL;
1875 }
1876 priv->wep_is_on = 1;
1877 memset(priv->wep_keys[idx], 0, 13);
1878 key_len = min ((int)ext->key_len, priv->wep_key_len[idx]);
1879 memcpy(priv->wep_keys[idx], ext->key, key_len);
1880 break;
1881 default:
1882 return -EINVAL;
1883 }
1884 }
1885
1886 return -EINPROGRESS;
1887}
1888
1889static int atmel_get_encodeext(struct net_device *dev,
1890 struct iw_request_info *info,
1891 union iwreq_data *wrqu,
1892 char *extra)
1893{
1894 struct atmel_private *priv = netdev_priv(dev);
1895 struct iw_point *encoding = &wrqu->encoding;
1896 struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
1897 int idx, max_key_len;
1898
1899 max_key_len = encoding->length - sizeof(*ext);
1900 if (max_key_len < 0)
1901 return -EINVAL;
1902
1903 idx = encoding->flags & IW_ENCODE_INDEX;
1904 if (idx) {
1905 if (idx < 1 || idx > 4)
1906 return -EINVAL;
1907 idx--;
1908 } else
1909 idx = priv->default_key;
1910
1911 encoding->flags = idx + 1;
1912 memset(ext, 0, sizeof(*ext));
1913
1914 if (!priv->wep_is_on) {
1915 ext->alg = IW_ENCODE_ALG_NONE;
1916 ext->key_len = 0;
1917 encoding->flags |= IW_ENCODE_DISABLED;
1918 } else {
1919 if (priv->encryption_level > 0)
1920 ext->alg = IW_ENCODE_ALG_WEP;
1921 else
1922 return -EINVAL;
1923
1924 ext->key_len = priv->wep_key_len[idx];
1925 memcpy(ext->key, priv->wep_keys[idx], ext->key_len);
1926 encoding->flags |= IW_ENCODE_ENABLED;
1927 }
1928
1929 return 0;
1930}
1931
1932static int atmel_set_auth(struct net_device *dev,
1933 struct iw_request_info *info,
1934 union iwreq_data *wrqu, char *extra)
1935{
1936 struct atmel_private *priv = netdev_priv(dev);
1937 struct iw_param *param = &wrqu->param;
1938
1939 switch (param->flags & IW_AUTH_INDEX) {
1940 case IW_AUTH_WPA_VERSION:
1941 case IW_AUTH_CIPHER_PAIRWISE:
1942 case IW_AUTH_CIPHER_GROUP:
1943 case IW_AUTH_KEY_MGMT:
1944 case IW_AUTH_RX_UNENCRYPTED_EAPOL:
1945 case IW_AUTH_PRIVACY_INVOKED:
1946 /*
1947 * atmel does not use these parameters
1948 */
1949 break;
1950
1951 case IW_AUTH_DROP_UNENCRYPTED:
1952 priv->exclude_unencrypted = param->value ? 1 : 0;
1953 break;
1954
1955 case IW_AUTH_80211_AUTH_ALG: {
1956 if (param->value & IW_AUTH_ALG_SHARED_KEY) {
1957 priv->exclude_unencrypted = 1;
1958 } else if (param->value & IW_AUTH_ALG_OPEN_SYSTEM) {
1959 priv->exclude_unencrypted = 0;
1960 } else
1961 return -EINVAL;
1962 break;
1963 }
1964
1965 case IW_AUTH_WPA_ENABLED:
1966 /* Silently accept disable of WPA */
1967 if (param->value > 0)
1968 return -EOPNOTSUPP;
1969 break;
1970
1971 default:
1972 return -EOPNOTSUPP;
1973 }
1974 return -EINPROGRESS;
1975}
1976
1977static int atmel_get_auth(struct net_device *dev,
1978 struct iw_request_info *info,
1979 union iwreq_data *wrqu, char *extra)
1980{
1981 struct atmel_private *priv = netdev_priv(dev);
1982 struct iw_param *param = &wrqu->param;
1983
1984 switch (param->flags & IW_AUTH_INDEX) {
1985 case IW_AUTH_DROP_UNENCRYPTED:
1986 param->value = priv->exclude_unencrypted;
1987 break;
1988
1989 case IW_AUTH_80211_AUTH_ALG:
1990 if (priv->exclude_unencrypted == 1)
1991 param->value = IW_AUTH_ALG_SHARED_KEY;
1992 else
1993 param->value = IW_AUTH_ALG_OPEN_SYSTEM;
1994 break;
1995
1996 case IW_AUTH_WPA_ENABLED:
1997 param->value = 0;
1998 break;
1999
2000 default:
2001 return -EOPNOTSUPP;
2002 }
2003 return 0;
2004}
2005
2006
2007static int atmel_get_name(struct net_device *dev,
2008 struct iw_request_info *info,
2009 union iwreq_data *wrqu,
2010 char *extra)
2011{
2012 strcpy(wrqu->name, "IEEE 802.11-DS");
2013 return 0;
2014}
2015
2016static int atmel_set_rate(struct net_device *dev,
2017 struct iw_request_info *info,
2018 union iwreq_data *wrqu,
2019 char *extra)
2020{
2021 struct iw_param *vwrq = &wrqu->bitrate;
2022 struct atmel_private *priv = netdev_priv(dev);
2023
2024 if (vwrq->fixed == 0) {
2025 priv->tx_rate = 3;
2026 priv->auto_tx_rate = 1;
2027 } else {
2028 priv->auto_tx_rate = 0;
2029
2030 /* Which type of value ? */
2031 if ((vwrq->value < 4) && (vwrq->value >= 0)) {
2032 /* Setting by rate index */
2033 priv->tx_rate = vwrq->value;
2034 } else {
2035 /* Setting by frequency value */
2036 switch (vwrq->value) {
2037 case 1000000:
2038 priv->tx_rate = 0;
2039 break;
2040 case 2000000:
2041 priv->tx_rate = 1;
2042 break;
2043 case 5500000:
2044 priv->tx_rate = 2;
2045 break;
2046 case 11000000:
2047 priv->tx_rate = 3;
2048 break;
2049 default:
2050 return -EINVAL;
2051 }
2052 }
2053 }
2054
2055 return -EINPROGRESS;
2056}
2057
2058static int atmel_set_mode(struct net_device *dev,
2059 struct iw_request_info *info,
2060 union iwreq_data *wrqu,
2061 char *extra)
2062{
2063 __u32 *uwrq = &wrqu->mode;
2064 struct atmel_private *priv = netdev_priv(dev);
2065
2066 if (*uwrq != IW_MODE_ADHOC && *uwrq != IW_MODE_INFRA)
2067 return -EINVAL;
2068
2069 priv->operating_mode = *uwrq;
2070 return -EINPROGRESS;
2071}
2072
2073static int atmel_get_mode(struct net_device *dev,
2074 struct iw_request_info *info,
2075 union iwreq_data *wrqu,
2076 char *extra)
2077{
2078 __u32 *uwrq = &wrqu->mode;
2079 struct atmel_private *priv = netdev_priv(dev);
2080
2081 *uwrq = priv->operating_mode;
2082 return 0;
2083}
2084
2085static int atmel_get_rate(struct net_device *dev,
2086 struct iw_request_info *info,
2087 union iwreq_data *wrqu,
2088 char *extra)
2089{
2090 struct iw_param *vwrq = &wrqu->bitrate;
2091 struct atmel_private *priv = netdev_priv(dev);
2092
2093 if (priv->auto_tx_rate) {
2094 vwrq->fixed = 0;
2095 vwrq->value = 11000000;
2096 } else {
2097 vwrq->fixed = 1;
2098 switch (priv->tx_rate) {
2099 case 0:
2100 vwrq->value = 1000000;
2101 break;
2102 case 1:
2103 vwrq->value = 2000000;
2104 break;
2105 case 2:
2106 vwrq->value = 5500000;
2107 break;
2108 case 3:
2109 vwrq->value = 11000000;
2110 break;
2111 }
2112 }
2113 return 0;
2114}
2115
2116static int atmel_set_power(struct net_device *dev,
2117 struct iw_request_info *info,
2118 union iwreq_data *wrqu,
2119 char *extra)
2120{
2121 struct iw_param *vwrq = &wrqu->power;
2122 struct atmel_private *priv = netdev_priv(dev);
2123 priv->power_mode = vwrq->disabled ? 0 : 1;
2124 return -EINPROGRESS;
2125}
2126
2127static int atmel_get_power(struct net_device *dev,
2128 struct iw_request_info *info,
2129 union iwreq_data *wrqu,
2130 char *extra)
2131{
2132 struct iw_param *vwrq = &wrqu->power;
2133 struct atmel_private *priv = netdev_priv(dev);
2134 vwrq->disabled = priv->power_mode ? 0 : 1;
2135 vwrq->flags = IW_POWER_ON;
2136 return 0;
2137}
2138
2139static int atmel_set_retry(struct net_device *dev,
2140 struct iw_request_info *info,
2141 union iwreq_data *wrqu,
2142 char *extra)
2143{
2144 struct iw_param *vwrq = &wrqu->retry;
2145 struct atmel_private *priv = netdev_priv(dev);
2146
2147 if (!vwrq->disabled && (vwrq->flags & IW_RETRY_LIMIT)) {
2148 if (vwrq->flags & IW_RETRY_LONG)
2149 priv->long_retry = vwrq->value;
2150 else if (vwrq->flags & IW_RETRY_SHORT)
2151 priv->short_retry = vwrq->value;
2152 else {
2153 /* No modifier : set both */
2154 priv->long_retry = vwrq->value;
2155 priv->short_retry = vwrq->value;
2156 }
2157 return -EINPROGRESS;
2158 }
2159
2160 return -EINVAL;
2161}
2162
2163static int atmel_get_retry(struct net_device *dev,
2164 struct iw_request_info *info,
2165 union iwreq_data *wrqu,
2166 char *extra)
2167{
2168 struct iw_param *vwrq = &wrqu->retry;
2169 struct atmel_private *priv = netdev_priv(dev);
2170
2171 vwrq->disabled = 0; /* Can't be disabled */
2172
2173 /* Note : by default, display the short retry number */
2174 if (vwrq->flags & IW_RETRY_LONG) {
2175 vwrq->flags = IW_RETRY_LIMIT | IW_RETRY_LONG;
2176 vwrq->value = priv->long_retry;
2177 } else {
2178 vwrq->flags = IW_RETRY_LIMIT;
2179 vwrq->value = priv->short_retry;
2180 if (priv->long_retry != priv->short_retry)
2181 vwrq->flags |= IW_RETRY_SHORT;
2182 }
2183
2184 return 0;
2185}
2186
2187static int atmel_set_rts(struct net_device *dev,
2188 struct iw_request_info *info,
2189 union iwreq_data *wrqu,
2190 char *extra)
2191{
2192 struct iw_param *vwrq = &wrqu->rts;
2193 struct atmel_private *priv = netdev_priv(dev);
2194 int rthr = vwrq->value;
2195
2196 if (vwrq->disabled)
2197 rthr = 2347;
2198 if ((rthr < 0) || (rthr > 2347)) {
2199 return -EINVAL;
2200 }
2201 priv->rts_threshold = rthr;
2202
2203 return -EINPROGRESS; /* Call commit handler */
2204}
2205
2206static int atmel_get_rts(struct net_device *dev,
2207 struct iw_request_info *info,
2208 union iwreq_data *wrqu,
2209 char *extra)
2210{
2211 struct iw_param *vwrq = &wrqu->rts;
2212 struct atmel_private *priv = netdev_priv(dev);
2213
2214 vwrq->value = priv->rts_threshold;
2215 vwrq->disabled = (vwrq->value >= 2347);
2216 vwrq->fixed = 1;
2217
2218 return 0;
2219}
2220
2221static int atmel_set_frag(struct net_device *dev,
2222 struct iw_request_info *info,
2223 union iwreq_data *wrqu,
2224 char *extra)
2225{
2226 struct iw_param *vwrq = &wrqu->frag;
2227 struct atmel_private *priv = netdev_priv(dev);
2228 int fthr = vwrq->value;
2229
2230 if (vwrq->disabled)
2231 fthr = 2346;
2232 if ((fthr < 256) || (fthr > 2346)) {
2233 return -EINVAL;
2234 }
2235 fthr &= ~0x1; /* Get an even value - is it really needed ??? */
2236 priv->frag_threshold = fthr;
2237
2238 return -EINPROGRESS; /* Call commit handler */
2239}
2240
2241static int atmel_get_frag(struct net_device *dev,
2242 struct iw_request_info *info,
2243 union iwreq_data *wrqu,
2244 char *extra)
2245{
2246 struct iw_param *vwrq = &wrqu->frag;
2247 struct atmel_private *priv = netdev_priv(dev);
2248
2249 vwrq->value = priv->frag_threshold;
2250 vwrq->disabled = (vwrq->value >= 2346);
2251 vwrq->fixed = 1;
2252
2253 return 0;
2254}
2255
2256static int atmel_set_freq(struct net_device *dev,
2257 struct iw_request_info *info,
2258 union iwreq_data *wrqu,
2259 char *extra)
2260{
2261 struct iw_freq *fwrq = &wrqu->freq;
2262 struct atmel_private *priv = netdev_priv(dev);
2263 int rc = -EINPROGRESS; /* Call commit handler */
2264
2265 /* If setting by frequency, convert to a channel */
2266 if (fwrq->e == 1) {
2267 int f = fwrq->m / 100000;
2268
2269 /* Hack to fall through... */
2270 fwrq->e = 0;
2271 fwrq->m = ieee80211_frequency_to_channel(f);
2272 }
2273 /* Setting by channel number */
2274 if (fwrq->m < 0 || fwrq->m > 1000 || fwrq->e > 0)
2275 rc = -EOPNOTSUPP;
2276 else {
2277 int channel = fwrq->m;
2278 if (atmel_validate_channel(priv, channel) == 0) {
2279 priv->channel = channel;
2280 } else {
2281 rc = -EINVAL;
2282 }
2283 }
2284 return rc;
2285}
2286
2287static int atmel_get_freq(struct net_device *dev,
2288 struct iw_request_info *info,
2289 union iwreq_data *wrqu,
2290 char *extra)
2291{
2292 struct iw_freq *fwrq = &wrqu->freq;
2293 struct atmel_private *priv = netdev_priv(dev);
2294
2295 fwrq->m = priv->channel;
2296 fwrq->e = 0;
2297 return 0;
2298}
2299
2300static int atmel_set_scan(struct net_device *dev,
2301 struct iw_request_info *info,
2302 union iwreq_data *dwrq,
2303 char *extra)
2304{
2305 struct atmel_private *priv = netdev_priv(dev);
2306 unsigned long flags;
2307
2308 /* Note : you may have realised that, as this is a SET operation,
2309 * this is privileged and therefore a normal user can't
2310 * perform scanning.
2311 * This is not an error, while the device perform scanning,
2312 * traffic doesn't flow, so it's a perfect DoS...
2313 * Jean II */
2314
2315 if (priv->station_state == STATION_STATE_DOWN)
2316 return -EAGAIN;
2317
2318 /* Timeout old surveys. */
2319 if (time_after(jiffies, priv->last_survey + 20 * HZ))
2320 priv->site_survey_state = SITE_SURVEY_IDLE;
2321 priv->last_survey = jiffies;
2322
2323 /* Initiate a scan command */
2324 if (priv->site_survey_state == SITE_SURVEY_IN_PROGRESS)
2325 return -EBUSY;
2326
2327 del_timer_sync(&priv->management_timer);
2328 spin_lock_irqsave(&priv->irqlock, flags);
2329
2330 priv->site_survey_state = SITE_SURVEY_IN_PROGRESS;
2331 priv->fast_scan = 0;
2332 atmel_scan(priv, 0);
2333 spin_unlock_irqrestore(&priv->irqlock, flags);
2334
2335 return 0;
2336}
2337
2338static int atmel_get_scan(struct net_device *dev,
2339 struct iw_request_info *info,
2340 union iwreq_data *wrqu,
2341 char *extra)
2342{
2343 struct iw_point *dwrq = &wrqu->data;
2344 struct atmel_private *priv = netdev_priv(dev);
2345 int i;
2346 char *current_ev = extra;
2347 struct iw_event iwe;
2348
2349 if (priv->site_survey_state != SITE_SURVEY_COMPLETED)
2350 return -EAGAIN;
2351
2352 for (i = 0; i < priv->BSS_list_entries; i++) {
2353 iwe.cmd = SIOCGIWAP;
2354 iwe.u.ap_addr.sa_family = ARPHRD_ETHER;
2355 memcpy(iwe.u.ap_addr.sa_data, priv->BSSinfo[i].BSSID, ETH_ALEN);
2356 current_ev = iwe_stream_add_event(info, current_ev,
2357 extra + IW_SCAN_MAX_DATA,
2358 &iwe, IW_EV_ADDR_LEN);
2359
2360 iwe.u.data.length = priv->BSSinfo[i].SSIDsize;
2361 if (iwe.u.data.length > 32)
2362 iwe.u.data.length = 32;
2363 iwe.cmd = SIOCGIWESSID;
2364 iwe.u.data.flags = 1;
2365 current_ev = iwe_stream_add_point(info, current_ev,
2366 extra + IW_SCAN_MAX_DATA,
2367 &iwe, priv->BSSinfo[i].SSID);
2368
2369 iwe.cmd = SIOCGIWMODE;
2370 iwe.u.mode = priv->BSSinfo[i].BSStype;
2371 current_ev = iwe_stream_add_event(info, current_ev,
2372 extra + IW_SCAN_MAX_DATA,
2373 &iwe, IW_EV_UINT_LEN);
2374
2375 iwe.cmd = SIOCGIWFREQ;
2376 iwe.u.freq.m = priv->BSSinfo[i].channel;
2377 iwe.u.freq.e = 0;
2378 current_ev = iwe_stream_add_event(info, current_ev,
2379 extra + IW_SCAN_MAX_DATA,
2380 &iwe, IW_EV_FREQ_LEN);
2381
2382 /* Add quality statistics */
2383 iwe.cmd = IWEVQUAL;
2384 iwe.u.qual.level = priv->BSSinfo[i].RSSI;
2385 iwe.u.qual.qual = iwe.u.qual.level;
2386 /* iwe.u.qual.noise = SOMETHING */
2387 current_ev = iwe_stream_add_event(info, current_ev,
2388 extra + IW_SCAN_MAX_DATA,
2389 &iwe, IW_EV_QUAL_LEN);
2390
2391
2392 iwe.cmd = SIOCGIWENCODE;
2393 if (priv->BSSinfo[i].UsingWEP)
2394 iwe.u.data.flags = IW_ENCODE_ENABLED | IW_ENCODE_NOKEY;
2395 else
2396 iwe.u.data.flags = IW_ENCODE_DISABLED;
2397 iwe.u.data.length = 0;
2398 current_ev = iwe_stream_add_point(info, current_ev,
2399 extra + IW_SCAN_MAX_DATA,
2400 &iwe, NULL);
2401 }
2402
2403 /* Length of data */
2404 dwrq->length = (current_ev - extra);
2405 dwrq->flags = 0;
2406
2407 return 0;
2408}
2409
2410static int atmel_get_range(struct net_device *dev,
2411 struct iw_request_info *info,
2412 union iwreq_data *wrqu,
2413 char *extra)
2414{
2415 struct iw_point *dwrq = &wrqu->data;
2416 struct atmel_private *priv = netdev_priv(dev);
2417 struct iw_range *range = (struct iw_range *) extra;
2418 int k, i, j;
2419
2420 dwrq->length = sizeof(struct iw_range);
2421 memset(range, 0, sizeof(struct iw_range));
2422 range->min_nwid = 0x0000;
2423 range->max_nwid = 0x0000;
2424 range->num_channels = 0;
2425 for (j = 0; j < ARRAY_SIZE(channel_table); j++)
2426 if (priv->reg_domain == channel_table[j].reg_domain) {
2427 range->num_channels = channel_table[j].max - channel_table[j].min + 1;
2428 break;
2429 }
2430 if (range->num_channels != 0) {
2431 for (k = 0, i = channel_table[j].min; i <= channel_table[j].max; i++) {
2432 range->freq[k].i = i; /* List index */
2433
2434 /* Values in MHz -> * 10^5 * 10 */
2435 range->freq[k].m = 100000 *
2436 ieee80211_channel_to_frequency(i, NL80211_BAND_2GHZ);
2437 range->freq[k++].e = 1;
2438 }
2439 range->num_frequency = k;
2440 }
2441
2442 range->max_qual.qual = 100;
2443 range->max_qual.level = 100;
2444 range->max_qual.noise = 0;
2445 range->max_qual.updated = IW_QUAL_NOISE_INVALID;
2446
2447 range->avg_qual.qual = 50;
2448 range->avg_qual.level = 50;
2449 range->avg_qual.noise = 0;
2450 range->avg_qual.updated = IW_QUAL_NOISE_INVALID;
2451
2452 range->sensitivity = 0;
2453
2454 range->bitrate[0] = 1000000;
2455 range->bitrate[1] = 2000000;
2456 range->bitrate[2] = 5500000;
2457 range->bitrate[3] = 11000000;
2458 range->num_bitrates = 4;
2459
2460 range->min_rts = 0;
2461 range->max_rts = 2347;
2462 range->min_frag = 256;
2463 range->max_frag = 2346;
2464
2465 range->encoding_size[0] = 5;
2466 range->encoding_size[1] = 13;
2467 range->num_encoding_sizes = 2;
2468 range->max_encoding_tokens = 4;
2469
2470 range->pmp_flags = IW_POWER_ON;
2471 range->pmt_flags = IW_POWER_ON;
2472 range->pm_capa = 0;
2473
2474 range->we_version_source = WIRELESS_EXT;
2475 range->we_version_compiled = WIRELESS_EXT;
2476 range->retry_capa = IW_RETRY_LIMIT ;
2477 range->retry_flags = IW_RETRY_LIMIT;
2478 range->r_time_flags = 0;
2479 range->min_retry = 1;
2480 range->max_retry = 65535;
2481
2482 return 0;
2483}
2484
2485static int atmel_set_wap(struct net_device *dev,
2486 struct iw_request_info *info,
2487 union iwreq_data *wrqu,
2488 char *extra)
2489{
2490 struct sockaddr *awrq = &wrqu->ap_addr;
2491 struct atmel_private *priv = netdev_priv(dev);
2492 int i;
2493 static const u8 any[] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF };
2494 static const u8 off[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
2495 unsigned long flags;
2496
2497 if (awrq->sa_family != ARPHRD_ETHER)
2498 return -EINVAL;
2499
2500 if (!memcmp(any, awrq->sa_data, 6) ||
2501 !memcmp(off, awrq->sa_data, 6)) {
2502 del_timer_sync(&priv->management_timer);
2503 spin_lock_irqsave(&priv->irqlock, flags);
2504 atmel_scan(priv, 1);
2505 spin_unlock_irqrestore(&priv->irqlock, flags);
2506 return 0;
2507 }
2508
2509 for (i = 0; i < priv->BSS_list_entries; i++) {
2510 if (memcmp(priv->BSSinfo[i].BSSID, awrq->sa_data, 6) == 0) {
2511 if (!priv->wep_is_on && priv->BSSinfo[i].UsingWEP) {
2512 return -EINVAL;
2513 } else if (priv->wep_is_on && !priv->BSSinfo[i].UsingWEP) {
2514 return -EINVAL;
2515 } else {
2516 del_timer_sync(&priv->management_timer);
2517 spin_lock_irqsave(&priv->irqlock, flags);
2518 atmel_join_bss(priv, i);
2519 spin_unlock_irqrestore(&priv->irqlock, flags);
2520 return 0;
2521 }
2522 }
2523 }
2524
2525 return -EINVAL;
2526}
2527
2528static int atmel_config_commit(struct net_device *dev,
2529 struct iw_request_info *info, /* NULL */
2530 union iwreq_data *zwrq, /* NULL */
2531 char *extra) /* NULL */
2532{
2533 return atmel_open(dev);
2534}
2535
2536static const iw_handler atmel_handler[] =
2537{
2538 IW_HANDLER(SIOCSIWCOMMIT, atmel_config_commit),
2539 IW_HANDLER(SIOCGIWNAME, atmel_get_name),
2540 IW_HANDLER(SIOCSIWFREQ, atmel_set_freq),
2541 IW_HANDLER(SIOCGIWFREQ, atmel_get_freq),
2542 IW_HANDLER(SIOCSIWMODE, atmel_set_mode),
2543 IW_HANDLER(SIOCGIWMODE, atmel_get_mode),
2544 IW_HANDLER(SIOCGIWRANGE, atmel_get_range),
2545 IW_HANDLER(SIOCSIWAP, atmel_set_wap),
2546 IW_HANDLER(SIOCGIWAP, atmel_get_wap),
2547 IW_HANDLER(SIOCSIWSCAN, atmel_set_scan),
2548 IW_HANDLER(SIOCGIWSCAN, atmel_get_scan),
2549 IW_HANDLER(SIOCSIWESSID, atmel_set_essid),
2550 IW_HANDLER(SIOCGIWESSID, atmel_get_essid),
2551 IW_HANDLER(SIOCSIWRATE, atmel_set_rate),
2552 IW_HANDLER(SIOCGIWRATE, atmel_get_rate),
2553 IW_HANDLER(SIOCSIWRTS, atmel_set_rts),
2554 IW_HANDLER(SIOCGIWRTS, atmel_get_rts),
2555 IW_HANDLER(SIOCSIWFRAG, atmel_set_frag),
2556 IW_HANDLER(SIOCGIWFRAG, atmel_get_frag),
2557 IW_HANDLER(SIOCSIWRETRY, atmel_set_retry),
2558 IW_HANDLER(SIOCGIWRETRY, atmel_get_retry),
2559 IW_HANDLER(SIOCSIWENCODE, atmel_set_encode),
2560 IW_HANDLER(SIOCGIWENCODE, atmel_get_encode),
2561 IW_HANDLER(SIOCSIWPOWER, atmel_set_power),
2562 IW_HANDLER(SIOCGIWPOWER, atmel_get_power),
2563 IW_HANDLER(SIOCSIWAUTH, atmel_set_auth),
2564 IW_HANDLER(SIOCGIWAUTH, atmel_get_auth),
2565 IW_HANDLER(SIOCSIWENCODEEXT, atmel_set_encodeext),
2566 IW_HANDLER(SIOCGIWENCODEEXT, atmel_get_encodeext),
2567};
2568
2569static const iw_handler atmel_private_handler[] =
2570{
2571 NULL, /* SIOCIWFIRSTPRIV */
2572};
2573
2574struct atmel_priv_ioctl {
2575 char id[32];
2576 unsigned char __user *data;
2577 unsigned short len;
2578};
2579
2580#define ATMELFWL SIOCIWFIRSTPRIV
2581#define ATMELIDIFC ATMELFWL + 1
2582#define ATMELRD ATMELFWL + 2
2583#define ATMELMAGIC 0x51807
2584#define REGDOMAINSZ 20
2585
2586static const struct iw_priv_args atmel_private_args[] = {
2587 {
2588 .cmd = ATMELFWL,
2589 .set_args = IW_PRIV_TYPE_BYTE
2590 | IW_PRIV_SIZE_FIXED
2591 | sizeof(struct atmel_priv_ioctl),
2592 .get_args = IW_PRIV_TYPE_NONE,
2593 .name = "atmelfwl"
2594 }, {
2595 .cmd = ATMELIDIFC,
2596 .set_args = IW_PRIV_TYPE_NONE,
2597 .get_args = IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1,
2598 .name = "atmelidifc"
2599 }, {
2600 .cmd = ATMELRD,
2601 .set_args = IW_PRIV_TYPE_CHAR | REGDOMAINSZ,
2602 .get_args = IW_PRIV_TYPE_NONE,
2603 .name = "regdomain"
2604 },
2605};
2606
2607static const struct iw_handler_def atmel_handler_def = {
2608 .num_standard = ARRAY_SIZE(atmel_handler),
2609 .num_private = ARRAY_SIZE(atmel_private_handler),
2610 .num_private_args = ARRAY_SIZE(atmel_private_args),
2611 .standard = atmel_handler,
2612 .private = atmel_private_handler,
2613 .private_args = (struct iw_priv_args *) atmel_private_args,
2614 .get_wireless_stats = atmel_get_wireless_stats
2615};
2616
2617struct auth_body {
2618 __le16 alg;
2619 __le16 trans_seq;
2620 __le16 status;
2621 u8 el_id;
2622 u8 chall_text_len;
2623 u8 chall_text[253];
2624};
2625
2626static void atmel_enter_state(struct atmel_private *priv, int new_state)
2627{
2628 int old_state = priv->station_state;
2629
2630 if (new_state == old_state)
2631 return;
2632
2633 priv->station_state = new_state;
2634
2635 if (new_state == STATION_STATE_READY) {
2636 netif_start_queue(priv->dev);
2637 netif_carrier_on(priv->dev);
2638 }
2639
2640 if (old_state == STATION_STATE_READY) {
2641 netif_carrier_off(priv->dev);
2642 if (netif_running(priv->dev))
2643 netif_stop_queue(priv->dev);
2644 priv->last_beacon_timestamp = 0;
2645 }
2646}
2647
2648static void atmel_scan(struct atmel_private *priv, int specific_ssid)
2649{
2650 struct {
2651 u8 BSSID[ETH_ALEN];
2652 u8 SSID[MAX_SSID_LENGTH];
2653 u8 scan_type;
2654 u8 channel;
2655 __le16 BSS_type;
2656 __le16 min_channel_time;
2657 __le16 max_channel_time;
2658 u8 options;
2659 u8 SSID_size;
2660 } cmd;
2661
2662 eth_broadcast_addr(cmd.BSSID);
2663
2664 if (priv->fast_scan) {
2665 cmd.SSID_size = priv->SSID_size;
2666 memcpy(cmd.SSID, priv->SSID, priv->SSID_size);
2667 cmd.min_channel_time = cpu_to_le16(10);
2668 cmd.max_channel_time = cpu_to_le16(50);
2669 } else {
2670 priv->BSS_list_entries = 0;
2671 cmd.SSID_size = 0;
2672 cmd.min_channel_time = cpu_to_le16(10);
2673 cmd.max_channel_time = cpu_to_le16(120);
2674 }
2675
2676 cmd.options = 0;
2677
2678 if (!specific_ssid)
2679 cmd.options |= SCAN_OPTIONS_SITE_SURVEY;
2680
2681 cmd.channel = (priv->channel & 0x7f);
2682 cmd.scan_type = SCAN_TYPE_ACTIVE;
2683 cmd.BSS_type = cpu_to_le16(priv->operating_mode == IW_MODE_ADHOC ?
2684 BSS_TYPE_AD_HOC : BSS_TYPE_INFRASTRUCTURE);
2685
2686 atmel_send_command(priv, CMD_Scan, &cmd, sizeof(cmd));
2687
2688 /* This must come after all hardware access to avoid being messed up
2689 by stuff happening in interrupt context after we leave STATE_DOWN */
2690 atmel_enter_state(priv, STATION_STATE_SCANNING);
2691}
2692
2693static void join(struct atmel_private *priv, int type)
2694{
2695 struct {
2696 u8 BSSID[6];
2697 u8 SSID[MAX_SSID_LENGTH];
2698 u8 BSS_type; /* this is a short in a scan command - weird */
2699 u8 channel;
2700 __le16 timeout;
2701 u8 SSID_size;
2702 u8 reserved;
2703 } cmd;
2704
2705 cmd.SSID_size = priv->SSID_size;
2706 memcpy(cmd.SSID, priv->SSID, priv->SSID_size);
2707 memcpy(cmd.BSSID, priv->CurrentBSSID, ETH_ALEN);
2708 cmd.channel = (priv->channel & 0x7f);
2709 cmd.BSS_type = type;
2710 cmd.timeout = cpu_to_le16(2000);
2711
2712 atmel_send_command(priv, CMD_Join, &cmd, sizeof(cmd));
2713}
2714
2715static void start(struct atmel_private *priv, int type)
2716{
2717 struct {
2718 u8 BSSID[6];
2719 u8 SSID[MAX_SSID_LENGTH];
2720 u8 BSS_type;
2721 u8 channel;
2722 u8 SSID_size;
2723 u8 reserved[3];
2724 } cmd;
2725
2726 cmd.SSID_size = priv->SSID_size;
2727 memcpy(cmd.SSID, priv->SSID, priv->SSID_size);
2728 memcpy(cmd.BSSID, priv->BSSID, ETH_ALEN);
2729 cmd.BSS_type = type;
2730 cmd.channel = (priv->channel & 0x7f);
2731
2732 atmel_send_command(priv, CMD_Start, &cmd, sizeof(cmd));
2733}
2734
2735static void handle_beacon_probe(struct atmel_private *priv, u16 capability,
2736 u8 channel)
2737{
2738 int rejoin = 0;
2739 int new = capability & WLAN_CAPABILITY_SHORT_PREAMBLE ?
2740 SHORT_PREAMBLE : LONG_PREAMBLE;
2741
2742 if (priv->preamble != new) {
2743 priv->preamble = new;
2744 rejoin = 1;
2745 atmel_set_mib8(priv, Local_Mib_Type, LOCAL_MIB_PREAMBLE_TYPE, new);
2746 }
2747
2748 if (priv->channel != channel) {
2749 priv->channel = channel;
2750 rejoin = 1;
2751 atmel_set_mib8(priv, Phy_Mib_Type, PHY_MIB_CHANNEL_POS, channel);
2752 }
2753
2754 if (rejoin) {
2755 priv->station_is_associated = 0;
2756 atmel_enter_state(priv, STATION_STATE_JOINNING);
2757
2758 if (priv->operating_mode == IW_MODE_INFRA)
2759 join(priv, BSS_TYPE_INFRASTRUCTURE);
2760 else
2761 join(priv, BSS_TYPE_AD_HOC);
2762 }
2763}
2764
2765static void send_authentication_request(struct atmel_private *priv, u16 system,
2766 u8 *challenge, int challenge_len)
2767{
2768 struct ieee80211_hdr header;
2769 struct auth_body auth;
2770
2771 header.frame_control = cpu_to_le16(IEEE80211_FTYPE_MGMT | IEEE80211_STYPE_AUTH);
2772 header.duration_id = cpu_to_le16(0x8000);
2773 header.seq_ctrl = 0;
2774 memcpy(header.addr1, priv->CurrentBSSID, ETH_ALEN);
2775 memcpy(header.addr2, priv->dev->dev_addr, ETH_ALEN);
2776 memcpy(header.addr3, priv->CurrentBSSID, ETH_ALEN);
2777
2778 if (priv->wep_is_on && priv->CurrentAuthentTransactionSeqNum != 1)
2779 /* no WEP for authentication frames with TrSeqNo 1 */
2780 header.frame_control |= cpu_to_le16(IEEE80211_FCTL_PROTECTED);
2781
2782 auth.alg = cpu_to_le16(system);
2783
2784 auth.status = 0;
2785 auth.trans_seq = cpu_to_le16(priv->CurrentAuthentTransactionSeqNum);
2786 priv->ExpectedAuthentTransactionSeqNum = priv->CurrentAuthentTransactionSeqNum+1;
2787 priv->CurrentAuthentTransactionSeqNum += 2;
2788
2789 if (challenge_len != 0) {
2790 auth.el_id = 16; /* challenge_text */
2791 auth.chall_text_len = challenge_len;
2792 memcpy(auth.chall_text, challenge, challenge_len);
2793 atmel_transmit_management_frame(priv, &header, (u8 *)&auth, 8 + challenge_len);
2794 } else {
2795 atmel_transmit_management_frame(priv, &header, (u8 *)&auth, 6);
2796 }
2797}
2798
2799static void send_association_request(struct atmel_private *priv, int is_reassoc)
2800{
2801 u8 *ssid_el_p;
2802 int bodysize;
2803 struct ieee80211_hdr header;
2804 struct ass_req_format {
2805 __le16 capability;
2806 __le16 listen_interval;
2807 u8 ap[ETH_ALEN]; /* nothing after here directly accessible */
2808 u8 ssid_el_id;
2809 u8 ssid_len;
2810 u8 ssid[MAX_SSID_LENGTH];
2811 u8 sup_rates_el_id;
2812 u8 sup_rates_len;
2813 u8 rates[4];
2814 } body;
2815
2816 header.frame_control = cpu_to_le16(IEEE80211_FTYPE_MGMT |
2817 (is_reassoc ? IEEE80211_STYPE_REASSOC_REQ : IEEE80211_STYPE_ASSOC_REQ));
2818 header.duration_id = cpu_to_le16(0x8000);
2819 header.seq_ctrl = 0;
2820
2821 memcpy(header.addr1, priv->CurrentBSSID, ETH_ALEN);
2822 memcpy(header.addr2, priv->dev->dev_addr, ETH_ALEN);
2823 memcpy(header.addr3, priv->CurrentBSSID, ETH_ALEN);
2824
2825 body.capability = cpu_to_le16(WLAN_CAPABILITY_ESS);
2826 if (priv->wep_is_on)
2827 body.capability |= cpu_to_le16(WLAN_CAPABILITY_PRIVACY);
2828 if (priv->preamble == SHORT_PREAMBLE)
2829 body.capability |= cpu_to_le16(WLAN_CAPABILITY_SHORT_PREAMBLE);
2830
2831 body.listen_interval = cpu_to_le16(priv->listen_interval * priv->beacon_period);
2832
2833 /* current AP address - only in reassoc frame */
2834 if (is_reassoc) {
2835 memcpy(body.ap, priv->CurrentBSSID, ETH_ALEN);
2836 ssid_el_p = &body.ssid_el_id;
2837 bodysize = 18 + priv->SSID_size;
2838 } else {
2839 ssid_el_p = &body.ap[0];
2840 bodysize = 12 + priv->SSID_size;
2841 }
2842
2843 ssid_el_p[0] = WLAN_EID_SSID;
2844 ssid_el_p[1] = priv->SSID_size;
2845 memcpy(ssid_el_p + 2, priv->SSID, priv->SSID_size);
2846 ssid_el_p[2 + priv->SSID_size] = WLAN_EID_SUPP_RATES;
2847 ssid_el_p[3 + priv->SSID_size] = 4; /* len of supported rates */
2848 memcpy(ssid_el_p + 4 + priv->SSID_size, atmel_basic_rates, 4);
2849
2850 atmel_transmit_management_frame(priv, &header, (void *)&body, bodysize);
2851}
2852
2853static int is_frame_from_current_bss(struct atmel_private *priv,
2854 struct ieee80211_hdr *header)
2855{
2856 if (le16_to_cpu(header->frame_control) & IEEE80211_FCTL_FROMDS)
2857 return memcmp(header->addr3, priv->CurrentBSSID, 6) == 0;
2858 else
2859 return memcmp(header->addr2, priv->CurrentBSSID, 6) == 0;
2860}
2861
2862static int retrieve_bss(struct atmel_private *priv)
2863{
2864 int i;
2865 int max_rssi = -128;
2866 int max_index = -1;
2867
2868 if (priv->BSS_list_entries == 0)
2869 return -1;
2870
2871 if (priv->connect_to_any_BSS) {
2872 /* Select a BSS with the max-RSSI but of the same type and of
2873 the same WEP mode and that it is not marked as 'bad' (i.e.
2874 we had previously failed to connect to this BSS with the
2875 settings that we currently use) */
2876 priv->current_BSS = 0;
2877 for (i = 0; i < priv->BSS_list_entries; i++) {
2878 if (priv->operating_mode == priv->BSSinfo[i].BSStype &&
2879 ((!priv->wep_is_on && !priv->BSSinfo[i].UsingWEP) ||
2880 (priv->wep_is_on && priv->BSSinfo[i].UsingWEP)) &&
2881 !(priv->BSSinfo[i].channel & 0x80)) {
2882 max_rssi = priv->BSSinfo[i].RSSI;
2883 priv->current_BSS = max_index = i;
2884 }
2885 }
2886 return max_index;
2887 }
2888
2889 for (i = 0; i < priv->BSS_list_entries; i++) {
2890 if (priv->SSID_size == priv->BSSinfo[i].SSIDsize &&
2891 memcmp(priv->SSID, priv->BSSinfo[i].SSID, priv->SSID_size) == 0 &&
2892 priv->operating_mode == priv->BSSinfo[i].BSStype &&
2893 atmel_validate_channel(priv, priv->BSSinfo[i].channel) == 0) {
2894 if (priv->BSSinfo[i].RSSI >= max_rssi) {
2895 max_rssi = priv->BSSinfo[i].RSSI;
2896 max_index = i;
2897 }
2898 }
2899 }
2900 return max_index;
2901}
2902
2903static void store_bss_info(struct atmel_private *priv,
2904 struct ieee80211_hdr *header, u16 capability,
2905 u16 beacon_period, u8 channel, u8 rssi, u8 ssid_len,
2906 u8 *ssid, int is_beacon)
2907{
2908 u8 *bss = capability & WLAN_CAPABILITY_ESS ? header->addr2 : header->addr3;
2909 int i, index;
2910
2911 for (index = -1, i = 0; i < priv->BSS_list_entries; i++)
2912 if (memcmp(bss, priv->BSSinfo[i].BSSID, ETH_ALEN) == 0)
2913 index = i;
2914
2915 /* If we process a probe and an entry from this BSS exists
2916 we will update the BSS entry with the info from this BSS.
2917 If we process a beacon we will only update RSSI */
2918
2919 if (index == -1) {
2920 if (priv->BSS_list_entries == MAX_BSS_ENTRIES)
2921 return;
2922 index = priv->BSS_list_entries++;
2923 memcpy(priv->BSSinfo[index].BSSID, bss, ETH_ALEN);
2924 priv->BSSinfo[index].RSSI = rssi;
2925 } else {
2926 if (rssi > priv->BSSinfo[index].RSSI)
2927 priv->BSSinfo[index].RSSI = rssi;
2928 if (is_beacon)
2929 return;
2930 }
2931
2932 priv->BSSinfo[index].channel = channel;
2933 priv->BSSinfo[index].beacon_period = beacon_period;
2934 priv->BSSinfo[index].UsingWEP = capability & WLAN_CAPABILITY_PRIVACY;
2935 memcpy(priv->BSSinfo[index].SSID, ssid, ssid_len);
2936 priv->BSSinfo[index].SSIDsize = ssid_len;
2937
2938 if (capability & WLAN_CAPABILITY_IBSS)
2939 priv->BSSinfo[index].BSStype = IW_MODE_ADHOC;
2940 else if (capability & WLAN_CAPABILITY_ESS)
2941 priv->BSSinfo[index].BSStype = IW_MODE_INFRA;
2942
2943 priv->BSSinfo[index].preamble = capability & WLAN_CAPABILITY_SHORT_PREAMBLE ?
2944 SHORT_PREAMBLE : LONG_PREAMBLE;
2945}
2946
2947static void authenticate(struct atmel_private *priv, u16 frame_len)
2948{
2949 struct auth_body *auth = (struct auth_body *)priv->rx_buf;
2950 u16 status = le16_to_cpu(auth->status);
2951 u16 trans_seq_no = le16_to_cpu(auth->trans_seq);
2952 u16 system = le16_to_cpu(auth->alg);
2953
2954 if (status == WLAN_STATUS_SUCCESS && !priv->wep_is_on) {
2955 /* no WEP */
2956 if (priv->station_was_associated) {
2957 atmel_enter_state(priv, STATION_STATE_REASSOCIATING);
2958 send_association_request(priv, 1);
2959 return;
2960 } else {
2961 atmel_enter_state(priv, STATION_STATE_ASSOCIATING);
2962 send_association_request(priv, 0);
2963 return;
2964 }
2965 }
2966
2967 if (status == WLAN_STATUS_SUCCESS && priv->wep_is_on) {
2968 int should_associate = 0;
2969 /* WEP */
2970 if (trans_seq_no != priv->ExpectedAuthentTransactionSeqNum)
2971 return;
2972
2973 if (system == WLAN_AUTH_OPEN) {
2974 if (trans_seq_no == 0x0002) {
2975 should_associate = 1;
2976 }
2977 } else if (system == WLAN_AUTH_SHARED_KEY) {
2978 if (trans_seq_no == 0x0002 &&
2979 auth->el_id == WLAN_EID_CHALLENGE) {
2980 send_authentication_request(priv, system, auth->chall_text, auth->chall_text_len);
2981 return;
2982 } else if (trans_seq_no == 0x0004) {
2983 should_associate = 1;
2984 }
2985 }
2986
2987 if (should_associate) {
2988 if (priv->station_was_associated) {
2989 atmel_enter_state(priv, STATION_STATE_REASSOCIATING);
2990 send_association_request(priv, 1);
2991 return;
2992 } else {
2993 atmel_enter_state(priv, STATION_STATE_ASSOCIATING);
2994 send_association_request(priv, 0);
2995 return;
2996 }
2997 }
2998 }
2999
3000 if (status == WLAN_STATUS_NOT_SUPPORTED_AUTH_ALG) {
3001 /* Flip back and forth between WEP auth modes until the max
3002 * authentication tries has been exceeded.
3003 */
3004 if (system == WLAN_AUTH_OPEN) {
3005 priv->CurrentAuthentTransactionSeqNum = 0x001;
3006 priv->exclude_unencrypted = 1;
3007 send_authentication_request(priv, WLAN_AUTH_SHARED_KEY, NULL, 0);
3008 return;
3009 } else if (system == WLAN_AUTH_SHARED_KEY
3010 && priv->wep_is_on) {
3011 priv->CurrentAuthentTransactionSeqNum = 0x001;
3012 priv->exclude_unencrypted = 0;
3013 send_authentication_request(priv, WLAN_AUTH_OPEN, NULL, 0);
3014 return;
3015 } else if (priv->connect_to_any_BSS) {
3016 int bss_index;
3017
3018 priv->BSSinfo[(int)(priv->current_BSS)].channel |= 0x80;
3019
3020 if ((bss_index = retrieve_bss(priv)) != -1) {
3021 atmel_join_bss(priv, bss_index);
3022 return;
3023 }
3024 }
3025 }
3026
3027 priv->AuthenticationRequestRetryCnt = 0;
3028 atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
3029 priv->station_is_associated = 0;
3030}
3031
3032static void associate(struct atmel_private *priv, u16 frame_len, u16 subtype)
3033{
3034 struct ass_resp_format {
3035 __le16 capability;
3036 __le16 status;
3037 __le16 ass_id;
3038 u8 el_id;
3039 u8 length;
3040 u8 rates[4];
3041 } *ass_resp = (struct ass_resp_format *)priv->rx_buf;
3042
3043 u16 status = le16_to_cpu(ass_resp->status);
3044 u16 ass_id = le16_to_cpu(ass_resp->ass_id);
3045 u16 rates_len = ass_resp->length > 4 ? 4 : ass_resp->length;
3046
3047 union iwreq_data wrqu;
3048
3049 if (frame_len < 8 + rates_len)
3050 return;
3051
3052 if (status == WLAN_STATUS_SUCCESS) {
3053 if (subtype == IEEE80211_STYPE_ASSOC_RESP)
3054 priv->AssociationRequestRetryCnt = 0;
3055 else
3056 priv->ReAssociationRequestRetryCnt = 0;
3057
3058 atmel_set_mib16(priv, Mac_Mgmt_Mib_Type,
3059 MAC_MGMT_MIB_STATION_ID_POS, ass_id & 0x3fff);
3060 atmel_set_mib(priv, Phy_Mib_Type,
3061 PHY_MIB_RATE_SET_POS, ass_resp->rates, rates_len);
3062 if (priv->power_mode == 0) {
3063 priv->listen_interval = 1;
3064 atmel_set_mib8(priv, Mac_Mgmt_Mib_Type,
3065 MAC_MGMT_MIB_PS_MODE_POS, ACTIVE_MODE);
3066 atmel_set_mib16(priv, Mac_Mgmt_Mib_Type,
3067 MAC_MGMT_MIB_LISTEN_INTERVAL_POS, 1);
3068 } else {
3069 priv->listen_interval = 2;
3070 atmel_set_mib8(priv, Mac_Mgmt_Mib_Type,
3071 MAC_MGMT_MIB_PS_MODE_POS, PS_MODE);
3072 atmel_set_mib16(priv, Mac_Mgmt_Mib_Type,
3073 MAC_MGMT_MIB_LISTEN_INTERVAL_POS, 2);
3074 }
3075
3076 priv->station_is_associated = 1;
3077 priv->station_was_associated = 1;
3078 atmel_enter_state(priv, STATION_STATE_READY);
3079
3080 /* Send association event to userspace */
3081 wrqu.data.length = 0;
3082 wrqu.data.flags = 0;
3083 memcpy(wrqu.ap_addr.sa_data, priv->CurrentBSSID, ETH_ALEN);
3084 wrqu.ap_addr.sa_family = ARPHRD_ETHER;
3085 wireless_send_event(priv->dev, SIOCGIWAP, &wrqu, NULL);
3086
3087 return;
3088 }
3089
3090 if (subtype == IEEE80211_STYPE_ASSOC_RESP &&
3091 status != WLAN_STATUS_ASSOC_DENIED_RATES &&
3092 status != WLAN_STATUS_CAPS_UNSUPPORTED &&
3093 priv->AssociationRequestRetryCnt < MAX_ASSOCIATION_RETRIES) {
3094 mod_timer(&priv->management_timer, jiffies + MGMT_JIFFIES);
3095 priv->AssociationRequestRetryCnt++;
3096 send_association_request(priv, 0);
3097 return;
3098 }
3099
3100 if (subtype == IEEE80211_STYPE_REASSOC_RESP &&
3101 status != WLAN_STATUS_ASSOC_DENIED_RATES &&
3102 status != WLAN_STATUS_CAPS_UNSUPPORTED &&
3103 priv->ReAssociationRequestRetryCnt < MAX_ASSOCIATION_RETRIES) {
3104 mod_timer(&priv->management_timer, jiffies + MGMT_JIFFIES);
3105 priv->ReAssociationRequestRetryCnt++;
3106 send_association_request(priv, 1);
3107 return;
3108 }
3109
3110 atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
3111 priv->station_is_associated = 0;
3112
3113 if (priv->connect_to_any_BSS) {
3114 int bss_index;
3115 priv->BSSinfo[(int)(priv->current_BSS)].channel |= 0x80;
3116
3117 if ((bss_index = retrieve_bss(priv)) != -1)
3118 atmel_join_bss(priv, bss_index);
3119 }
3120}
3121
3122static void atmel_join_bss(struct atmel_private *priv, int bss_index)
3123{
3124 struct bss_info *bss = &priv->BSSinfo[bss_index];
3125
3126 memcpy(priv->CurrentBSSID, bss->BSSID, ETH_ALEN);
3127 memcpy(priv->SSID, bss->SSID, priv->SSID_size = bss->SSIDsize);
3128
3129 /* The WPA stuff cares about the current AP address */
3130 if (priv->use_wpa)
3131 build_wpa_mib(priv);
3132
3133 /* When switching to AdHoc turn OFF Power Save if needed */
3134
3135 if (bss->BSStype == IW_MODE_ADHOC &&
3136 priv->operating_mode != IW_MODE_ADHOC &&
3137 priv->power_mode) {
3138 priv->power_mode = 0;
3139 priv->listen_interval = 1;
3140 atmel_set_mib8(priv, Mac_Mgmt_Mib_Type,
3141 MAC_MGMT_MIB_PS_MODE_POS, ACTIVE_MODE);
3142 atmel_set_mib16(priv, Mac_Mgmt_Mib_Type,
3143 MAC_MGMT_MIB_LISTEN_INTERVAL_POS, 1);
3144 }
3145
3146 priv->operating_mode = bss->BSStype;
3147 priv->channel = bss->channel & 0x7f;
3148 priv->beacon_period = bss->beacon_period;
3149
3150 if (priv->preamble != bss->preamble) {
3151 priv->preamble = bss->preamble;
3152 atmel_set_mib8(priv, Local_Mib_Type,
3153 LOCAL_MIB_PREAMBLE_TYPE, bss->preamble);
3154 }
3155
3156 if (!priv->wep_is_on && bss->UsingWEP) {
3157 atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
3158 priv->station_is_associated = 0;
3159 return;
3160 }
3161
3162 if (priv->wep_is_on && !bss->UsingWEP) {
3163 atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
3164 priv->station_is_associated = 0;
3165 return;
3166 }
3167
3168 atmel_enter_state(priv, STATION_STATE_JOINNING);
3169
3170 if (priv->operating_mode == IW_MODE_INFRA)
3171 join(priv, BSS_TYPE_INFRASTRUCTURE);
3172 else
3173 join(priv, BSS_TYPE_AD_HOC);
3174}
3175
3176static void restart_search(struct atmel_private *priv)
3177{
3178 int bss_index;
3179
3180 if (!priv->connect_to_any_BSS) {
3181 atmel_scan(priv, 1);
3182 } else {
3183 priv->BSSinfo[(int)(priv->current_BSS)].channel |= 0x80;
3184
3185 if ((bss_index = retrieve_bss(priv)) != -1)
3186 atmel_join_bss(priv, bss_index);
3187 else
3188 atmel_scan(priv, 0);
3189 }
3190}
3191
3192static void smooth_rssi(struct atmel_private *priv, u8 rssi)
3193{
3194 u8 old = priv->wstats.qual.level;
3195 u8 max_rssi = 42; /* 502-rmfd-revd max by experiment, default for now */
3196
3197 switch (priv->firmware_type) {
3198 case ATMEL_FW_TYPE_502E:
3199 max_rssi = 63; /* 502-rmfd-reve max by experiment */
3200 break;
3201 default:
3202 break;
3203 }
3204
3205 rssi = rssi * 100 / max_rssi;
3206 if ((rssi + old) % 2)
3207 priv->wstats.qual.level = (rssi + old) / 2 + 1;
3208 else
3209 priv->wstats.qual.level = (rssi + old) / 2;
3210 priv->wstats.qual.updated |= IW_QUAL_LEVEL_UPDATED;
3211 priv->wstats.qual.updated &= ~IW_QUAL_LEVEL_INVALID;
3212}
3213
3214static void atmel_smooth_qual(struct atmel_private *priv)
3215{
3216 unsigned long time_diff = (jiffies - priv->last_qual) / HZ;
3217 while (time_diff--) {
3218 priv->last_qual += HZ;
3219 priv->wstats.qual.qual = priv->wstats.qual.qual / 2;
3220 priv->wstats.qual.qual +=
3221 priv->beacons_this_sec * priv->beacon_period * (priv->wstats.qual.level + 100) / 4000;
3222 priv->beacons_this_sec = 0;
3223 }
3224 priv->wstats.qual.updated |= IW_QUAL_QUAL_UPDATED;
3225 priv->wstats.qual.updated &= ~IW_QUAL_QUAL_INVALID;
3226}
3227
3228/* deals with incoming management frames. */
3229static void atmel_management_frame(struct atmel_private *priv,
3230 struct ieee80211_hdr *header,
3231 u16 frame_len, u8 rssi)
3232{
3233 u16 subtype;
3234
3235 subtype = le16_to_cpu(header->frame_control) & IEEE80211_FCTL_STYPE;
3236 switch (subtype) {
3237 case IEEE80211_STYPE_BEACON:
3238 case IEEE80211_STYPE_PROBE_RESP:
3239
3240 /* beacon frame has multiple variable-length fields -
3241 never let an engineer loose with a data structure design. */
3242 {
3243 struct beacon_format {
3244 __le64 timestamp;
3245 __le16 interval;
3246 __le16 capability;
3247 u8 ssid_el_id;
3248 u8 ssid_length;
3249 /* ssid here */
3250 u8 rates_el_id;
3251 u8 rates_length;
3252 /* rates here */
3253 u8 ds_el_id;
3254 u8 ds_length;
3255 /* ds here */
3256 } *beacon = (struct beacon_format *)priv->rx_buf;
3257
3258 u8 channel, rates_length, ssid_length;
3259 u64 timestamp = le64_to_cpu(beacon->timestamp);
3260 u16 beacon_interval = le16_to_cpu(beacon->interval);
3261 u16 capability = le16_to_cpu(beacon->capability);
3262 u8 *beaconp = priv->rx_buf;
3263 ssid_length = beacon->ssid_length;
3264 /* this blows chunks. */
3265 if (frame_len < 14 || frame_len < ssid_length + 15)
3266 return;
3267 rates_length = beaconp[beacon->ssid_length + 15];
3268 if (frame_len < ssid_length + rates_length + 18)
3269 return;
3270 if (ssid_length > MAX_SSID_LENGTH)
3271 return;
3272 channel = beaconp[ssid_length + rates_length + 18];
3273
3274 if (priv->station_state == STATION_STATE_READY) {
3275 smooth_rssi(priv, rssi);
3276 if (is_frame_from_current_bss(priv, header)) {
3277 priv->beacons_this_sec++;
3278 atmel_smooth_qual(priv);
3279 if (priv->last_beacon_timestamp) {
3280 /* Note truncate this to 32 bits - kernel can't divide a long */
3281 u32 beacon_delay = timestamp - priv->last_beacon_timestamp;
3282 int beacons = beacon_delay / (beacon_interval * 1000);
3283 if (beacons > 1)
3284 priv->wstats.miss.beacon += beacons - 1;
3285 }
3286 priv->last_beacon_timestamp = timestamp;
3287 handle_beacon_probe(priv, capability, channel);
3288 }
3289 }
3290
3291 if (priv->station_state == STATION_STATE_SCANNING)
3292 store_bss_info(priv, header, capability,
3293 beacon_interval, channel, rssi,
3294 ssid_length,
3295 &beacon->rates_el_id,
3296 subtype == IEEE80211_STYPE_BEACON);
3297 }
3298 break;
3299
3300 case IEEE80211_STYPE_AUTH:
3301
3302 if (priv->station_state == STATION_STATE_AUTHENTICATING)
3303 authenticate(priv, frame_len);
3304
3305 break;
3306
3307 case IEEE80211_STYPE_ASSOC_RESP:
3308 case IEEE80211_STYPE_REASSOC_RESP:
3309
3310 if (priv->station_state == STATION_STATE_ASSOCIATING ||
3311 priv->station_state == STATION_STATE_REASSOCIATING)
3312 associate(priv, frame_len, subtype);
3313
3314 break;
3315
3316 case IEEE80211_STYPE_DISASSOC:
3317 if (priv->station_is_associated &&
3318 priv->operating_mode == IW_MODE_INFRA &&
3319 is_frame_from_current_bss(priv, header)) {
3320 priv->station_was_associated = 0;
3321 priv->station_is_associated = 0;
3322
3323 atmel_enter_state(priv, STATION_STATE_JOINNING);
3324 join(priv, BSS_TYPE_INFRASTRUCTURE);
3325 }
3326
3327 break;
3328
3329 case IEEE80211_STYPE_DEAUTH:
3330 if (priv->operating_mode == IW_MODE_INFRA &&
3331 is_frame_from_current_bss(priv, header)) {
3332 priv->station_was_associated = 0;
3333
3334 atmel_enter_state(priv, STATION_STATE_JOINNING);
3335 join(priv, BSS_TYPE_INFRASTRUCTURE);
3336 }
3337
3338 break;
3339 }
3340}
3341
3342/* run when timer expires */
3343static void atmel_management_timer(struct timer_list *t)
3344{
3345 struct atmel_private *priv = from_timer(priv, t, management_timer);
3346 unsigned long flags;
3347
3348 /* Check if the card has been yanked. */
3349 if (priv->card && priv->present_callback &&
3350 !(*priv->present_callback)(priv->card))
3351 return;
3352
3353 spin_lock_irqsave(&priv->irqlock, flags);
3354
3355 switch (priv->station_state) {
3356
3357 case STATION_STATE_AUTHENTICATING:
3358 if (priv->AuthenticationRequestRetryCnt >= MAX_AUTHENTICATION_RETRIES) {
3359 atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
3360 priv->station_is_associated = 0;
3361 priv->AuthenticationRequestRetryCnt = 0;
3362 restart_search(priv);
3363 } else {
3364 int auth = WLAN_AUTH_OPEN;
3365 priv->AuthenticationRequestRetryCnt++;
3366 priv->CurrentAuthentTransactionSeqNum = 0x0001;
3367 mod_timer(&priv->management_timer, jiffies + MGMT_JIFFIES);
3368 if (priv->wep_is_on && priv->exclude_unencrypted)
3369 auth = WLAN_AUTH_SHARED_KEY;
3370 send_authentication_request(priv, auth, NULL, 0);
3371 }
3372 break;
3373
3374 case STATION_STATE_ASSOCIATING:
3375 if (priv->AssociationRequestRetryCnt == MAX_ASSOCIATION_RETRIES) {
3376 atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
3377 priv->station_is_associated = 0;
3378 priv->AssociationRequestRetryCnt = 0;
3379 restart_search(priv);
3380 } else {
3381 priv->AssociationRequestRetryCnt++;
3382 mod_timer(&priv->management_timer, jiffies + MGMT_JIFFIES);
3383 send_association_request(priv, 0);
3384 }
3385 break;
3386
3387 case STATION_STATE_REASSOCIATING:
3388 if (priv->ReAssociationRequestRetryCnt == MAX_ASSOCIATION_RETRIES) {
3389 atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
3390 priv->station_is_associated = 0;
3391 priv->ReAssociationRequestRetryCnt = 0;
3392 restart_search(priv);
3393 } else {
3394 priv->ReAssociationRequestRetryCnt++;
3395 mod_timer(&priv->management_timer, jiffies + MGMT_JIFFIES);
3396 send_association_request(priv, 1);
3397 }
3398 break;
3399
3400 default:
3401 break;
3402 }
3403
3404 spin_unlock_irqrestore(&priv->irqlock, flags);
3405}
3406
3407static void atmel_command_irq(struct atmel_private *priv)
3408{
3409 u8 status = atmel_rmem8(priv, atmel_co(priv, CMD_BLOCK_STATUS_OFFSET));
3410 u8 command = atmel_rmem8(priv, atmel_co(priv, CMD_BLOCK_COMMAND_OFFSET));
3411 int fast_scan;
3412 union iwreq_data wrqu;
3413
3414 if (status == CMD_STATUS_IDLE ||
3415 status == CMD_STATUS_IN_PROGRESS)
3416 return;
3417
3418 switch (command) {
3419 case CMD_Start:
3420 if (status == CMD_STATUS_COMPLETE) {
3421 priv->station_was_associated = priv->station_is_associated;
3422 atmel_get_mib(priv, Mac_Mgmt_Mib_Type, MAC_MGMT_MIB_CUR_BSSID_POS,
3423 (u8 *)priv->CurrentBSSID, 6);
3424 atmel_enter_state(priv, STATION_STATE_READY);
3425 }
3426 break;
3427
3428 case CMD_Scan:
3429 fast_scan = priv->fast_scan;
3430 priv->fast_scan = 0;
3431
3432 if (status != CMD_STATUS_COMPLETE) {
3433 atmel_scan(priv, 1);
3434 } else {
3435 int bss_index = retrieve_bss(priv);
3436 int notify_scan_complete = 1;
3437 if (bss_index != -1) {
3438 atmel_join_bss(priv, bss_index);
3439 } else if (priv->operating_mode == IW_MODE_ADHOC &&
3440 priv->SSID_size != 0) {
3441 start(priv, BSS_TYPE_AD_HOC);
3442 } else {
3443 priv->fast_scan = !fast_scan;
3444 atmel_scan(priv, 1);
3445 notify_scan_complete = 0;
3446 }
3447 priv->site_survey_state = SITE_SURVEY_COMPLETED;
3448 if (notify_scan_complete) {
3449 wrqu.data.length = 0;
3450 wrqu.data.flags = 0;
3451 wireless_send_event(priv->dev, SIOCGIWSCAN, &wrqu, NULL);
3452 }
3453 }
3454 break;
3455
3456 case CMD_SiteSurvey:
3457 priv->fast_scan = 0;
3458
3459 if (status != CMD_STATUS_COMPLETE)
3460 return;
3461
3462 priv->site_survey_state = SITE_SURVEY_COMPLETED;
3463 if (priv->station_is_associated) {
3464 atmel_enter_state(priv, STATION_STATE_READY);
3465 wrqu.data.length = 0;
3466 wrqu.data.flags = 0;
3467 wireless_send_event(priv->dev, SIOCGIWSCAN, &wrqu, NULL);
3468 } else {
3469 atmel_scan(priv, 1);
3470 }
3471 break;
3472
3473 case CMD_Join:
3474 if (status == CMD_STATUS_COMPLETE) {
3475 if (priv->operating_mode == IW_MODE_ADHOC) {
3476 priv->station_was_associated = priv->station_is_associated;
3477 atmel_enter_state(priv, STATION_STATE_READY);
3478 } else {
3479 int auth = WLAN_AUTH_OPEN;
3480 priv->AuthenticationRequestRetryCnt = 0;
3481 atmel_enter_state(priv, STATION_STATE_AUTHENTICATING);
3482
3483 mod_timer(&priv->management_timer, jiffies + MGMT_JIFFIES);
3484 priv->CurrentAuthentTransactionSeqNum = 0x0001;
3485 if (priv->wep_is_on && priv->exclude_unencrypted)
3486 auth = WLAN_AUTH_SHARED_KEY;
3487 send_authentication_request(priv, auth, NULL, 0);
3488 }
3489 return;
3490 }
3491
3492 atmel_scan(priv, 1);
3493 }
3494}
3495
3496static int atmel_wakeup_firmware(struct atmel_private *priv)
3497{
3498 struct host_info_struct *iface = &priv->host_info;
3499 u16 mr1, mr3;
3500 int i;
3501
3502 if (priv->card_type == CARD_TYPE_SPI_FLASH)
3503 atmel_set_gcr(priv->dev, GCR_REMAP);
3504
3505 /* wake up on-board processor */
3506 atmel_clear_gcr(priv->dev, 0x0040);
3507 atmel_write16(priv->dev, BSR, BSS_SRAM);
3508
3509 if (priv->card_type == CARD_TYPE_SPI_FLASH)
3510 mdelay(100);
3511
3512 /* and wait for it */
3513 for (i = LOOP_RETRY_LIMIT; i; i--) {
3514 mr1 = atmel_read16(priv->dev, MR1);
3515 mr3 = atmel_read16(priv->dev, MR3);
3516
3517 if (mr3 & MAC_BOOT_COMPLETE)
3518 break;
3519 if (mr1 & MAC_BOOT_COMPLETE &&
3520 priv->bus_type == BUS_TYPE_PCCARD)
3521 break;
3522 }
3523
3524 if (i == 0) {
3525 printk(KERN_ALERT "%s: MAC failed to boot.\n", priv->dev->name);
3526 return -EIO;
3527 }
3528
3529 if ((priv->host_info_base = atmel_read16(priv->dev, MR2)) == 0xffff) {
3530 printk(KERN_ALERT "%s: card missing.\n", priv->dev->name);
3531 return -ENODEV;
3532 }
3533
3534 /* now check for completion of MAC initialization through
3535 the FunCtrl field of the IFACE, poll MR1 to detect completion of
3536 MAC initialization, check completion status, set interrupt mask,
3537 enables interrupts and calls Tx and Rx initialization functions */
3538
3539 atmel_wmem8(priv, atmel_hi(priv, IFACE_FUNC_CTRL_OFFSET), FUNC_CTRL_INIT_COMPLETE);
3540
3541 for (i = LOOP_RETRY_LIMIT; i; i--) {
3542 mr1 = atmel_read16(priv->dev, MR1);
3543 mr3 = atmel_read16(priv->dev, MR3);
3544
3545 if (mr3 & MAC_INIT_COMPLETE)
3546 break;
3547 if (mr1 & MAC_INIT_COMPLETE &&
3548 priv->bus_type == BUS_TYPE_PCCARD)
3549 break;
3550 }
3551
3552 if (i == 0) {
3553 printk(KERN_ALERT "%s: MAC failed to initialise.\n",
3554 priv->dev->name);
3555 return -EIO;
3556 }
3557
3558 /* Check for MAC_INIT_OK only on the register that the MAC_INIT_OK was set */
3559 if ((mr3 & MAC_INIT_COMPLETE) &&
3560 !(atmel_read16(priv->dev, MR3) & MAC_INIT_OK)) {
3561 printk(KERN_ALERT "%s: MAC failed MR3 self-test.\n", priv->dev->name);
3562 return -EIO;
3563 }
3564 if ((mr1 & MAC_INIT_COMPLETE) &&
3565 !(atmel_read16(priv->dev, MR1) & MAC_INIT_OK)) {
3566 printk(KERN_ALERT "%s: MAC failed MR1 self-test.\n", priv->dev->name);
3567 return -EIO;
3568 }
3569
3570 atmel_copy_to_host(priv->dev, (unsigned char *)iface,
3571 priv->host_info_base, sizeof(*iface));
3572
3573 iface->tx_buff_pos = le16_to_cpu(iface->tx_buff_pos);
3574 iface->tx_buff_size = le16_to_cpu(iface->tx_buff_size);
3575 iface->tx_desc_pos = le16_to_cpu(iface->tx_desc_pos);
3576 iface->tx_desc_count = le16_to_cpu(iface->tx_desc_count);
3577 iface->rx_buff_pos = le16_to_cpu(iface->rx_buff_pos);
3578 iface->rx_buff_size = le16_to_cpu(iface->rx_buff_size);
3579 iface->rx_desc_pos = le16_to_cpu(iface->rx_desc_pos);
3580 iface->rx_desc_count = le16_to_cpu(iface->rx_desc_count);
3581 iface->build_version = le16_to_cpu(iface->build_version);
3582 iface->command_pos = le16_to_cpu(iface->command_pos);
3583 iface->major_version = le16_to_cpu(iface->major_version);
3584 iface->minor_version = le16_to_cpu(iface->minor_version);
3585 iface->func_ctrl = le16_to_cpu(iface->func_ctrl);
3586 iface->mac_status = le16_to_cpu(iface->mac_status);
3587
3588 return 0;
3589}
3590
3591/* determine type of memory and MAC address */
3592static int probe_atmel_card(struct net_device *dev)
3593{
3594 int rc = 0;
3595 struct atmel_private *priv = netdev_priv(dev);
3596 u8 addr[ETH_ALEN] = {};
3597
3598 /* reset pccard */
3599 if (priv->bus_type == BUS_TYPE_PCCARD)
3600 atmel_write16(dev, GCR, 0x0060);
3601
3602 atmel_write16(dev, GCR, 0x0040);
3603 msleep(500);
3604
3605 if (atmel_read16(dev, MR2) == 0) {
3606 /* No stored firmware so load a small stub which just
3607 tells us the MAC address */
3608 int i;
3609 priv->card_type = CARD_TYPE_EEPROM;
3610 atmel_write16(dev, BSR, BSS_IRAM);
3611 atmel_copy_to_card(dev, 0, mac_reader, sizeof(mac_reader));
3612 atmel_set_gcr(dev, GCR_REMAP);
3613 atmel_clear_gcr(priv->dev, 0x0040);
3614 atmel_write16(dev, BSR, BSS_SRAM);
3615 for (i = LOOP_RETRY_LIMIT; i; i--)
3616 if (atmel_read16(dev, MR3) & MAC_BOOT_COMPLETE)
3617 break;
3618 if (i == 0) {
3619 printk(KERN_ALERT "%s: MAC failed to boot MAC address reader.\n", dev->name);
3620 } else {
3621
3622 atmel_copy_to_host(dev, addr, atmel_read16(dev, MR2), 6);
3623 eth_hw_addr_set(dev, addr);
3624 /* got address, now squash it again until the network
3625 interface is opened */
3626 if (priv->bus_type == BUS_TYPE_PCCARD)
3627 atmel_write16(dev, GCR, 0x0060);
3628 atmel_write16(dev, GCR, 0x0040);
3629 rc = 1;
3630 }
3631 } else if (atmel_read16(dev, MR4) == 0) {
3632 /* Mac address easy in this case. */
3633 priv->card_type = CARD_TYPE_PARALLEL_FLASH;
3634 atmel_write16(dev, BSR, 1);
3635 atmel_copy_to_host(dev, addr, 0xc000, 6);
3636 eth_hw_addr_set(dev, addr);
3637 atmel_write16(dev, BSR, 0x200);
3638 rc = 1;
3639 } else {
3640 /* Standard firmware in flash, boot it up and ask
3641 for the Mac Address */
3642 priv->card_type = CARD_TYPE_SPI_FLASH;
3643 if (atmel_wakeup_firmware(priv) == 0) {
3644 atmel_get_mib(priv, Mac_Address_Mib_Type, 0, addr, 6);
3645 eth_hw_addr_set(dev, addr);
3646
3647 /* got address, now squash it again until the network
3648 interface is opened */
3649 if (priv->bus_type == BUS_TYPE_PCCARD)
3650 atmel_write16(dev, GCR, 0x0060);
3651 atmel_write16(dev, GCR, 0x0040);
3652 rc = 1;
3653 }
3654 }
3655
3656 if (rc) {
3657 if (dev->dev_addr[0] == 0xFF) {
3658 static const u8 default_mac[] = {
3659 0x00, 0x04, 0x25, 0x00, 0x00, 0x00
3660 };
3661 printk(KERN_ALERT "%s: *** Invalid MAC address. UPGRADE Firmware ****\n", dev->name);
3662 eth_hw_addr_set(dev, default_mac);
3663 }
3664 }
3665
3666 return rc;
3667}
3668
3669/* Move the encyption information on the MIB structure.
3670 This routine is for the pre-WPA firmware: later firmware has
3671 a different format MIB and a different routine. */
3672static void build_wep_mib(struct atmel_private *priv)
3673{
3674 struct { /* NB this is matched to the hardware, don't change. */
3675 u8 wep_is_on;
3676 u8 default_key; /* 0..3 */
3677 u8 reserved;
3678 u8 exclude_unencrypted;
3679
3680 u32 WEPICV_error_count;
3681 u32 WEP_excluded_count;
3682
3683 u8 wep_keys[MAX_ENCRYPTION_KEYS][13];
3684 u8 encryption_level; /* 0, 1, 2 */
3685 u8 reserved2[3];
3686 } mib;
3687 int i;
3688
3689 mib.wep_is_on = priv->wep_is_on;
3690 if (priv->wep_is_on) {
3691 if (priv->wep_key_len[priv->default_key] > 5)
3692 mib.encryption_level = 2;
3693 else
3694 mib.encryption_level = 1;
3695 } else {
3696 mib.encryption_level = 0;
3697 }
3698
3699 mib.default_key = priv->default_key;
3700 mib.exclude_unencrypted = priv->exclude_unencrypted;
3701
3702 for (i = 0; i < MAX_ENCRYPTION_KEYS; i++)
3703 memcpy(mib.wep_keys[i], priv->wep_keys[i], 13);
3704
3705 atmel_set_mib(priv, Mac_Wep_Mib_Type, 0, (u8 *)&mib, sizeof(mib));
3706}
3707
3708static void build_wpa_mib(struct atmel_private *priv)
3709{
3710 /* This is for the later (WPA enabled) firmware. */
3711
3712 struct { /* NB this is matched to the hardware, don't change. */
3713 u8 cipher_default_key_value[MAX_ENCRYPTION_KEYS][MAX_ENCRYPTION_KEY_SIZE];
3714 u8 receiver_address[ETH_ALEN];
3715 u8 wep_is_on;
3716 u8 default_key; /* 0..3 */
3717 u8 group_key;
3718 u8 exclude_unencrypted;
3719 u8 encryption_type;
3720 u8 reserved;
3721
3722 u32 WEPICV_error_count;
3723 u32 WEP_excluded_count;
3724
3725 u8 key_RSC[4][8];
3726 } mib;
3727
3728 int i;
3729
3730 mib.wep_is_on = priv->wep_is_on;
3731 mib.exclude_unencrypted = priv->exclude_unencrypted;
3732 memcpy(mib.receiver_address, priv->CurrentBSSID, ETH_ALEN);
3733
3734 /* zero all the keys before adding in valid ones. */
3735 memset(mib.cipher_default_key_value, 0, sizeof(mib.cipher_default_key_value));
3736
3737 if (priv->wep_is_on) {
3738 /* There's a comment in the Atmel code to the effect that this
3739 is only valid when still using WEP, it may need to be set to
3740 something to use WPA */
3741 memset(mib.key_RSC, 0, sizeof(mib.key_RSC));
3742
3743 mib.default_key = mib.group_key = 255;
3744 for (i = 0; i < MAX_ENCRYPTION_KEYS; i++) {
3745 if (priv->wep_key_len[i] > 0) {
3746 memcpy(mib.cipher_default_key_value[i], priv->wep_keys[i], MAX_ENCRYPTION_KEY_SIZE);
3747 if (i == priv->default_key) {
3748 mib.default_key = i;
3749 mib.cipher_default_key_value[i][MAX_ENCRYPTION_KEY_SIZE-1] = 7;
3750 mib.cipher_default_key_value[i][MAX_ENCRYPTION_KEY_SIZE-2] = priv->pairwise_cipher_suite;
3751 } else {
3752 mib.group_key = i;
3753 priv->group_cipher_suite = priv->pairwise_cipher_suite;
3754 mib.cipher_default_key_value[i][MAX_ENCRYPTION_KEY_SIZE-1] = 1;
3755 mib.cipher_default_key_value[i][MAX_ENCRYPTION_KEY_SIZE-2] = priv->group_cipher_suite;
3756 }
3757 }
3758 }
3759 if (mib.default_key == 255)
3760 mib.default_key = mib.group_key != 255 ? mib.group_key : 0;
3761 if (mib.group_key == 255)
3762 mib.group_key = mib.default_key;
3763
3764 }
3765
3766 atmel_set_mib(priv, Mac_Wep_Mib_Type, 0, (u8 *)&mib, sizeof(mib));
3767}
3768
3769static int reset_atmel_card(struct net_device *dev)
3770{
3771 /* do everything necessary to wake up the hardware, including
3772 waiting for the lightning strike and throwing the knife switch....
3773
3774 set all the Mib values which matter in the card to match
3775 their settings in the atmel_private structure. Some of these
3776 can be altered on the fly, but many (WEP, infrastructure or ad-hoc)
3777 can only be changed by tearing down the world and coming back through
3778 here.
3779
3780 This routine is also responsible for initialising some
3781 hardware-specific fields in the atmel_private structure,
3782 including a copy of the firmware's hostinfo structure
3783 which is the route into the rest of the firmware datastructures. */
3784
3785 struct atmel_private *priv = netdev_priv(dev);
3786 u8 configuration;
3787 int old_state = priv->station_state;
3788 int err = 0;
3789
3790 /* data to add to the firmware names, in priority order
3791 this implemenents firmware versioning */
3792
3793 static char *firmware_modifier[] = {
3794 "-wpa",
3795 "",
3796 NULL
3797 };
3798
3799 /* reset pccard */
3800 if (priv->bus_type == BUS_TYPE_PCCARD)
3801 atmel_write16(priv->dev, GCR, 0x0060);
3802
3803 /* stop card , disable interrupts */
3804 atmel_write16(priv->dev, GCR, 0x0040);
3805
3806 if (priv->card_type == CARD_TYPE_EEPROM) {
3807 /* copy in firmware if needed */
3808 const struct firmware *fw_entry = NULL;
3809 const unsigned char *fw;
3810 int len = priv->firmware_length;
3811 if (!(fw = priv->firmware)) {
3812 if (priv->firmware_type == ATMEL_FW_TYPE_NONE) {
3813 if (strlen(priv->firmware_id) == 0) {
3814 printk(KERN_INFO
3815 "%s: card type is unknown: assuming at76c502 firmware is OK.\n",
3816 dev->name);
3817 printk(KERN_INFO
3818 "%s: if not, use the firmware= module parameter.\n",
3819 dev->name);
3820 strcpy(priv->firmware_id, "atmel_at76c502.bin");
3821 }
3822 err = request_firmware(&fw_entry, priv->firmware_id, priv->sys_dev);
3823 if (err != 0) {
3824 printk(KERN_ALERT
3825 "%s: firmware %s is missing, cannot continue.\n",
3826 dev->name, priv->firmware_id);
3827 return err;
3828 }
3829 } else {
3830 int fw_index = 0;
3831 int success = 0;
3832
3833 /* get firmware filename entry based on firmware type ID */
3834 while (fw_table[fw_index].fw_type != priv->firmware_type
3835 && fw_table[fw_index].fw_type != ATMEL_FW_TYPE_NONE)
3836 fw_index++;
3837
3838 /* construct the actual firmware file name */
3839 if (fw_table[fw_index].fw_type != ATMEL_FW_TYPE_NONE) {
3840 int i;
3841 for (i = 0; firmware_modifier[i]; i++) {
3842 snprintf(priv->firmware_id, 32, "%s%s.%s", fw_table[fw_index].fw_file,
3843 firmware_modifier[i], fw_table[fw_index].fw_file_ext);
3844 priv->firmware_id[31] = '\0';
3845 if (request_firmware(&fw_entry, priv->firmware_id, priv->sys_dev) == 0) {
3846 success = 1;
3847 break;
3848 }
3849 }
3850 }
3851 if (!success) {
3852 printk(KERN_ALERT
3853 "%s: firmware %s is missing, cannot start.\n",
3854 dev->name, priv->firmware_id);
3855 priv->firmware_id[0] = '\0';
3856 return -ENOENT;
3857 }
3858 }
3859
3860 fw = fw_entry->data;
3861 len = fw_entry->size;
3862 }
3863
3864 if (len <= 0x6000) {
3865 atmel_write16(priv->dev, BSR, BSS_IRAM);
3866 atmel_copy_to_card(priv->dev, 0, fw, len);
3867 atmel_set_gcr(priv->dev, GCR_REMAP);
3868 } else {
3869 /* Remap */
3870 atmel_set_gcr(priv->dev, GCR_REMAP);
3871 atmel_write16(priv->dev, BSR, BSS_IRAM);
3872 atmel_copy_to_card(priv->dev, 0, fw, 0x6000);
3873 atmel_write16(priv->dev, BSR, 0x2ff);
3874 atmel_copy_to_card(priv->dev, 0x8000, &fw[0x6000], len - 0x6000);
3875 }
3876
3877 release_firmware(fw_entry);
3878 }
3879
3880 err = atmel_wakeup_firmware(priv);
3881 if (err != 0)
3882 return err;
3883
3884 /* Check the version and set the correct flag for wpa stuff,
3885 old and new firmware is incompatible.
3886 The pre-wpa 3com firmware reports major version 5,
3887 the wpa 3com firmware is major version 4 and doesn't need
3888 the 3com broken-ness filter. */
3889 priv->use_wpa = (priv->host_info.major_version == 4);
3890 priv->radio_on_broken = (priv->host_info.major_version == 5);
3891
3892 /* unmask all irq sources */
3893 atmel_wmem8(priv, atmel_hi(priv, IFACE_INT_MASK_OFFSET), 0xff);
3894
3895 /* int Tx system and enable Tx */
3896 atmel_wmem8(priv, atmel_tx(priv, TX_DESC_FLAGS_OFFSET, 0), 0);
3897 atmel_wmem32(priv, atmel_tx(priv, TX_DESC_NEXT_OFFSET, 0), 0x80000000L);
3898 atmel_wmem16(priv, atmel_tx(priv, TX_DESC_POS_OFFSET, 0), 0);
3899 atmel_wmem16(priv, atmel_tx(priv, TX_DESC_SIZE_OFFSET, 0), 0);
3900
3901 priv->tx_desc_free = priv->host_info.tx_desc_count;
3902 priv->tx_desc_head = 0;
3903 priv->tx_desc_tail = 0;
3904 priv->tx_desc_previous = 0;
3905 priv->tx_free_mem = priv->host_info.tx_buff_size;
3906 priv->tx_buff_head = 0;
3907 priv->tx_buff_tail = 0;
3908
3909 configuration = atmel_rmem8(priv, atmel_hi(priv, IFACE_FUNC_CTRL_OFFSET));
3910 atmel_wmem8(priv, atmel_hi(priv, IFACE_FUNC_CTRL_OFFSET),
3911 configuration | FUNC_CTRL_TxENABLE);
3912
3913 /* init Rx system and enable */
3914 priv->rx_desc_head = 0;
3915
3916 configuration = atmel_rmem8(priv, atmel_hi(priv, IFACE_FUNC_CTRL_OFFSET));
3917 atmel_wmem8(priv, atmel_hi(priv, IFACE_FUNC_CTRL_OFFSET),
3918 configuration | FUNC_CTRL_RxENABLE);
3919
3920 if (!priv->radio_on_broken) {
3921 if (atmel_send_command_wait(priv, CMD_EnableRadio, NULL, 0) ==
3922 CMD_STATUS_REJECTED_RADIO_OFF) {
3923 printk(KERN_INFO "%s: cannot turn the radio on.\n",
3924 dev->name);
3925 return -EIO;
3926 }
3927 }
3928
3929 /* set up enough MIB values to run. */
3930 atmel_set_mib8(priv, Local_Mib_Type, LOCAL_MIB_AUTO_TX_RATE_POS, priv->auto_tx_rate);
3931 atmel_set_mib8(priv, Local_Mib_Type, LOCAL_MIB_TX_PROMISCUOUS_POS, PROM_MODE_OFF);
3932 atmel_set_mib16(priv, Mac_Mib_Type, MAC_MIB_RTS_THRESHOLD_POS, priv->rts_threshold);
3933 atmel_set_mib16(priv, Mac_Mib_Type, MAC_MIB_FRAG_THRESHOLD_POS, priv->frag_threshold);
3934 atmel_set_mib8(priv, Mac_Mib_Type, MAC_MIB_SHORT_RETRY_POS, priv->short_retry);
3935 atmel_set_mib8(priv, Mac_Mib_Type, MAC_MIB_LONG_RETRY_POS, priv->long_retry);
3936 atmel_set_mib8(priv, Local_Mib_Type, LOCAL_MIB_PREAMBLE_TYPE, priv->preamble);
3937 atmel_set_mib(priv, Mac_Address_Mib_Type, MAC_ADDR_MIB_MAC_ADDR_POS,
3938 priv->dev->dev_addr, 6);
3939 atmel_set_mib8(priv, Mac_Mgmt_Mib_Type, MAC_MGMT_MIB_PS_MODE_POS, ACTIVE_MODE);
3940 atmel_set_mib16(priv, Mac_Mgmt_Mib_Type, MAC_MGMT_MIB_LISTEN_INTERVAL_POS, 1);
3941 atmel_set_mib16(priv, Mac_Mgmt_Mib_Type, MAC_MGMT_MIB_BEACON_PER_POS, priv->default_beacon_period);
3942 atmel_set_mib(priv, Phy_Mib_Type, PHY_MIB_RATE_SET_POS, atmel_basic_rates, 4);
3943 atmel_set_mib8(priv, Mac_Mgmt_Mib_Type, MAC_MGMT_MIB_CUR_PRIVACY_POS, priv->wep_is_on);
3944 if (priv->use_wpa)
3945 build_wpa_mib(priv);
3946 else
3947 build_wep_mib(priv);
3948
3949 if (old_state == STATION_STATE_READY) {
3950 union iwreq_data wrqu;
3951
3952 wrqu.data.length = 0;
3953 wrqu.data.flags = 0;
3954 wrqu.ap_addr.sa_family = ARPHRD_ETHER;
3955 eth_zero_addr(wrqu.ap_addr.sa_data);
3956 wireless_send_event(priv->dev, SIOCGIWAP, &wrqu, NULL);
3957 }
3958
3959 return 0;
3960}
3961
3962static void atmel_send_command(struct atmel_private *priv, int command,
3963 void *cmd, int cmd_size)
3964{
3965 if (cmd)
3966 atmel_copy_to_card(priv->dev, atmel_co(priv, CMD_BLOCK_PARAMETERS_OFFSET),
3967 cmd, cmd_size);
3968
3969 atmel_wmem8(priv, atmel_co(priv, CMD_BLOCK_COMMAND_OFFSET), command);
3970 atmel_wmem8(priv, atmel_co(priv, CMD_BLOCK_STATUS_OFFSET), 0);
3971}
3972
3973static int atmel_send_command_wait(struct atmel_private *priv, int command,
3974 void *cmd, int cmd_size)
3975{
3976 int i, status;
3977
3978 atmel_send_command(priv, command, cmd, cmd_size);
3979
3980 for (i = 5000; i; i--) {
3981 status = atmel_rmem8(priv, atmel_co(priv, CMD_BLOCK_STATUS_OFFSET));
3982 if (status != CMD_STATUS_IDLE &&
3983 status != CMD_STATUS_IN_PROGRESS)
3984 break;
3985 udelay(20);
3986 }
3987
3988 if (i == 0) {
3989 printk(KERN_ALERT "%s: failed to contact MAC.\n", priv->dev->name);
3990 status = CMD_STATUS_HOST_ERROR;
3991 } else {
3992 if (command != CMD_EnableRadio)
3993 status = CMD_STATUS_COMPLETE;
3994 }
3995
3996 return status;
3997}
3998
3999static u8 atmel_get_mib8(struct atmel_private *priv, u8 type, u8 index)
4000{
4001 struct get_set_mib m;
4002 m.type = type;
4003 m.size = 1;
4004 m.index = index;
4005
4006 atmel_send_command_wait(priv, CMD_Get_MIB_Vars, &m, MIB_HEADER_SIZE + 1);
4007 return atmel_rmem8(priv, atmel_co(priv, CMD_BLOCK_PARAMETERS_OFFSET + MIB_HEADER_SIZE));
4008}
4009
4010static void atmel_set_mib8(struct atmel_private *priv, u8 type, u8 index, u8 data)
4011{
4012 struct get_set_mib m;
4013 m.type = type;
4014 m.size = 1;
4015 m.index = index;
4016 m.data[0] = data;
4017
4018 atmel_send_command_wait(priv, CMD_Set_MIB_Vars, &m, MIB_HEADER_SIZE + 1);
4019}
4020
4021static void atmel_set_mib16(struct atmel_private *priv, u8 type, u8 index,
4022 u16 data)
4023{
4024 struct get_set_mib m;
4025 m.type = type;
4026 m.size = 2;
4027 m.index = index;
4028 m.data[0] = data;
4029 m.data[1] = data >> 8;
4030
4031 atmel_send_command_wait(priv, CMD_Set_MIB_Vars, &m, MIB_HEADER_SIZE + 2);
4032}
4033
4034static void atmel_set_mib(struct atmel_private *priv, u8 type, u8 index,
4035 const u8 *data, int data_len)
4036{
4037 struct get_set_mib m;
4038 m.type = type;
4039 m.size = data_len;
4040 m.index = index;
4041
4042 if (data_len > MIB_MAX_DATA_BYTES)
4043 printk(KERN_ALERT "%s: MIB buffer too small.\n", priv->dev->name);
4044
4045 memcpy(m.data, data, data_len);
4046 atmel_send_command_wait(priv, CMD_Set_MIB_Vars, &m, MIB_HEADER_SIZE + data_len);
4047}
4048
4049static void atmel_get_mib(struct atmel_private *priv, u8 type, u8 index,
4050 u8 *data, int data_len)
4051{
4052 struct get_set_mib m;
4053 m.type = type;
4054 m.size = data_len;
4055 m.index = index;
4056
4057 if (data_len > MIB_MAX_DATA_BYTES)
4058 printk(KERN_ALERT "%s: MIB buffer too small.\n", priv->dev->name);
4059
4060 atmel_send_command_wait(priv, CMD_Get_MIB_Vars, &m, MIB_HEADER_SIZE + data_len);
4061 atmel_copy_to_host(priv->dev, data,
4062 atmel_co(priv, CMD_BLOCK_PARAMETERS_OFFSET + MIB_HEADER_SIZE), data_len);
4063}
4064
4065static void atmel_writeAR(struct net_device *dev, u16 data)
4066{
4067 int i;
4068 outw(data, dev->base_addr + AR);
4069 /* Address register appears to need some convincing..... */
4070 for (i = 0; data != inw(dev->base_addr + AR) && i < 10; i++)
4071 outw(data, dev->base_addr + AR);
4072}
4073
4074static void atmel_copy_to_card(struct net_device *dev, u16 dest,
4075 const unsigned char *src, u16 len)
4076{
4077 int i;
4078 atmel_writeAR(dev, dest);
4079 if (dest % 2) {
4080 atmel_write8(dev, DR, *src);
4081 src++; len--;
4082 }
4083 for (i = len; i > 1 ; i -= 2) {
4084 u8 lb = *src++;
4085 u8 hb = *src++;
4086 atmel_write16(dev, DR, lb | (hb << 8));
4087 }
4088 if (i)
4089 atmel_write8(dev, DR, *src);
4090}
4091
4092static void atmel_copy_to_host(struct net_device *dev, unsigned char *dest,
4093 u16 src, u16 len)
4094{
4095 int i;
4096 atmel_writeAR(dev, src);
4097 if (src % 2) {
4098 *dest = atmel_read8(dev, DR);
4099 dest++; len--;
4100 }
4101 for (i = len; i > 1 ; i -= 2) {
4102 u16 hw = atmel_read16(dev, DR);
4103 *dest++ = hw;
4104 *dest++ = hw >> 8;
4105 }
4106 if (i)
4107 *dest = atmel_read8(dev, DR);
4108}
4109
4110static void atmel_set_gcr(struct net_device *dev, u16 mask)
4111{
4112 outw(inw(dev->base_addr + GCR) | mask, dev->base_addr + GCR);
4113}
4114
4115static void atmel_clear_gcr(struct net_device *dev, u16 mask)
4116{
4117 outw(inw(dev->base_addr + GCR) & ~mask, dev->base_addr + GCR);
4118}
4119
4120static int atmel_lock_mac(struct atmel_private *priv)
4121{
4122 int i, j = 20;
4123 retry:
4124 for (i = 5000; i; i--) {
4125 if (!atmel_rmem8(priv, atmel_hi(priv, IFACE_LOCKOUT_HOST_OFFSET)))
4126 break;
4127 udelay(20);
4128 }
4129
4130 if (!i)
4131 return 0; /* timed out */
4132
4133 atmel_wmem8(priv, atmel_hi(priv, IFACE_LOCKOUT_MAC_OFFSET), 1);
4134 if (atmel_rmem8(priv, atmel_hi(priv, IFACE_LOCKOUT_HOST_OFFSET))) {
4135 atmel_wmem8(priv, atmel_hi(priv, IFACE_LOCKOUT_MAC_OFFSET), 0);
4136 if (!j--)
4137 return 0; /* timed out */
4138 goto retry;
4139 }
4140
4141 return 1;
4142}
4143
4144static void atmel_wmem32(struct atmel_private *priv, u16 pos, u32 data)
4145{
4146 atmel_writeAR(priv->dev, pos);
4147 atmel_write16(priv->dev, DR, data); /* card is little-endian */
4148 atmel_write16(priv->dev, DR, data >> 16);
4149}
4150
4151/***************************************************************************/
4152/* There follows the source form of the MAC address reading firmware */
4153/***************************************************************************/
4154#if 0
4155
4156/* Copyright 2003 Matthew T. Russotto */
4157/* But derived from the Atmel 76C502 firmware written by Atmel and */
4158/* included in "atmel wireless lan drivers" package */
4159/*
4160 This file is part of net.russotto.AtmelMACFW, hereto referred to
4161 as AtmelMACFW
4162
4163 AtmelMACFW is free software; you can redistribute it and/or modify
4164 it under the terms of the GNU General Public License version 2
4165 as published by the Free Software Foundation.
4166
4167 AtmelMACFW is distributed in the hope that it will be useful,
4168 but WITHOUT ANY WARRANTY; without even the implied warranty of
4169 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
4170 GNU General Public License for more details.
4171
4172 You should have received a copy of the GNU General Public License
4173 along with AtmelMACFW; if not, see <http://www.gnu.org/licenses/>.
4174
4175****************************************************************************/
4176/* This firmware should work on the 76C502 RFMD, RFMD_D, and RFMD_E */
4177/* It will probably work on the 76C504 and 76C502 RFMD_3COM */
4178/* It only works on SPI EEPROM versions of the card. */
4179
4180/* This firmware initializes the SPI controller and clock, reads the MAC */
4181/* address from the EEPROM into SRAM, and puts the SRAM offset of the MAC */
4182/* address in MR2, and sets MR3 to 0x10 to indicate it is done */
4183/* It also puts a complete copy of the EEPROM in SRAM with the offset in */
4184/* MR4, for investigational purposes (maybe we can determine chip type */
4185/* from that?) */
4186
4187 .org 0
4188 .set MRBASE, 0x8000000
4189 .set CPSR_INITIAL, 0xD3 /* IRQ/FIQ disabled, ARM mode, Supervisor state */
4190 .set CPSR_USER, 0xD1 /* IRQ/FIQ disabled, ARM mode, USER state */
4191 .set SRAM_BASE, 0x02000000
4192 .set SP_BASE, 0x0F300000
4193 .set UNK_BASE, 0x0F000000 /* Some internal device, but which one? */
4194 .set SPI_CGEN_BASE, 0x0E000000 /* Some internal device, but which one? */
4195 .set UNK3_BASE, 0x02014000 /* Some internal device, but which one? */
4196 .set STACK_BASE, 0x5600
4197 .set SP_SR, 0x10
4198 .set SP_TDRE, 2 /* status register bit -- TDR empty */
4199 .set SP_RDRF, 1 /* status register bit -- RDR full */
4200 .set SP_SWRST, 0x80
4201 .set SP_SPIEN, 0x1
4202 .set SP_CR, 0 /* control register */
4203 .set SP_MR, 4 /* mode register */
4204 .set SP_RDR, 0x08 /* Read Data Register */
4205 .set SP_TDR, 0x0C /* Transmit Data Register */
4206 .set SP_CSR0, 0x30 /* chip select registers */
4207 .set SP_CSR1, 0x34
4208 .set SP_CSR2, 0x38
4209 .set SP_CSR3, 0x3C
4210 .set NVRAM_CMD_RDSR, 5 /* read status register */
4211 .set NVRAM_CMD_READ, 3 /* read data */
4212 .set NVRAM_SR_RDY, 1 /* RDY bit. This bit is inverted */
4213 .set SPI_8CLOCKS, 0xFF /* Writing this to the TDR doesn't do anything to the
4214 serial output, since SO is normally high. But it
4215 does cause 8 clock cycles and thus 8 bits to be
4216 clocked in to the chip. See Atmel's SPI
4217 controller (e.g. AT91M55800) timing and 4K
4218 SPI EEPROM manuals */
4219
4220 .set NVRAM_SCRATCH, 0x02000100 /* arbitrary area for scratchpad memory */
4221 .set NVRAM_IMAGE, 0x02000200
4222 .set NVRAM_LENGTH, 0x0200
4223 .set MAC_ADDRESS_MIB, SRAM_BASE
4224 .set MAC_ADDRESS_LENGTH, 6
4225 .set MAC_BOOT_FLAG, 0x10
4226 .set MR1, 0
4227 .set MR2, 4
4228 .set MR3, 8
4229 .set MR4, 0xC
4230RESET_VECTOR:
4231 b RESET_HANDLER
4232UNDEF_VECTOR:
4233 b HALT1
4234SWI_VECTOR:
4235 b HALT1
4236IABORT_VECTOR:
4237 b HALT1
4238DABORT_VECTOR:
4239RESERVED_VECTOR:
4240 b HALT1
4241IRQ_VECTOR:
4242 b HALT1
4243FIQ_VECTOR:
4244 b HALT1
4245HALT1: b HALT1
4246RESET_HANDLER:
4247 mov r0, #CPSR_INITIAL
4248 msr CPSR_c, r0 /* This is probably unnecessary */
4249
4250/* I'm guessing this is initializing clock generator electronics for SPI */
4251 ldr r0, =SPI_CGEN_BASE
4252 mov r1, #0
4253 mov r1, r1, lsl #3
4254 orr r1, r1, #0
4255 str r1, [r0]
4256 ldr r1, [r0, #28]
4257 bic r1, r1, #16
4258 str r1, [r0, #28]
4259 mov r1, #1
4260 str r1, [r0, #8]
4261
4262 ldr r0, =MRBASE
4263 mov r1, #0
4264 strh r1, [r0, #MR1]
4265 strh r1, [r0, #MR2]
4266 strh r1, [r0, #MR3]
4267 strh r1, [r0, #MR4]
4268
4269 mov sp, #STACK_BASE
4270 bl SP_INIT
4271 mov r0, #10
4272 bl DELAY9
4273 bl GET_MAC_ADDR
4274 bl GET_WHOLE_NVRAM
4275 ldr r0, =MRBASE
4276 ldr r1, =MAC_ADDRESS_MIB
4277 strh r1, [r0, #MR2]
4278 ldr r1, =NVRAM_IMAGE
4279 strh r1, [r0, #MR4]
4280 mov r1, #MAC_BOOT_FLAG
4281 strh r1, [r0, #MR3]
4282HALT2: b HALT2
4283.func Get_Whole_NVRAM, GET_WHOLE_NVRAM
4284GET_WHOLE_NVRAM:
4285 stmdb sp!, {lr}
4286 mov r2, #0 /* 0th bytes of NVRAM */
4287 mov r3, #NVRAM_LENGTH
4288 mov r1, #0 /* not used in routine */
4289 ldr r0, =NVRAM_IMAGE
4290 bl NVRAM_XFER
4291 ldmia sp!, {lr}
4292 bx lr
4293.endfunc
4294
4295.func Get_MAC_Addr, GET_MAC_ADDR
4296GET_MAC_ADDR:
4297 stmdb sp!, {lr}
4298 mov r2, #0x120 /* address of MAC Address within NVRAM */
4299 mov r3, #MAC_ADDRESS_LENGTH
4300 mov r1, #0 /* not used in routine */
4301 ldr r0, =MAC_ADDRESS_MIB
4302 bl NVRAM_XFER
4303 ldmia sp!, {lr}
4304 bx lr
4305.endfunc
4306.ltorg
4307.func Delay9, DELAY9
4308DELAY9:
4309 adds r0, r0, r0, LSL #3 /* r0 = r0 * 9 */
4310DELAYLOOP:
4311 beq DELAY9_done
4312 subs r0, r0, #1
4313 b DELAYLOOP
4314DELAY9_done:
4315 bx lr
4316.endfunc
4317
4318.func SP_Init, SP_INIT
4319SP_INIT:
4320 mov r1, #SP_SWRST
4321 ldr r0, =SP_BASE
4322 str r1, [r0, #SP_CR] /* reset the SPI */
4323 mov r1, #0
4324 str r1, [r0, #SP_CR] /* release SPI from reset state */
4325 mov r1, #SP_SPIEN
4326 str r1, [r0, #SP_MR] /* set the SPI to MASTER mode*/
4327 str r1, [r0, #SP_CR] /* enable the SPI */
4328
4329/* My guess would be this turns on the SPI clock */
4330 ldr r3, =SPI_CGEN_BASE
4331 ldr r1, [r3, #28]
4332 orr r1, r1, #0x2000
4333 str r1, [r3, #28]
4334
4335 ldr r1, =0x2000c01
4336 str r1, [r0, #SP_CSR0]
4337 ldr r1, =0x2000201
4338 str r1, [r0, #SP_CSR1]
4339 str r1, [r0, #SP_CSR2]
4340 str r1, [r0, #SP_CSR3]
4341 ldr r1, [r0, #SP_SR]
4342 ldr r0, [r0, #SP_RDR]
4343 bx lr
4344.endfunc
4345.func NVRAM_Init, NVRAM_INIT
4346NVRAM_INIT:
4347 ldr r1, =SP_BASE
4348 ldr r0, [r1, #SP_RDR]
4349 mov r0, #NVRAM_CMD_RDSR
4350 str r0, [r1, #SP_TDR]
4351SP_loop1:
4352 ldr r0, [r1, #SP_SR]
4353 tst r0, #SP_TDRE
4354 beq SP_loop1
4355
4356 mov r0, #SPI_8CLOCKS
4357 str r0, [r1, #SP_TDR]
4358SP_loop2:
4359 ldr r0, [r1, #SP_SR]
4360 tst r0, #SP_TDRE
4361 beq SP_loop2
4362
4363 ldr r0, [r1, #SP_RDR]
4364SP_loop3:
4365 ldr r0, [r1, #SP_SR]
4366 tst r0, #SP_RDRF
4367 beq SP_loop3
4368
4369 ldr r0, [r1, #SP_RDR]
4370 and r0, r0, #255
4371 bx lr
4372.endfunc
4373
4374.func NVRAM_Xfer, NVRAM_XFER
4375 /* r0 = dest address */
4376 /* r1 = not used */
4377 /* r2 = src address within NVRAM */
4378 /* r3 = length */
4379NVRAM_XFER:
4380 stmdb sp!, {r4, r5, lr}
4381 mov r5, r0 /* save r0 (dest address) */
4382 mov r4, r3 /* save r3 (length) */
4383 mov r0, r2, LSR #5 /* SPI memories put A8 in the command field */
4384 and r0, r0, #8
4385 add r0, r0, #NVRAM_CMD_READ
4386 ldr r1, =NVRAM_SCRATCH
4387 strb r0, [r1, #0] /* save command in NVRAM_SCRATCH[0] */
4388 strb r2, [r1, #1] /* save low byte of source address in NVRAM_SCRATCH[1] */
4389_local1:
4390 bl NVRAM_INIT
4391 tst r0, #NVRAM_SR_RDY
4392 bne _local1
4393 mov r0, #20
4394 bl DELAY9
4395 mov r2, r4 /* length */
4396 mov r1, r5 /* dest address */
4397 mov r0, #2 /* bytes to transfer in command */
4398 bl NVRAM_XFER2
4399 ldmia sp!, {r4, r5, lr}
4400 bx lr
4401.endfunc
4402
4403.func NVRAM_Xfer2, NVRAM_XFER2
4404NVRAM_XFER2:
4405 stmdb sp!, {r4, r5, r6, lr}
4406 ldr r4, =SP_BASE
4407 mov r3, #0
4408 cmp r0, #0
4409 bls _local2
4410 ldr r5, =NVRAM_SCRATCH
4411_local4:
4412 ldrb r6, [r5, r3]
4413 str r6, [r4, #SP_TDR]
4414_local3:
4415 ldr r6, [r4, #SP_SR]
4416 tst r6, #SP_TDRE
4417 beq _local3
4418 add r3, r3, #1
4419 cmp r3, r0 /* r0 is # of bytes to send out (command+addr) */
4420 blo _local4
4421_local2:
4422 mov r3, #SPI_8CLOCKS
4423 str r3, [r4, #SP_TDR]
4424 ldr r0, [r4, #SP_RDR]
4425_local5:
4426 ldr r0, [r4, #SP_SR]
4427 tst r0, #SP_RDRF
4428 beq _local5
4429 ldr r0, [r4, #SP_RDR] /* what's this byte? It's the byte read while writing the TDR -- nonsense, because the NVRAM doesn't read and write at the same time */
4430 mov r0, #0
4431 cmp r2, #0 /* r2 is # of bytes to copy in */
4432 bls _local6
4433_local7:
4434 ldr r5, [r4, #SP_SR]
4435 tst r5, #SP_TDRE
4436 beq _local7
4437 str r3, [r4, #SP_TDR] /* r3 has SPI_8CLOCKS */
4438_local8:
4439 ldr r5, [r4, #SP_SR]
4440 tst r5, #SP_RDRF
4441 beq _local8
4442 ldr r5, [r4, #SP_RDR] /* but didn't we read this byte above? */
4443 strb r5, [r1], #1 /* postindexed */
4444 add r0, r0, #1
4445 cmp r0, r2
4446 blo _local7 /* since we don't send another address, the NVRAM must be capable of sequential reads */
4447_local6:
4448 mov r0, #200
4449 bl DELAY9
4450 ldmia sp!, {r4, r5, r6, lr}
4451 bx lr
4452#endif
drivers/net/wireless/atmel/atmel.h+0−31
@@ -1,31 +0,0 @@
1/* SPDX-License-Identifier: GPL-2.0-or-later */
2/*** -*- linux-c -*- **********************************************************
3
4 Driver for Atmel at76c502 at76c504 and at76c506 wireless cards.
5
6 Copyright 2005 Dan Williams and Red Hat, Inc.
7
8
9******************************************************************************/
10
11#ifndef _ATMEL_H
12#define _ATMEL_H
13
14typedef enum {
15 ATMEL_FW_TYPE_NONE = 0,
16 ATMEL_FW_TYPE_502,
17 ATMEL_FW_TYPE_502D,
18 ATMEL_FW_TYPE_502E,
19 ATMEL_FW_TYPE_502_3COM,
20 ATMEL_FW_TYPE_504,
21 ATMEL_FW_TYPE_504_2958,
22 ATMEL_FW_TYPE_504A_2958,
23 ATMEL_FW_TYPE_506
24} AtmelFWType;
25
26struct net_device *init_atmel_card(unsigned short, unsigned long, const AtmelFWType, struct device *,
27 int (*present_func)(void *), void * );
28void stop_atmel_card( struct net_device *);
29int atmel_open( struct net_device * );
30
31#endif
drivers/net/wireless/atmel/atmel_cs.c+0−292
@@ -1,292 +0,0 @@
1/*** -*- linux-c -*- **********************************************************
2
3 Driver for Atmel at76c502 at76c504 and at76c506 wireless cards.
4
5 Copyright 2000-2001 ATMEL Corporation.
6 Copyright 2003 Simon Kelley.
7
8 This code was developed from version 2.1.1 of the Atmel drivers,
9 released by Atmel corp. under the GPL in December 2002. It also
10 includes code from the Linux aironet drivers (C) Benjamin Reed,
11 and the Linux PCMCIA package, (C) David Hinds.
12
13 For all queries about this code, please contact the current author,
14 Simon Kelley <simon@thekelleys.org.uk> and not Atmel Corporation.
15
16 This program is free software; you can redistribute it and/or modify
17 it under the terms of the GNU General Public License as published by
18 the Free Software Foundation; either version 2 of the License, or
19 (at your option) any later version.
20
21 This software is distributed in the hope that it will be useful,
22 but WITHOUT ANY WARRANTY; without even the implied warranty of
23 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24 GNU General Public License for more details.
25
26 You should have received a copy of the GNU General Public License
27 along with Atmel wireless lan drivers; if not, see
28 <http://www.gnu.org/licenses/>.
29
30******************************************************************************/
31
32#ifdef __IN_PCMCIA_PACKAGE__
33#include <pcmcia/k_compat.h>
34#endif
35#include <linux/kernel.h>
36#include <linux/module.h>
37#include <linux/ptrace.h>
38#include <linux/slab.h>
39#include <linux/string.h>
40#include <linux/netdevice.h>
41#include <linux/moduleparam.h>
42#include <linux/device.h>
43
44#include <pcmcia/cistpl.h>
45#include <pcmcia/cisreg.h>
46#include <pcmcia/ds.h>
47#include <pcmcia/ciscode.h>
48
49#include <asm/io.h>
50#include <linux/wireless.h>
51
52#include "atmel.h"
53
54
55/*====================================================================*/
56
57MODULE_AUTHOR("Simon Kelley");
58MODULE_DESCRIPTION("Support for Atmel at76c50x 802.11 wireless ethernet cards.");
59MODULE_LICENSE("GPL");
60
61/*====================================================================*/
62
63static int atmel_config(struct pcmcia_device *link);
64static void atmel_release(struct pcmcia_device *link);
65
66static void atmel_detach(struct pcmcia_device *p_dev);
67
68struct local_info {
69 struct net_device *eth_dev;
70};
71
72static int atmel_probe(struct pcmcia_device *p_dev)
73{
74 struct local_info *local;
75 int ret;
76
77 dev_dbg(&p_dev->dev, "atmel_attach()\n");
78
79 /* Allocate space for private device-specific data */
80 local = kzalloc(sizeof(*local), GFP_KERNEL);
81 if (!local)
82 return -ENOMEM;
83
84 p_dev->priv = local;
85
86 ret = atmel_config(p_dev);
87 if (ret)
88 goto err_free_priv;
89
90 return 0;
91
92err_free_priv:
93 kfree(p_dev->priv);
94 return ret;
95}
96
97static void atmel_detach(struct pcmcia_device *link)
98{
99 dev_dbg(&link->dev, "atmel_detach\n");
100
101 atmel_release(link);
102
103 kfree(link->priv);
104}
105
106/* Call-back function to interrogate PCMCIA-specific information
107 about the current existence of the card */
108static int card_present(void *arg)
109{
110 struct pcmcia_device *link = (struct pcmcia_device *)arg;
111
112 if (pcmcia_dev_present(link))
113 return 1;
114
115 return 0;
116}
117
118static int atmel_config_check(struct pcmcia_device *p_dev, void *priv_data)
119{
120 if (p_dev->config_index == 0)
121 return -EINVAL;
122
123 return pcmcia_request_io(p_dev);
124}
125
126static int atmel_config(struct pcmcia_device *link)
127{
128 int ret;
129 const struct pcmcia_device_id *did;
130
131 did = dev_get_drvdata(&link->dev);
132
133 dev_dbg(&link->dev, "atmel_config\n");
134
135 link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP |
136 CONF_AUTO_AUDIO | CONF_AUTO_SET_IO;
137
138 if (pcmcia_loop_config(link, atmel_config_check, NULL))
139 goto failed;
140
141 if (!link->irq) {
142 dev_err(&link->dev, "atmel: cannot assign IRQ: check that CONFIG_ISA is set in kernel config.");
143 goto failed;
144 }
145
146 ret = pcmcia_enable_device(link);
147 if (ret)
148 goto failed;
149
150 ((struct local_info *)link->priv)->eth_dev =
151 init_atmel_card(link->irq,
152 link->resource[0]->start,
153 did ? did->driver_info : ATMEL_FW_TYPE_NONE,
154 &link->dev,
155 card_present,
156 link);
157 if (!((struct local_info *)link->priv)->eth_dev)
158 goto failed;
159
160
161 return 0;
162
163 failed:
164 atmel_release(link);
165 return -ENODEV;
166}
167
168static void atmel_release(struct pcmcia_device *link)
169{
170 struct net_device *dev = ((struct local_info *)link->priv)->eth_dev;
171
172 dev_dbg(&link->dev, "atmel_release\n");
173
174 if (dev)
175 stop_atmel_card(dev);
176 ((struct local_info *)link->priv)->eth_dev = NULL;
177
178 pcmcia_disable_device(link);
179}
180
181static int atmel_suspend(struct pcmcia_device *link)
182{
183 struct local_info *local = link->priv;
184
185 netif_device_detach(local->eth_dev);
186
187 return 0;
188}
189
190static int atmel_resume(struct pcmcia_device *link)
191{
192 struct local_info *local = link->priv;
193
194 atmel_open(local->eth_dev);
195 netif_device_attach(local->eth_dev);
196
197 return 0;
198}
199
200/*====================================================================*/
201/* We use the driver_info field to store the correct firmware type for a card. */
202
203#define PCMCIA_DEVICE_MANF_CARD_INFO(manf, card, info) { \
204 .match_flags = PCMCIA_DEV_ID_MATCH_MANF_ID| \
205 PCMCIA_DEV_ID_MATCH_CARD_ID, \
206 .manf_id = (manf), \
207 .card_id = (card), \
208 .driver_info = (kernel_ulong_t)(info), }
209
210#define PCMCIA_DEVICE_PROD_ID12_INFO(v1, v2, vh1, vh2, info) { \
211 .match_flags = PCMCIA_DEV_ID_MATCH_PROD_ID1| \
212 PCMCIA_DEV_ID_MATCH_PROD_ID2, \
213 .prod_id = { (v1), (v2), NULL, NULL }, \
214 .prod_id_hash = { (vh1), (vh2), 0, 0 }, \
215 .driver_info = (kernel_ulong_t)(info), }
216
217static const struct pcmcia_device_id atmel_ids[] = {
218 PCMCIA_DEVICE_MANF_CARD_INFO(0x0101, 0x0620, ATMEL_FW_TYPE_502_3COM),
219 PCMCIA_DEVICE_MANF_CARD_INFO(0x0101, 0x0696, ATMEL_FW_TYPE_502_3COM),
220 PCMCIA_DEVICE_MANF_CARD_INFO(0x01bf, 0x3302, ATMEL_FW_TYPE_502E),
221 PCMCIA_DEVICE_MANF_CARD_INFO(0xd601, 0x0007, ATMEL_FW_TYPE_502),
222 PCMCIA_DEVICE_PROD_ID12_INFO("11WAVE", "11WP611AL-E", 0x9eb2da1f, 0xc9a0d3f9, ATMEL_FW_TYPE_502E),
223 PCMCIA_DEVICE_PROD_ID12_INFO("ATMEL", "AT76C502AR", 0xabda4164, 0x41b37e1f, ATMEL_FW_TYPE_502),
224 PCMCIA_DEVICE_PROD_ID12_INFO("ATMEL", "AT76C502AR_D", 0xabda4164, 0x3675d704, ATMEL_FW_TYPE_502D),
225 PCMCIA_DEVICE_PROD_ID12_INFO("ATMEL", "AT76C502AR_E", 0xabda4164, 0x4172e792, ATMEL_FW_TYPE_502E),
226 PCMCIA_DEVICE_PROD_ID12_INFO("ATMEL", "AT76C504_R", 0xabda4164, 0x917f3d72, ATMEL_FW_TYPE_504_2958),
227 PCMCIA_DEVICE_PROD_ID12_INFO("ATMEL", "AT76C504", 0xabda4164, 0x5040670a, ATMEL_FW_TYPE_504),
228 PCMCIA_DEVICE_PROD_ID12_INFO("ATMEL", "AT76C504A", 0xabda4164, 0xe15ed87f, ATMEL_FW_TYPE_504A_2958),
229 PCMCIA_DEVICE_PROD_ID12_INFO("BT", "Voyager 1020 Laptop Adapter", 0xae49b86a, 0x1e957cd5, ATMEL_FW_TYPE_502),
230 PCMCIA_DEVICE_PROD_ID12_INFO("CNet", "CNWLC 11Mbps Wireless PC Card V-5", 0xbc477dde, 0x502fae6b, ATMEL_FW_TYPE_502E),
231 PCMCIA_DEVICE_PROD_ID12_INFO("IEEE 802.11b", "Wireless LAN PC Card", 0x5b878724, 0x122f1df6, ATMEL_FW_TYPE_502),
232 PCMCIA_DEVICE_PROD_ID12_INFO("IEEE 802.11b", "Wireless LAN Card S", 0x5b878724, 0x5fba533a, ATMEL_FW_TYPE_504_2958),
233 PCMCIA_DEVICE_PROD_ID12_INFO("OEM", "11Mbps Wireless LAN PC Card V-3", 0xfea54c90, 0x1c5b0f68, ATMEL_FW_TYPE_502),
234 PCMCIA_DEVICE_PROD_ID12_INFO("SMC", "2632W", 0xc4f8b18b, 0x30f38774, ATMEL_FW_TYPE_502D),
235 PCMCIA_DEVICE_PROD_ID12_INFO("SMC", "2632W-V2", 0xc4f8b18b, 0x172d1377, ATMEL_FW_TYPE_502),
236 PCMCIA_DEVICE_PROD_ID12_INFO("Wireless", "PC_CARD", 0xa407ecdd, 0x119f6314, ATMEL_FW_TYPE_502D),
237 PCMCIA_DEVICE_PROD_ID12_INFO("WLAN", "802.11b PC CARD", 0x575c516c, 0xb1f6dbc4, ATMEL_FW_TYPE_502D),
238 PCMCIA_DEVICE_PROD_ID12_INFO("LG", "LW2100N", 0xb474d43a, 0x6b1fec94, ATMEL_FW_TYPE_502E),
239 PCMCIA_DEVICE_NULL
240};
241
242MODULE_DEVICE_TABLE(pcmcia, atmel_ids);
243
244static struct pcmcia_driver atmel_driver = {
245 .owner = THIS_MODULE,
246 .name = "atmel_cs",
247 .probe = atmel_probe,
248 .remove = atmel_detach,
249 .id_table = atmel_ids,
250 .suspend = atmel_suspend,
251 .resume = atmel_resume,
252};
253module_pcmcia_driver(atmel_driver);
254
255/*
256 This program is free software; you can redistribute it and/or
257 modify it under the terms of the GNU General Public License
258 as published by the Free Software Foundation; either version 2
259 of the License, or (at your option) any later version.
260
261 This program is distributed in the hope that it will be useful,
262 but WITHOUT ANY WARRANTY; without even the implied warranty of
263 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
264 GNU General Public License for more details.
265
266 In addition:
267
268 Redistribution and use in source and binary forms, with or without
269 modification, are permitted provided that the following conditions
270 are met:
271
272 1. Redistributions of source code must retain the above copyright
273 notice, this list of conditions and the following disclaimer.
274 2. Redistributions in binary form must reproduce the above copyright
275 notice, this list of conditions and the following disclaimer in the
276 documentation and/or other materials provided with the distribution.
277 3. The name of the author may not be used to endorse or promote
278 products derived from this software without specific prior written
279 permission.
280
281 THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
282 IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
283 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
284 ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
285 INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
286 (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
287 SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
288 HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
289 STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
290 IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
291 POSSIBILITY OF SUCH DAMAGE.
292*/
drivers/net/wireless/atmel/atmel_pci.c+0−65
@@ -1,65 +0,0 @@
1// SPDX-License-Identifier: GPL-2.0-or-later
2/*** -*- linux-c -*- **********************************************************
3
4 Driver for Atmel at76c502 at76c504 and at76c506 wireless cards.
5
6 Copyright 2004 Simon Kelley.
7
8
9******************************************************************************/
10#include <linux/pci.h>
11#include <linux/kernel.h>
12#include <linux/module.h>
13#include <linux/netdevice.h>
14#include "atmel.h"
15
16MODULE_AUTHOR("Simon Kelley");
17MODULE_DESCRIPTION("Support for Atmel at76c50x 802.11 wireless ethernet cards.");
18MODULE_LICENSE("GPL");
19
20static const struct pci_device_id card_ids[] = {
21 { 0x1114, 0x0506, PCI_ANY_ID, PCI_ANY_ID },
22 { 0, }
23};
24
25MODULE_DEVICE_TABLE(pci, card_ids);
26
27static int atmel_pci_probe(struct pci_dev *, const struct pci_device_id *);
28static void atmel_pci_remove(struct pci_dev *);
29
30static struct pci_driver atmel_driver = {
31 .name = "atmel",
32 .id_table = card_ids,
33 .probe = atmel_pci_probe,
34 .remove = atmel_pci_remove,
35};
36
37
38static int atmel_pci_probe(struct pci_dev *pdev,
39 const struct pci_device_id *pent)
40{
41 struct net_device *dev;
42
43 if (pci_enable_device(pdev))
44 return -ENODEV;
45
46 pci_set_master(pdev);
47
48 dev = init_atmel_card(pdev->irq, pdev->resource[1].start,
49 ATMEL_FW_TYPE_506,
50 &pdev->dev, NULL, NULL);
51 if (!dev) {
52 pci_disable_device(pdev);
53 return -ENODEV;
54 }
55
56 pci_set_drvdata(pdev, dev);
57 return 0;
58}
59
60static void atmel_pci_remove(struct pci_dev *pdev)
61{
62 stop_atmel_card(pci_get_drvdata(pdev));
63}
64
65module_pci_driver(atmel_driver);
drivers/net/wireless/broadcom/brcm80211/brcmfmac/cfg80211.c+1−1
@@ -866,7 +866,7 @@ struct wireless_dev *brcmf_apsta_add_vif(struct wiphy *wiphy, const char *name, · 865 unmodified lines
866 goto fail;866 goto fail;
867 }867 }
868 868
869 strncpy(ifp->ndev->name, name, sizeof(ifp->ndev->name) - 1);869 strscpy(ifp->ndev->name, name, sizeof(ifp->ndev->name));
870 err = brcmf_net_attach(ifp, true);870 err = brcmf_net_attach(ifp, true);
871 if (err) {871 if (err) {
872 bphy_err(drvr, "Registering netdevice failed\n");872 bphy_err(drvr, "Registering netdevice failed\n");
drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c+1−1
@@ -2334,7 +2334,7 @@ struct wireless_dev *brcmf_p2p_add_vif(struct wiphy *wiphy, const char *name, · 2333 unmodified lines
2334 goto fail;2334 goto fail;
2335 }2335 }
2336 2336
2337 strncpy(ifp->ndev->name, name, sizeof(ifp->ndev->name) - 1);2337 strscpy(ifp->ndev->name, name, sizeof(ifp->ndev->name));
2338 ifp->ndev->name_assign_type = name_assign_type;2338 ifp->ndev->name_assign_type = name_assign_type;
2339 err = brcmf_net_attach(ifp, true);2339 err = brcmf_net_attach(ifp, true);
2340 if (err) {2340 if (err) {
drivers/net/wireless/broadcom/brcm80211/brcmsmac/channel.c+3−3
@@ -341,7 +341,7 @@ struct brcms_cm_info *brcms_c_channel_mgr_attach(struct brcms_c_info *wlc) · 340 unmodified lines
341 /* store the country code for passing up as a regulatory hint */341 /* store the country code for passing up as a regulatory hint */
342 wlc_cm->world_regd = brcms_world_regd(ccode, ccode_len);342 wlc_cm->world_regd = brcms_world_regd(ccode, ccode_len);
343 if (brcms_c_country_valid(ccode))343 if (brcms_c_country_valid(ccode))
344 strncpy(wlc->pub->srom_ccode, ccode, ccode_len);344 memcpy(wlc->pub->srom_ccode, ccode, ccode_len);
345 345
346 /*346 /*
347 * If no custom world domain is found in the SROM, use the347 * If no custom world domain is found in the SROM, use the
@@ -354,10 +354,10 @@ struct brcms_cm_info *brcms_c_channel_mgr_attach(struct brcms_c_info *wlc) · 6 unmodified lines
354 }354 }
355 355
356 /* save default country for exiting 11d regulatory mode */356 /* save default country for exiting 11d regulatory mode */
357 strncpy(wlc->country_default, ccode, ccode_len);357 memcpy(wlc->country_default, ccode, ccode_len);
358 358
359 /* initialize autocountry_default to driver default */359 /* initialize autocountry_default to driver default */
360 strncpy(wlc->autocountry_default, ccode, ccode_len);360 memcpy(wlc->autocountry_default, ccode, ccode_len);
361 361
362 brcms_c_set_country(wlc_cm, wlc_cm->world_regd);362 brcms_c_set_country(wlc_cm, wlc_cm->world_regd);
363 363
drivers/net/wireless/broadcom/brcm80211/brcmsmac/dma.c+1−2
@@ -584,8 +584,7 @@ struct dma_pub *dma_attach(char *name, struct brcms_c_info *wlc, · 583 unmodified lines
584 rxextheadroom, nrxpost, rxoffset, txregbase, rxregbase);584 rxextheadroom, nrxpost, rxoffset, txregbase, rxregbase);
585 585
586 /* make a private copy of our callers name */586 /* make a private copy of our callers name */
587 strncpy(di->name, name, MAXNAMEL);587 strscpy(di->name, name, sizeof(di->name));
588 di->name[MAXNAMEL - 1] = '\0';
589 588
590 di->dmadev = core->dma_dev;589 di->dmadev = core->dma_dev;
591 590
drivers/net/wireless/broadcom/brcm80211/brcmsmac/main.c+2−2
@@ -5551,8 +5551,8 @@ int brcms_c_module_register(struct brcms_pub *pub, · 5550 unmodified lines
5551 /* find an empty entry and just add, no duplication check! */5551 /* find an empty entry and just add, no duplication check! */
5552 for (i = 0; i < BRCMS_MAXMODULES; i++) {5552 for (i = 0; i < BRCMS_MAXMODULES; i++) {
5553 if (wlc->modulecb[i].name[0] == '\0') {5553 if (wlc->modulecb[i].name[0] == '\0') {
5554 strncpy(wlc->modulecb[i].name, name,5554 strscpy(wlc->modulecb[i].name, name,
5555 sizeof(wlc->modulecb[i].name) - 1);5555 sizeof(wlc->modulecb[i].name));
5556 wlc->modulecb[i].hdl = hdl;5556 wlc->modulecb[i].hdl = hdl;
5557 wlc->modulecb[i].down_fn = d_fn;5557 wlc->modulecb[i].down_fn = d_fn;
5558 return 0;5558 return 0;
drivers/net/wireless/cisco/Kconfig+0−59
@@ -1,59 +0,0 @@
1# SPDX-License-Identifier: GPL-2.0-only
2config WLAN_VENDOR_CISCO
3 bool "Cisco devices"
4 default y
5 help
6 If you have a wireless card belonging to this class, say Y.
7
8 Note that the answer to this question doesn't directly affect the
9 kernel: saying N will just cause the configurator to skip all the
10 questions about these cards. If you say Y, you will be asked for
11 your specific card in the following questions.
12
13if WLAN_VENDOR_CISCO
14
15config AIRO
16 tristate "Cisco/Aironet 34X/35X/4500/4800 ISA and PCI cards"
17 depends on CFG80211 && (PCI || BROKEN)
18 select WIRELESS_EXT
19 select CRYPTO
20 select CRYPTO_SKCIPHER
21 select WEXT_SPY
22 select WEXT_PRIV
23 help
24 This is the standard Linux driver to support Cisco/Aironet ISA and
25 PCI 802.11 wireless cards.
26 It supports the new 802.11b cards from Cisco (Cisco 34X, Cisco 35X
27 - with or without encryption) as well as card before the Cisco
28 acquisition (Aironet 4500, Aironet 4800, Aironet 4800B).
29
30 This driver support both the standard Linux Wireless Extensions
31 and Cisco proprietary API, so both the Linux Wireless Tools and the
32 Cisco Linux utilities can be used to configure the card.
33
34 The driver can be compiled as a module and will be named "airo".
35
36config AIRO_CS
37 tristate "Cisco/Aironet 34X/35X/4500/4800 PCMCIA cards"
38 depends on CFG80211 && PCMCIA
39 select WIRELESS_EXT
40 select WEXT_SPY
41 select WEXT_PRIV
42 select CRYPTO
43 select CRYPTO_AES
44 select CRYPTO_CTR
45 help
46 This is the standard Linux driver to support Cisco/Aironet PCMCIA
47 802.11 wireless cards. This driver is the same as the Aironet
48 driver part of the Linux Pcmcia package.
49 It supports the new 802.11b cards from Cisco (Cisco 34X, Cisco 35X
50 - with or without encryption) as well as card before the Cisco
51 acquisition (Aironet 4500, Aironet 4800, Aironet 4800B). It also
52 supports OEM of Cisco such as the DELL TrueMobile 4800 and Xircom
53 802.11b cards.
54
55 This driver support both the standard Linux Wireless Extensions
56 and Cisco proprietary API, so both the Linux Wireless Tools and the
57 Cisco Linux utilities can be used to configure the card.
58
59endif # WLAN_VENDOR_CISCO
drivers/net/wireless/cisco/Makefile+0−3
@@ -1,3 +0,0 @@
1# SPDX-License-Identifier: GPL-2.0-only
2obj-$(CONFIG_AIRO) += airo.o
3obj-$(CONFIG_AIRO_CS) += airo_cs.o airo.o
drivers/net/wireless/cisco/airo.c+0−8288
@@ -1,8288 +0,0 @@
1/*======================================================================
2
3 Aironet driver for 4500 and 4800 series cards
4
5 This code is released under both the GPL version 2 and BSD licenses.
6 Either license may be used. The respective licenses are found at
7 the end of this file.
8
9 This code was developed by Benjamin Reed <breed@users.sourceforge.net>
10 including portions of which come from the Aironet PC4500
11 Developer's Reference Manual and used with permission. Copyright
12 (C) 1999 Benjamin Reed. All Rights Reserved. Permission to use
13 code in the Developer's manual was granted for this driver by
14 Aironet. Major code contributions were received from Javier Achirica
15 <achirica@users.sourceforge.net> and Jean Tourrilhes <jt@hpl.hp.com>.
16 Code was also integrated from the Cisco Aironet driver for Linux.
17 Support for MPI350 cards was added by Fabrice Bellet
18 <fabrice@bellet.info>.
19
20======================================================================*/
21
22#include <linux/err.h>
23#include <linux/init.h>
24
25#include <linux/kernel.h>
26#include <linux/module.h>
27#include <linux/proc_fs.h>
28
29#include <linux/sched.h>
30#include <linux/ptrace.h>
31#include <linux/slab.h>
32#include <linux/string.h>
33#include <linux/timer.h>
34#include <linux/interrupt.h>
35#include <linux/in.h>
36#include <linux/bitops.h>
37#include <linux/scatterlist.h>
38#include <linux/crypto.h>
39#include <linux/io.h>
40#include <asm/unaligned.h>
41
42#include <linux/netdevice.h>
43#include <linux/etherdevice.h>
44#include <linux/skbuff.h>
45#include <linux/if_arp.h>
46#include <linux/ioport.h>
47#include <linux/pci.h>
48#include <linux/uaccess.h>
49#include <linux/kthread.h>
50#include <linux/freezer.h>
51
52#include <crypto/aes.h>
53#include <crypto/skcipher.h>
54
55#include <net/cfg80211.h>
56#include <net/iw_handler.h>
57
58#include "airo.h"
59
60#define DRV_NAME "airo"
61
62#ifdef CONFIG_PCI
63static const struct pci_device_id card_ids[] = {
64 { 0x14b9, 1, PCI_ANY_ID, PCI_ANY_ID, },
65 { 0x14b9, 0x4500, PCI_ANY_ID, PCI_ANY_ID },
66 { 0x14b9, 0x4800, PCI_ANY_ID, PCI_ANY_ID, },
67 { 0x14b9, 0x0340, PCI_ANY_ID, PCI_ANY_ID, },
68 { 0x14b9, 0x0350, PCI_ANY_ID, PCI_ANY_ID, },
69 { 0x14b9, 0x5000, PCI_ANY_ID, PCI_ANY_ID, },
70 { 0x14b9, 0xa504, PCI_ANY_ID, PCI_ANY_ID, },
71 { 0, }
72};
73MODULE_DEVICE_TABLE(pci, card_ids);
74
75static int airo_pci_probe(struct pci_dev *, const struct pci_device_id *);
76static void airo_pci_remove(struct pci_dev *);
77static int __maybe_unused airo_pci_suspend(struct device *dev);
78static int __maybe_unused airo_pci_resume(struct device *dev);
79
80static SIMPLE_DEV_PM_OPS(airo_pci_pm_ops,
81 airo_pci_suspend,
82 airo_pci_resume);
83
84static struct pci_driver airo_driver = {
85 .name = DRV_NAME,
86 .id_table = card_ids,
87 .probe = airo_pci_probe,
88 .remove = airo_pci_remove,
89 .driver.pm = &airo_pci_pm_ops,
90};
91#endif /* CONFIG_PCI */
92
93/* Include Wireless Extension definition and check version - Jean II */
94#include <linux/wireless.h>
95#define WIRELESS_SPY /* enable iwspy support */
96
97#define CISCO_EXT /* enable Cisco extensions */
98#ifdef CISCO_EXT
99#include <linux/delay.h>
100#endif
101
102/* Hack to do some power saving */
103#define POWER_ON_DOWN
104
105/* As you can see this list is HUGH!
106 I really don't know what a lot of these counts are about, but they
107 are all here for completeness. If the IGNLABEL macro is put in
108 infront of the label, that statistic will not be included in the list
109 of statistics in the /proc filesystem */
110
111#define IGNLABEL(comment) NULL
112static const char *statsLabels[] = {
113 "RxOverrun",
114 IGNLABEL("RxPlcpCrcErr"),
115 IGNLABEL("RxPlcpFormatErr"),
116 IGNLABEL("RxPlcpLengthErr"),
117 "RxMacCrcErr",
118 "RxMacCrcOk",
119 "RxWepErr",
120 "RxWepOk",
121 "RetryLong",
122 "RetryShort",
123 "MaxRetries",
124 "NoAck",
125 "NoCts",
126 "RxAck",
127 "RxCts",
128 "TxAck",
129 "TxRts",
130 "TxCts",
131 "TxMc",
132 "TxBc",
133 "TxUcFrags",
134 "TxUcPackets",
135 "TxBeacon",
136 "RxBeacon",
137 "TxSinColl",
138 "TxMulColl",
139 "DefersNo",
140 "DefersProt",
141 "DefersEngy",
142 "DupFram",
143 "RxFragDisc",
144 "TxAged",
145 "RxAged",
146 "LostSync-MaxRetry",
147 "LostSync-MissedBeacons",
148 "LostSync-ArlExceeded",
149 "LostSync-Deauth",
150 "LostSync-Disassoced",
151 "LostSync-TsfTiming",
152 "HostTxMc",
153 "HostTxBc",
154 "HostTxUc",
155 "HostTxFail",
156 "HostRxMc",
157 "HostRxBc",
158 "HostRxUc",
159 "HostRxDiscard",
160 IGNLABEL("HmacTxMc"),
161 IGNLABEL("HmacTxBc"),
162 IGNLABEL("HmacTxUc"),
163 IGNLABEL("HmacTxFail"),
164 IGNLABEL("HmacRxMc"),
165 IGNLABEL("HmacRxBc"),
166 IGNLABEL("HmacRxUc"),
167 IGNLABEL("HmacRxDiscard"),
168 IGNLABEL("HmacRxAccepted"),
169 "SsidMismatch",
170 "ApMismatch",
171 "RatesMismatch",
172 "AuthReject",
173 "AuthTimeout",
174 "AssocReject",
175 "AssocTimeout",
176 IGNLABEL("ReasonOutsideTable"),
177 IGNLABEL("ReasonStatus1"),
178 IGNLABEL("ReasonStatus2"),
179 IGNLABEL("ReasonStatus3"),
180 IGNLABEL("ReasonStatus4"),
181 IGNLABEL("ReasonStatus5"),
182 IGNLABEL("ReasonStatus6"),
183 IGNLABEL("ReasonStatus7"),
184 IGNLABEL("ReasonStatus8"),
185 IGNLABEL("ReasonStatus9"),
186 IGNLABEL("ReasonStatus10"),
187 IGNLABEL("ReasonStatus11"),
188 IGNLABEL("ReasonStatus12"),
189 IGNLABEL("ReasonStatus13"),
190 IGNLABEL("ReasonStatus14"),
191 IGNLABEL("ReasonStatus15"),
192 IGNLABEL("ReasonStatus16"),
193 IGNLABEL("ReasonStatus17"),
194 IGNLABEL("ReasonStatus18"),
195 IGNLABEL("ReasonStatus19"),
196 "RxMan",
197 "TxMan",
198 "RxRefresh",
199 "TxRefresh",
200 "RxPoll",
201 "TxPoll",
202 "HostRetries",
203 "LostSync-HostReq",
204 "HostTxBytes",
205 "HostRxBytes",
206 "ElapsedUsec",
207 "ElapsedSec",
208 "LostSyncBetterAP",
209 "PrivacyMismatch",
210 "Jammed",
211 "DiscRxNotWepped",
212 "PhyEleMismatch",
213 (char*)-1 };
214#ifndef RUN_AT
215#define RUN_AT(x) (jiffies+(x))
216#endif
217
218
219/* These variables are for insmod, since it seems that the rates
220 can only be set in setup_card. Rates should be a comma separated
221 (no spaces) list of rates (up to 8). */
222
223static int rates[8];
224static char *ssids[3];
225
226static int io[4];
227static int irq[4];
228
229static
230int maxencrypt /* = 0 */; /* The highest rate that the card can encrypt at.
231 0 means no limit. For old cards this was 4 */
232
233static int auto_wep /* = 0 */; /* If set, it tries to figure out the wep mode */
234static int aux_bap /* = 0 */; /* Checks to see if the aux ports are needed to read
235 the bap, needed on some older cards and buses. */
236static int adhoc;
237
238static int probe = 1;
239
240static kuid_t proc_kuid;
241static int proc_uid /* = 0 */;
242
243static kgid_t proc_kgid;
244static int proc_gid /* = 0 */;
245
246static int airo_perm = 0555;
247
248static int proc_perm = 0644;
249
250MODULE_AUTHOR("Benjamin Reed");
251MODULE_DESCRIPTION("Support for Cisco/Aironet 802.11 wireless ethernet cards. "
252 "Direct support for ISA/PCI/MPI cards and support for PCMCIA when used with airo_cs.");
253MODULE_LICENSE("Dual BSD/GPL");
254module_param_hw_array(io, int, ioport, NULL, 0);
255module_param_hw_array(irq, int, irq, NULL, 0);
256module_param_array(rates, int, NULL, 0);
257module_param_array(ssids, charp, NULL, 0);
258module_param(auto_wep, int, 0);
259MODULE_PARM_DESC(auto_wep,
260 "If non-zero, the driver will keep looping through the authentication options until an association is made. "
261 "The value of auto_wep is number of the wep keys to check. "
262 "A value of 2 will try using the key at index 0 and index 1.");
263module_param(aux_bap, int, 0);
264MODULE_PARM_DESC(aux_bap,
265 "If non-zero, the driver will switch into a mode that seems to work better for older cards with some older buses. "
266 "Before switching it checks that the switch is needed.");
267module_param(maxencrypt, int, 0);
268MODULE_PARM_DESC(maxencrypt,
269 "The maximum speed that the card can do encryption. "
270 "Units are in 512kbs. "
271 "Zero (default) means there is no limit. "
272 "Older cards used to be limited to 2mbs (4).");
273module_param(adhoc, int, 0);
274MODULE_PARM_DESC(adhoc, "If non-zero, the card will start in adhoc mode.");
275module_param(probe, int, 0);
276MODULE_PARM_DESC(probe, "If zero, the driver won't start the card.");
277
278module_param(proc_uid, int, 0);
279MODULE_PARM_DESC(proc_uid, "The uid that the /proc files will belong to.");
280module_param(proc_gid, int, 0);
281MODULE_PARM_DESC(proc_gid, "The gid that the /proc files will belong to.");
282module_param(airo_perm, int, 0);
283MODULE_PARM_DESC(airo_perm, "The permission bits of /proc/[driver/]aironet.");
284module_param(proc_perm, int, 0);
285MODULE_PARM_DESC(proc_perm, "The permission bits of the files in /proc");
286
287/* This is a kind of sloppy hack to get this information to OUT4500 and
288 IN4500. I would be extremely interested in the situation where this
289 doesn't work though!!! */
290static int do8bitIO /* = 0 */;
291
292/* Return codes */
293#define SUCCESS 0
294#define ERROR -1
295#define NO_PACKET -2
296
297/* Commands */
298#define NOP2 0x0000
299#define MAC_ENABLE 0x0001
300#define MAC_DISABLE 0x0002
301#define CMD_LOSE_SYNC 0x0003 /* Not sure what this does... */
302#define CMD_SOFTRESET 0x0004
303#define HOSTSLEEP 0x0005
304#define CMD_MAGIC_PKT 0x0006
305#define CMD_SETWAKEMASK 0x0007
306#define CMD_READCFG 0x0008
307#define CMD_SETMODE 0x0009
308#define CMD_ALLOCATETX 0x000a
309#define CMD_TRANSMIT 0x000b
310#define CMD_DEALLOCATETX 0x000c
311#define NOP 0x0010
312#define CMD_WORKAROUND 0x0011
313#define CMD_ALLOCATEAUX 0x0020
314#define CMD_ACCESS 0x0021
315#define CMD_PCIBAP 0x0022
316#define CMD_PCIAUX 0x0023
317#define CMD_ALLOCBUF 0x0028
318#define CMD_GETTLV 0x0029
319#define CMD_PUTTLV 0x002a
320#define CMD_DELTLV 0x002b
321#define CMD_FINDNEXTTLV 0x002c
322#define CMD_PSPNODES 0x0030
323#define CMD_SETCW 0x0031
324#define CMD_SETPCF 0x0032
325#define CMD_SETPHYREG 0x003e
326#define CMD_TXTEST 0x003f
327#define MAC_ENABLETX 0x0101
328#define CMD_LISTBSS 0x0103
329#define CMD_SAVECFG 0x0108
330#define CMD_ENABLEAUX 0x0111
331#define CMD_WRITERID 0x0121
332#define CMD_USEPSPNODES 0x0130
333#define MAC_ENABLERX 0x0201
334
335/* Command errors */
336#define ERROR_QUALIF 0x00
337#define ERROR_ILLCMD 0x01
338#define ERROR_ILLFMT 0x02
339#define ERROR_INVFID 0x03
340#define ERROR_INVRID 0x04
341#define ERROR_LARGE 0x05
342#define ERROR_NDISABL 0x06
343#define ERROR_ALLOCBSY 0x07
344#define ERROR_NORD 0x0B
345#define ERROR_NOWR 0x0C
346#define ERROR_INVFIDTX 0x0D
347#define ERROR_TESTACT 0x0E
348#define ERROR_TAGNFND 0x12
349#define ERROR_DECODE 0x20
350#define ERROR_DESCUNAV 0x21
351#define ERROR_BADLEN 0x22
352#define ERROR_MODE 0x80
353#define ERROR_HOP 0x81
354#define ERROR_BINTER 0x82
355#define ERROR_RXMODE 0x83
356#define ERROR_MACADDR 0x84
357#define ERROR_RATES 0x85
358#define ERROR_ORDER 0x86
359#define ERROR_SCAN 0x87
360#define ERROR_AUTH 0x88
361#define ERROR_PSMODE 0x89
362#define ERROR_RTYPE 0x8A
363#define ERROR_DIVER 0x8B
364#define ERROR_SSID 0x8C
365#define ERROR_APLIST 0x8D
366#define ERROR_AUTOWAKE 0x8E
367#define ERROR_LEAP 0x8F
368
369/* Registers */
370#define COMMAND 0x00
371#define PARAM0 0x02
372#define PARAM1 0x04
373#define PARAM2 0x06
374#define STATUS 0x08
375#define RESP0 0x0a
376#define RESP1 0x0c
377#define RESP2 0x0e
378#define LINKSTAT 0x10
379#define SELECT0 0x18
380#define OFFSET0 0x1c
381#define RXFID 0x20
382#define TXALLOCFID 0x22
383#define TXCOMPLFID 0x24
384#define DATA0 0x36
385#define EVSTAT 0x30
386#define EVINTEN 0x32
387#define EVACK 0x34
388#define SWS0 0x28
389#define SWS1 0x2a
390#define SWS2 0x2c
391#define SWS3 0x2e
392#define AUXPAGE 0x3A
393#define AUXOFF 0x3C
394#define AUXDATA 0x3E
395
396#define FID_TX 1
397#define FID_RX 2
398/* Offset into aux memory for descriptors */
399#define AUX_OFFSET 0x800
400/* Size of allocated packets */
401#define PKTSIZE 1840
402#define RIDSIZE 2048
403/* Size of the transmit queue */
404#define MAXTXQ 64
405
406/* BAP selectors */
407#define BAP0 0 /* Used for receiving packets */
408#define BAP1 2 /* Used for xmiting packets and working with RIDS */
409
410/* Flags */
411#define COMMAND_BUSY 0x8000
412
413#define BAP_BUSY 0x8000
414#define BAP_ERR 0x4000
415#define BAP_DONE 0x2000
416
417#define PROMISC 0xffff
418#define NOPROMISC 0x0000
419
420#define EV_CMD 0x10
421#define EV_CLEARCOMMANDBUSY 0x4000
422#define EV_RX 0x01
423#define EV_TX 0x02
424#define EV_TXEXC 0x04
425#define EV_ALLOC 0x08
426#define EV_LINK 0x80
427#define EV_AWAKE 0x100
428#define EV_TXCPY 0x400
429#define EV_UNKNOWN 0x800
430#define EV_MIC 0x1000 /* Message Integrity Check Interrupt */
431#define EV_AWAKEN 0x2000
432#define STATUS_INTS (EV_AWAKE|EV_LINK|EV_TXEXC|EV_TX|EV_TXCPY|EV_RX|EV_MIC)
433
434#ifdef CHECK_UNKNOWN_INTS
435#define IGNORE_INTS (EV_CMD | EV_UNKNOWN)
436#else
437#define IGNORE_INTS (~STATUS_INTS)
438#endif
439
440/* RID TYPES */
441#define RID_RW 0x20
442
443/* The RIDs */
444#define RID_CAPABILITIES 0xFF00
445#define RID_APINFO 0xFF01
446#define RID_RADIOINFO 0xFF02
447#define RID_UNKNOWN3 0xFF03
448#define RID_RSSI 0xFF04
449#define RID_CONFIG 0xFF10
450#define RID_SSID 0xFF11
451#define RID_APLIST 0xFF12
452#define RID_DRVNAME 0xFF13
453#define RID_ETHERENCAP 0xFF14
454#define RID_WEP_TEMP 0xFF15
455#define RID_WEP_PERM 0xFF16
456#define RID_MODULATION 0xFF17
457#define RID_OPTIONS 0xFF18
458#define RID_ACTUALCONFIG 0xFF20 /*readonly*/
459#define RID_FACTORYCONFIG 0xFF21
460#define RID_UNKNOWN22 0xFF22
461#define RID_LEAPUSERNAME 0xFF23
462#define RID_LEAPPASSWORD 0xFF24
463#define RID_STATUS 0xFF50
464#define RID_BEACON_HST 0xFF51
465#define RID_BUSY_HST 0xFF52
466#define RID_RETRIES_HST 0xFF53
467#define RID_UNKNOWN54 0xFF54
468#define RID_UNKNOWN55 0xFF55
469#define RID_UNKNOWN56 0xFF56
470#define RID_MIC 0xFF57
471#define RID_STATS16 0xFF60
472#define RID_STATS16DELTA 0xFF61
473#define RID_STATS16DELTACLEAR 0xFF62
474#define RID_STATS 0xFF68
475#define RID_STATSDELTA 0xFF69
476#define RID_STATSDELTACLEAR 0xFF6A
477#define RID_ECHOTEST_RID 0xFF70
478#define RID_ECHOTEST_RESULTS 0xFF71
479#define RID_BSSLISTFIRST 0xFF72
480#define RID_BSSLISTNEXT 0xFF73
481#define RID_WPA_BSSLISTFIRST 0xFF74
482#define RID_WPA_BSSLISTNEXT 0xFF75
483
484typedef struct {
485 u16 cmd;
486 u16 parm0;
487 u16 parm1;
488 u16 parm2;
489} Cmd;
490
491typedef struct {
492 u16 status;
493 u16 rsp0;
494 u16 rsp1;
495 u16 rsp2;
496} Resp;
497
498/*
499 * Rids and endian-ness: The Rids will always be in cpu endian, since
500 * this all the patches from the big-endian guys end up doing that.
501 * so all rid access should use the read/writeXXXRid routines.
502 */
503
504/* This structure came from an email sent to me from an engineer at
505 aironet for inclusion into this driver */
506typedef struct WepKeyRid WepKeyRid;
507struct WepKeyRid {
508 __le16 len;
509 __le16 kindex;
510 u8 mac[ETH_ALEN];
511 __le16 klen;
512 u8 key[16];
513} __packed;
514
515/* These structures are from the Aironet's PC4500 Developers Manual */
516typedef struct Ssid Ssid;
517struct Ssid {
518 __le16 len;
519 u8 ssid[32];
520} __packed;
521
522typedef struct SsidRid SsidRid;
523struct SsidRid {
524 __le16 len;
525 Ssid ssids[3];
526} __packed;
527
528typedef struct ModulationRid ModulationRid;
529struct ModulationRid {
530 __le16 len;
531 __le16 modulation;
532#define MOD_DEFAULT cpu_to_le16(0)
533#define MOD_CCK cpu_to_le16(1)
534#define MOD_MOK cpu_to_le16(2)
535} __packed;
536
537typedef struct ConfigRid ConfigRid;
538struct ConfigRid {
539 __le16 len; /* sizeof(ConfigRid) */
540 __le16 opmode; /* operating mode */
541#define MODE_STA_IBSS cpu_to_le16(0)
542#define MODE_STA_ESS cpu_to_le16(1)
543#define MODE_AP cpu_to_le16(2)
544#define MODE_AP_RPTR cpu_to_le16(3)
545#define MODE_CFG_MASK cpu_to_le16(0xff)
546#define MODE_ETHERNET_HOST cpu_to_le16(0<<8) /* rx payloads converted */
547#define MODE_LLC_HOST cpu_to_le16(1<<8) /* rx payloads left as is */
548#define MODE_AIRONET_EXTEND cpu_to_le16(1<<9) /* enable Aironet extensions */
549#define MODE_AP_INTERFACE cpu_to_le16(1<<10) /* enable ap interface extensions */
550#define MODE_ANTENNA_ALIGN cpu_to_le16(1<<11) /* enable antenna alignment */
551#define MODE_ETHER_LLC cpu_to_le16(1<<12) /* enable ethernet LLC */
552#define MODE_LEAF_NODE cpu_to_le16(1<<13) /* enable leaf node bridge */
553#define MODE_CF_POLLABLE cpu_to_le16(1<<14) /* enable CF pollable */
554#define MODE_MIC cpu_to_le16(1<<15) /* enable MIC */
555 __le16 rmode; /* receive mode */
556#define RXMODE_BC_MC_ADDR cpu_to_le16(0)
557#define RXMODE_BC_ADDR cpu_to_le16(1) /* ignore multicasts */
558#define RXMODE_ADDR cpu_to_le16(2) /* ignore multicast and broadcast */
559#define RXMODE_RFMON cpu_to_le16(3) /* wireless monitor mode */
560#define RXMODE_RFMON_ANYBSS cpu_to_le16(4)
561#define RXMODE_LANMON cpu_to_le16(5) /* lan style monitor -- data packets only */
562#define RXMODE_MASK cpu_to_le16(255)
563#define RXMODE_DISABLE_802_3_HEADER cpu_to_le16(1<<8) /* disables 802.3 header on rx */
564#define RXMODE_FULL_MASK (RXMODE_MASK | RXMODE_DISABLE_802_3_HEADER)
565#define RXMODE_NORMALIZED_RSSI cpu_to_le16(1<<9) /* return normalized RSSI */
566 __le16 fragThresh;
567 __le16 rtsThres;
568 u8 macAddr[ETH_ALEN];
569 u8 rates[8];
570 __le16 shortRetryLimit;
571 __le16 longRetryLimit;
572 __le16 txLifetime; /* in kusec */
573 __le16 rxLifetime; /* in kusec */
574 __le16 stationary;
575 __le16 ordering;
576 __le16 u16deviceType; /* for overriding device type */
577 __le16 cfpRate;
578 __le16 cfpDuration;
579 __le16 _reserved1[3];
580 /*---------- Scanning/Associating ----------*/
581 __le16 scanMode;
582#define SCANMODE_ACTIVE cpu_to_le16(0)
583#define SCANMODE_PASSIVE cpu_to_le16(1)
584#define SCANMODE_AIROSCAN cpu_to_le16(2)
585 __le16 probeDelay; /* in kusec */
586 __le16 probeEnergyTimeout; /* in kusec */
587 __le16 probeResponseTimeout;
588 __le16 beaconListenTimeout;
589 __le16 joinNetTimeout;
590 __le16 authTimeout;
591 __le16 authType;
592#define AUTH_OPEN cpu_to_le16(0x1)
593#define AUTH_ENCRYPT cpu_to_le16(0x101)
594#define AUTH_SHAREDKEY cpu_to_le16(0x102)
595#define AUTH_ALLOW_UNENCRYPTED cpu_to_le16(0x200)
596 __le16 associationTimeout;
597 __le16 specifiedApTimeout;
598 __le16 offlineScanInterval;
599 __le16 offlineScanDuration;
600 __le16 linkLossDelay;
601 __le16 maxBeaconLostTime;
602 __le16 refreshInterval;
603#define DISABLE_REFRESH cpu_to_le16(0xFFFF)
604 __le16 _reserved1a[1];
605 /*---------- Power save operation ----------*/
606 __le16 powerSaveMode;
607#define POWERSAVE_CAM cpu_to_le16(0)
608#define POWERSAVE_PSP cpu_to_le16(1)
609#define POWERSAVE_PSPCAM cpu_to_le16(2)
610 __le16 sleepForDtims;
611 __le16 listenInterval;
612 __le16 fastListenInterval;
613 __le16 listenDecay;
614 __le16 fastListenDelay;
615 __le16 _reserved2[2];
616 /*---------- Ap/Ibss config items ----------*/
617 __le16 beaconPeriod;
618 __le16 atimDuration;
619 __le16 hopPeriod;
620 __le16 channelSet;
621 __le16 channel;
622 __le16 dtimPeriod;
623 __le16 bridgeDistance;
624 __le16 radioID;
625 /*---------- Radio configuration ----------*/
626 __le16 radioType;
627#define RADIOTYPE_DEFAULT cpu_to_le16(0)
628#define RADIOTYPE_802_11 cpu_to_le16(1)
629#define RADIOTYPE_LEGACY cpu_to_le16(2)
630 u8 rxDiversity;
631 u8 txDiversity;
632 __le16 txPower;
633#define TXPOWER_DEFAULT 0
634 __le16 rssiThreshold;
635#define RSSI_DEFAULT 0
636 __le16 modulation;
637#define PREAMBLE_AUTO cpu_to_le16(0)
638#define PREAMBLE_LONG cpu_to_le16(1)
639#define PREAMBLE_SHORT cpu_to_le16(2)
640 __le16 preamble;
641 __le16 homeProduct;
642 __le16 radioSpecific;
643 /*---------- Aironet Extensions ----------*/
644 u8 nodeName[16];
645 __le16 arlThreshold;
646 __le16 arlDecay;
647 __le16 arlDelay;
648 __le16 _reserved4[1];
649 /*---------- Aironet Extensions ----------*/
650 u8 magicAction;
651#define MAGIC_ACTION_STSCHG 1
652#define MAGIC_ACTION_RESUME 2
653#define MAGIC_IGNORE_MCAST (1<<8)
654#define MAGIC_IGNORE_BCAST (1<<9)
655#define MAGIC_SWITCH_TO_PSP (0<<10)
656#define MAGIC_STAY_IN_CAM (1<<10)
657 u8 magicControl;
658 __le16 autoWake;
659} __packed;
660
661typedef struct StatusRid StatusRid;
662struct StatusRid {
663 __le16 len;
664 u8 mac[ETH_ALEN];
665 __le16 mode;
666 __le16 errorCode;
667 __le16 sigQuality;
668 __le16 SSIDlen;
669 char SSID[32];
670 char apName[16];
671 u8 bssid[4][ETH_ALEN];
672 __le16 beaconPeriod;
673 __le16 dimPeriod;
674 __le16 atimDuration;
675 __le16 hopPeriod;
676 __le16 channelSet;
677 __le16 channel;
678 __le16 hopsToBackbone;
679 __le16 apTotalLoad;
680 __le16 generatedLoad;
681 __le16 accumulatedArl;
682 __le16 signalQuality;
683 __le16 currentXmitRate;
684 __le16 apDevExtensions;
685 __le16 normalizedSignalStrength;
686 __le16 shortPreamble;
687 u8 apIP[4];
688 u8 noisePercent; /* Noise percent in last second */
689 u8 noisedBm; /* Noise dBm in last second */
690 u8 noiseAvePercent; /* Noise percent in last minute */
691 u8 noiseAvedBm; /* Noise dBm in last minute */
692 u8 noiseMaxPercent; /* Highest noise percent in last minute */
693 u8 noiseMaxdBm; /* Highest noise dbm in last minute */
694 __le16 load;
695 u8 carrier[4];
696 __le16 assocStatus;
697#define STAT_NOPACKETS 0
698#define STAT_NOCARRIERSET 10
699#define STAT_GOTCARRIERSET 11
700#define STAT_WRONGSSID 20
701#define STAT_BADCHANNEL 25
702#define STAT_BADBITRATES 30
703#define STAT_BADPRIVACY 35
704#define STAT_APFOUND 40
705#define STAT_APREJECTED 50
706#define STAT_AUTHENTICATING 60
707#define STAT_DEAUTHENTICATED 61
708#define STAT_AUTHTIMEOUT 62
709#define STAT_ASSOCIATING 70
710#define STAT_DEASSOCIATED 71
711#define STAT_ASSOCTIMEOUT 72
712#define STAT_NOTAIROAP 73
713#define STAT_ASSOCIATED 80
714#define STAT_LEAPING 90
715#define STAT_LEAPFAILED 91
716#define STAT_LEAPTIMEDOUT 92
717#define STAT_LEAPCOMPLETE 93
718} __packed;
719
720typedef struct StatsRid StatsRid;
721struct StatsRid {
722 __le16 len;
723 __le16 spacer;
724 __le32 vals[100];
725} __packed;
726
727typedef struct APListRid APListRid;
728struct APListRid {
729 __le16 len;
730 u8 ap[4][ETH_ALEN];
731} __packed;
732
733typedef struct CapabilityRid CapabilityRid;
734struct CapabilityRid {
735 __le16 len;
736 char oui[3];
737 char zero;
738 __le16 prodNum;
739 char manName[32];
740 char prodName[16];
741 char prodVer[8];
742 char factoryAddr[ETH_ALEN];
743 char aironetAddr[ETH_ALEN];
744 __le16 radioType;
745 __le16 country;
746 char callid[ETH_ALEN];
747 char supportedRates[8];
748 char rxDiversity;
749 char txDiversity;
750 __le16 txPowerLevels[8];
751 __le16 hardVer;
752 __le16 hardCap;
753 __le16 tempRange;
754 __le16 softVer;
755 __le16 softSubVer;
756 __le16 interfaceVer;
757 __le16 softCap;
758 __le16 bootBlockVer;
759 __le16 requiredHard;
760 __le16 extSoftCap;
761} __packed;
762
763/* Only present on firmware >= 5.30.17 */
764typedef struct BSSListRidExtra BSSListRidExtra;
765struct BSSListRidExtra {
766 __le16 unknown[4];
767 u8 fixed[12]; /* WLAN management frame */
768 u8 iep[624];
769} __packed;
770
771typedef struct BSSListRid BSSListRid;
772struct BSSListRid {
773 __le16 len;
774 __le16 index; /* First is 0 and 0xffff means end of list */
775#define RADIO_FH 1 /* Frequency hopping radio type */
776#define RADIO_DS 2 /* Direct sequence radio type */
777#define RADIO_TMA 4 /* Proprietary radio used in old cards (2500) */
778 __le16 radioType;
779 u8 bssid[ETH_ALEN]; /* Mac address of the BSS */
780 u8 zero;
781 u8 ssidLen;
782 u8 ssid[32];
783 __le16 dBm;
784#define CAP_ESS cpu_to_le16(1<<0)
785#define CAP_IBSS cpu_to_le16(1<<1)
786#define CAP_PRIVACY cpu_to_le16(1<<4)
787#define CAP_SHORTHDR cpu_to_le16(1<<5)
788 __le16 cap;
789 __le16 beaconInterval;
790 u8 rates[8]; /* Same as rates for config rid */
791 struct { /* For frequency hopping only */
792 __le16 dwell;
793 u8 hopSet;
794 u8 hopPattern;
795 u8 hopIndex;
796 u8 fill;
797 } fh;
798 __le16 dsChannel;
799 __le16 atimWindow;
800
801 /* Only present on firmware >= 5.30.17 */
802 BSSListRidExtra extra;
803} __packed;
804
805typedef struct {
806 BSSListRid bss;
807 struct list_head list;
808} BSSListElement;
809
810typedef struct tdsRssiEntry tdsRssiEntry;
811struct tdsRssiEntry {
812 u8 rssipct;
813 u8 rssidBm;
814} __packed;
815
816typedef struct tdsRssiRid tdsRssiRid;
817struct tdsRssiRid {
818 u16 len;
819 tdsRssiEntry x[256];
820} __packed;
821
822typedef struct MICRid MICRid;
823struct MICRid {
824 __le16 len;
825 __le16 state;
826 __le16 multicastValid;
827 u8 multicast[16];
828 __le16 unicastValid;
829 u8 unicast[16];
830} __packed;
831
832typedef struct MICBuffer MICBuffer;
833struct MICBuffer {
834 __be16 typelen;
835
836 union {
837 u8 snap[8];
838 struct {
839 u8 dsap;
840 u8 ssap;
841 u8 control;
842 u8 orgcode[3];
843 u8 fieldtype[2];
844 } llc;
845 } u;
846 __be32 mic;
847 __be32 seq;
848} __packed;
849
850typedef struct {
851 u8 da[ETH_ALEN];
852 u8 sa[ETH_ALEN];
853} etherHead;
854
855#define TXCTL_TXOK (1<<1) /* report if tx is ok */
856#define TXCTL_TXEX (1<<2) /* report if tx fails */
857#define TXCTL_802_3 (0<<3) /* 802.3 packet */
858#define TXCTL_802_11 (1<<3) /* 802.11 mac packet */
859#define TXCTL_ETHERNET (0<<4) /* payload has ethertype */
860#define TXCTL_LLC (1<<4) /* payload is llc */
861#define TXCTL_RELEASE (0<<5) /* release after completion */
862#define TXCTL_NORELEASE (1<<5) /* on completion returns to host */
863
864#define BUSY_FID 0x10000
865
866#ifdef CISCO_EXT
867#define AIROMAGIC 0xa55a
868/* Warning : SIOCDEVPRIVATE may disapear during 2.5.X - Jean II */
869#ifdef SIOCIWFIRSTPRIV
870#ifdef SIOCDEVPRIVATE
871#define AIROOLDIOCTL SIOCDEVPRIVATE
872#define AIROOLDIDIFC AIROOLDIOCTL + 1
873#endif /* SIOCDEVPRIVATE */
874#else /* SIOCIWFIRSTPRIV */
875#define SIOCIWFIRSTPRIV SIOCDEVPRIVATE
876#endif /* SIOCIWFIRSTPRIV */
877/* This may be wrong. When using the new SIOCIWFIRSTPRIV range, we probably
878 * should use only "GET" ioctls (last bit set to 1). "SET" ioctls are root
879 * only and don't return the modified struct ifreq to the application which
880 * is usually a problem. - Jean II */
881#define AIROIOCTL SIOCIWFIRSTPRIV
882#define AIROIDIFC AIROIOCTL + 1
883
884/* Ioctl constants to be used in airo_ioctl.command */
885
886#define AIROGCAP 0 // Capability rid
887#define AIROGCFG 1 // USED A LOT
888#define AIROGSLIST 2 // System ID list
889#define AIROGVLIST 3 // List of specified AP's
890#define AIROGDRVNAM 4 // NOTUSED
891#define AIROGEHTENC 5 // NOTUSED
892#define AIROGWEPKTMP 6
893#define AIROGWEPKNV 7
894#define AIROGSTAT 8
895#define AIROGSTATSC32 9
896#define AIROGSTATSD32 10
897#define AIROGMICRID 11
898#define AIROGMICSTATS 12
899#define AIROGFLAGS 13
900#define AIROGID 14
901#define AIRORRID 15
902#define AIRORSWVERSION 17
903
904/* Leave gap of 40 commands after AIROGSTATSD32 for future */
905
906#define AIROPCAP AIROGSTATSD32 + 40
907#define AIROPVLIST AIROPCAP + 1
908#define AIROPSLIST AIROPVLIST + 1
909#define AIROPCFG AIROPSLIST + 1
910#define AIROPSIDS AIROPCFG + 1
911#define AIROPAPLIST AIROPSIDS + 1
912#define AIROPMACON AIROPAPLIST + 1 /* Enable mac */
913#define AIROPMACOFF AIROPMACON + 1 /* Disable mac */
914#define AIROPSTCLR AIROPMACOFF + 1
915#define AIROPWEPKEY AIROPSTCLR + 1
916#define AIROPWEPKEYNV AIROPWEPKEY + 1
917#define AIROPLEAPPWD AIROPWEPKEYNV + 1
918#define AIROPLEAPUSR AIROPLEAPPWD + 1
919
920/* Flash codes */
921
922#define AIROFLSHRST AIROPWEPKEYNV + 40
923#define AIROFLSHGCHR AIROFLSHRST + 1
924#define AIROFLSHSTFL AIROFLSHGCHR + 1
925#define AIROFLSHPCHR AIROFLSHSTFL + 1
926#define AIROFLPUTBUF AIROFLSHPCHR + 1
927#define AIRORESTART AIROFLPUTBUF + 1
928
929#define FLASHSIZE 32768
930#define AUXMEMSIZE (256 * 1024)
931
932typedef struct aironet_ioctl {
933 unsigned short command; // What to do
934 unsigned short len; // Len of data
935 unsigned short ridnum; // rid number
936 unsigned char __user *data; // d-data
937} aironet_ioctl;
938
939static const char swversion[] = "2.1";
940#endif /* CISCO_EXT */
941
942#define NUM_MODULES 2
943#define MIC_MSGLEN_MAX 2400
944#define EMMH32_MSGLEN_MAX MIC_MSGLEN_MAX
945#define AIRO_DEF_MTU 2312
946
947typedef struct {
948 u32 size; // size
949 u8 enabled; // MIC enabled or not
950 u32 rxSuccess; // successful packets received
951 u32 rxIncorrectMIC; // pkts dropped due to incorrect MIC comparison
952 u32 rxNotMICed; // pkts dropped due to not being MIC'd
953 u32 rxMICPlummed; // pkts dropped due to not having a MIC plummed
954 u32 rxWrongSequence; // pkts dropped due to sequence number violation
955 u32 reserve[32];
956} mic_statistics;
957
958typedef struct {
959 __be32 coeff[((EMMH32_MSGLEN_MAX)+3)>>2];
960 u64 accum; // accumulated mic, reduced to u32 in final()
961 int position; // current position (byte offset) in message
962 union {
963 u8 d8[4];
964 __be32 d32;
965 } part; // saves partial message word across update() calls
966} emmh32_context;
967
968typedef struct {
969 emmh32_context seed; // Context - the seed
970 u32 rx; // Received sequence number
971 u32 tx; // Tx sequence number
972 u32 window; // Start of window
973 u8 valid; // Flag to say if context is valid or not
974 u8 key[16];
975} miccntx;
976
977typedef struct {
978 miccntx mCtx; // Multicast context
979 miccntx uCtx; // Unicast context
980} mic_module;
981
982typedef struct {
983 unsigned int rid: 16;
984 unsigned int len: 15;
985 unsigned int valid: 1;
986 dma_addr_t host_addr;
987} Rid;
988
989typedef struct {
990 unsigned int offset: 15;
991 unsigned int eoc: 1;
992 unsigned int len: 15;
993 unsigned int valid: 1;
994 dma_addr_t host_addr;
995} TxFid;
996
997struct rx_hdr {
998 __le16 status, len;
999 u8 rssi[2];
1000 u8 rate;
1001 u8 freq;
1002 __le16 tmp[4];
1003} __packed;
1004
1005typedef struct {
1006 unsigned int ctl: 15;
1007 unsigned int rdy: 1;
1008 unsigned int len: 15;
1009 unsigned int valid: 1;
1010 dma_addr_t host_addr;
1011} RxFid;
1012
1013/*
1014 * Host receive descriptor
1015 */
1016typedef struct {
1017 unsigned char __iomem *card_ram_off; /* offset into card memory of the
1018 desc */
1019 RxFid rx_desc; /* card receive descriptor */
1020 char *virtual_host_addr; /* virtual address of host receive
1021 buffer */
1022 int pending;
1023} HostRxDesc;
1024
1025/*
1026 * Host transmit descriptor
1027 */
1028typedef struct {
1029 unsigned char __iomem *card_ram_off; /* offset into card memory of the
1030 desc */
1031 TxFid tx_desc; /* card transmit descriptor */
1032 char *virtual_host_addr; /* virtual address of host receive
1033 buffer */
1034 int pending;
1035} HostTxDesc;
1036
1037/*
1038 * Host RID descriptor
1039 */
1040typedef struct {
1041 unsigned char __iomem *card_ram_off; /* offset into card memory of the
1042 descriptor */
1043 Rid rid_desc; /* card RID descriptor */
1044 char *virtual_host_addr; /* virtual address of host receive
1045 buffer */
1046} HostRidDesc;
1047
1048typedef struct {
1049 u16 sw0;
1050 u16 sw1;
1051 u16 status;
1052 u16 len;
1053#define HOST_SET (1 << 0)
1054#define HOST_INT_TX (1 << 1) /* Interrupt on successful TX */
1055#define HOST_INT_TXERR (1 << 2) /* Interrupt on unseccessful TX */
1056#define HOST_LCC_PAYLOAD (1 << 4) /* LLC payload, 0 = Ethertype */
1057#define HOST_DONT_RLSE (1 << 5) /* Don't release buffer when done */
1058#define HOST_DONT_RETRY (1 << 6) /* Don't retry trasmit */
1059#define HOST_CLR_AID (1 << 7) /* clear AID failure */
1060#define HOST_RTS (1 << 9) /* Force RTS use */
1061#define HOST_SHORT (1 << 10) /* Do short preamble */
1062 u16 ctl;
1063 u16 aid;
1064 u16 retries;
1065 u16 fill;
1066} TxCtlHdr;
1067
1068typedef struct {
1069 u16 ctl;
1070 u16 duration;
1071 char addr1[6];
1072 char addr2[6];
1073 char addr3[6];
1074 u16 seq;
1075 char addr4[6];
1076} WifiHdr;
1077
1078
1079typedef struct {
1080 TxCtlHdr ctlhdr;
1081 u16 fill1;
1082 u16 fill2;
1083 WifiHdr wifihdr;
1084 u16 gaplen;
1085 u16 status;
1086} WifiCtlHdr;
1087
1088static WifiCtlHdr wifictlhdr8023 = {
1089 .ctlhdr = {
1090 .ctl = HOST_DONT_RLSE,
1091 }
1092};
1093
1094// A few details needed for WEP (Wireless Equivalent Privacy)
1095#define MAX_KEY_SIZE 13 // 128 (?) bits
1096#define MIN_KEY_SIZE 5 // 40 bits RC4 - WEP
1097typedef struct wep_key_t {
1098 u16 len;
1099 u8 key[16]; /* 40-bit and 104-bit keys */
1100} wep_key_t;
1101
1102/* List of Wireless Handlers (new API) */
1103static const struct iw_handler_def airo_handler_def;
1104
1105static const char version[] = "airo.c 0.6 (Ben Reed & Javier Achirica)";
1106
1107struct airo_info;
1108
1109static int get_dec_u16(char *buffer, int *start, int limit);
1110static void OUT4500(struct airo_info *, u16 reg, u16 value);
1111static unsigned short IN4500(struct airo_info *, u16 reg);
1112static u16 setup_card(struct airo_info*, struct net_device *dev, int lock);
1113static int enable_MAC(struct airo_info *ai, int lock);
1114static void disable_MAC(struct airo_info *ai, int lock);
1115static void enable_interrupts(struct airo_info*);
1116static void disable_interrupts(struct airo_info*);
1117static u16 issuecommand(struct airo_info*, Cmd *pCmd, Resp *pRsp,
1118 bool may_sleep);
1119static int bap_setup(struct airo_info*, u16 rid, u16 offset, int whichbap);
1120static int aux_bap_read(struct airo_info*, __le16 *pu16Dst, int bytelen,
1121 int whichbap);
1122static int fast_bap_read(struct airo_info*, __le16 *pu16Dst, int bytelen,
1123 int whichbap);
1124static int bap_write(struct airo_info*, const __le16 *pu16Src, int bytelen,
1125 int whichbap);
1126static int PC4500_accessrid(struct airo_info*, u16 rid, u16 accmd);
1127static int PC4500_readrid(struct airo_info*, u16 rid, void *pBuf, int len, int lock);
1128static int PC4500_writerid(struct airo_info*, u16 rid, const void
1129 *pBuf, int len, int lock);
1130static int do_writerid(struct airo_info*, u16 rid, const void *rid_data,
1131 int len, int dummy);
1132static u16 transmit_allocate(struct airo_info*, int lenPayload, int raw);
1133static int transmit_802_3_packet(struct airo_info*, int len, char *pPacket,
1134 bool may_sleep);
1135static int transmit_802_11_packet(struct airo_info*, int len, char *pPacket,
1136 bool may_sleep);
1137
1138static int mpi_send_packet(struct net_device *dev);
1139static void mpi_unmap_card(struct pci_dev *pci);
1140static void mpi_receive_802_3(struct airo_info *ai);
1141static void mpi_receive_802_11(struct airo_info *ai);
1142static int waitbusy(struct airo_info *ai);
1143
1144static irqreturn_t airo_interrupt(int irq, void* dev_id);
1145static int airo_thread(void *data);
1146static void timer_func(struct net_device *dev);
1147static int airo_siocdevprivate(struct net_device *dev, struct ifreq *rq, void __user *, int cmd);
1148static struct iw_statistics *airo_get_wireless_stats(struct net_device *dev);
1149#ifdef CISCO_EXT
1150static int readrids(struct net_device *dev, aironet_ioctl *comp);
1151static int writerids(struct net_device *dev, aironet_ioctl *comp);
1152static int flashcard(struct net_device *dev, aironet_ioctl *comp);
1153#endif /* CISCO_EXT */
1154static void micinit(struct airo_info *ai);
1155static int micsetup(struct airo_info *ai);
1156static int encapsulate(struct airo_info *ai, etherHead *pPacket, MICBuffer *buffer, int len);
1157static int decapsulate(struct airo_info *ai, MICBuffer *mic, etherHead *pPacket, u16 payLen);
1158
1159static u8 airo_rssi_to_dbm(tdsRssiEntry *rssi_rid, u8 rssi);
1160static u8 airo_dbm_to_pct(tdsRssiEntry *rssi_rid, u8 dbm);
1161
1162static void airo_networks_free(struct airo_info *ai);
1163
1164struct airo_info {
1165 struct net_device *dev;
1166 struct list_head dev_list;
1167 /* Note, we can have MAX_FIDS outstanding. FIDs are 16-bits, so we
1168 use the high bit to mark whether it is in use. */
1169#define MAX_FIDS 6
1170#define MPI_MAX_FIDS 1
1171 u32 fids[MAX_FIDS];
1172 ConfigRid config;
1173 char keyindex; // Used with auto wep
1174 char defindex; // Used with auto wep
1175 struct proc_dir_entry *proc_entry;
1176 spinlock_t aux_lock;
1177#define FLAG_RADIO_OFF 0 /* User disabling of MAC */
1178#define FLAG_RADIO_DOWN 1 /* ifup/ifdown disabling of MAC */
1179#define FLAG_RADIO_MASK 0x03
1180#define FLAG_ENABLED 2
1181#define FLAG_ADHOC 3 /* Needed by MIC */
1182#define FLAG_MIC_CAPABLE 4
1183#define FLAG_UPDATE_MULTI 5
1184#define FLAG_UPDATE_UNI 6
1185#define FLAG_802_11 7
1186#define FLAG_PROMISC 8 /* IFF_PROMISC 0x100 - include/linux/if.h */
1187#define FLAG_PENDING_XMIT 9
1188#define FLAG_PENDING_XMIT11 10
1189#define FLAG_MPI 11
1190#define FLAG_REGISTERED 12
1191#define FLAG_COMMIT 13
1192#define FLAG_RESET 14
1193#define FLAG_FLASHING 15
1194#define FLAG_WPA_CAPABLE 16
1195 unsigned long flags;
1196#define JOB_DIE 0
1197#define JOB_XMIT 1
1198#define JOB_XMIT11 2
1199#define JOB_STATS 3
1200#define JOB_PROMISC 4
1201#define JOB_MIC 5
1202#define JOB_EVENT 6
1203#define JOB_AUTOWEP 7
1204#define JOB_SCAN_RESULTS 9
1205 unsigned long jobs;
1206 int (*bap_read)(struct airo_info*, __le16 *pu16Dst, int bytelen,
1207 int whichbap);
1208 unsigned short *flash;
1209 tdsRssiEntry *rssi;
1210 struct task_struct *list_bss_task;
1211 struct task_struct *airo_thread_task;
1212 struct semaphore sem;
1213 wait_queue_head_t thr_wait;
1214 unsigned long expires;
1215 struct {
1216 struct sk_buff *skb;
1217 int fid;
1218 } xmit, xmit11;
1219 struct net_device *wifidev;
1220 struct iw_statistics wstats; // wireless stats
1221 unsigned long scan_timeout; /* Time scan should be read */
1222 struct iw_spy_data spy_data;
1223 struct iw_public_data wireless_data;
1224 /* MIC stuff */
1225 struct crypto_sync_skcipher *tfm;
1226 mic_module mod[2];
1227 mic_statistics micstats;
1228 HostRxDesc rxfids[MPI_MAX_FIDS]; // rx/tx/config MPI350 descriptors
1229 HostTxDesc txfids[MPI_MAX_FIDS];
1230 HostRidDesc config_desc;
1231 unsigned long ridbus; // phys addr of config_desc
1232 struct sk_buff_head txq;// tx queue used by mpi350 code
1233 struct pci_dev *pci;
1234 unsigned char __iomem *pcimem;
1235 unsigned char __iomem *pciaux;
1236 unsigned char *shared;
1237 dma_addr_t shared_dma;
1238 pm_message_t power;
1239 SsidRid *SSID;
1240 APListRid APList;
1241#define PCI_SHARED_LEN 2*MPI_MAX_FIDS*PKTSIZE+RIDSIZE
1242 char proc_name[IFNAMSIZ];
1243
1244 int wep_capable;
1245 int max_wep_idx;
1246 int last_auth;
1247
1248 /* WPA-related stuff */
1249 unsigned int bssListFirst;
1250 unsigned int bssListNext;
1251 unsigned int bssListRidLen;
1252
1253 struct list_head network_list;
1254 struct list_head network_free_list;
1255 BSSListElement *networks;
1256};
1257
1258static inline int bap_read(struct airo_info *ai, __le16 *pu16Dst, int bytelen,
1259 int whichbap)
1260{
1261 return ai->bap_read(ai, pu16Dst, bytelen, whichbap);
1262}
1263
1264static int setup_proc_entry(struct net_device *dev,
1265 struct airo_info *apriv);
1266static int takedown_proc_entry(struct net_device *dev,
1267 struct airo_info *apriv);
1268
1269static int cmdreset(struct airo_info *ai);
1270static int setflashmode(struct airo_info *ai);
1271static int flashgchar(struct airo_info *ai, int matchbyte, int dwelltime);
1272static int flashputbuf(struct airo_info *ai);
1273static int flashrestart(struct airo_info *ai, struct net_device *dev);
1274
1275#define airo_print(type, name, fmt, args...) \
1276 printk(type DRV_NAME "(%s): " fmt "\n", name, ##args)
1277
1278#define airo_print_info(name, fmt, args...) \
1279 airo_print(KERN_INFO, name, fmt, ##args)
1280
1281#define airo_print_dbg(name, fmt, args...) \
1282 airo_print(KERN_DEBUG, name, fmt, ##args)
1283
1284#define airo_print_warn(name, fmt, args...) \
1285 airo_print(KERN_WARNING, name, fmt, ##args)
1286
1287#define airo_print_err(name, fmt, args...) \
1288 airo_print(KERN_ERR, name, fmt, ##args)
1289
1290#define AIRO_FLASH(dev) (((struct airo_info *)dev->ml_priv)->flash)
1291
1292/***********************************************************************
1293 * MIC ROUTINES *
1294 ***********************************************************************
1295 */
1296
1297static int RxSeqValid(struct airo_info *ai, miccntx *context, int mcast, u32 micSeq);
1298static void MoveWindow(miccntx *context, u32 micSeq);
1299static void emmh32_setseed(emmh32_context *context, u8 *pkey, int keylen,
1300 struct crypto_sync_skcipher *tfm);
1301static void emmh32_init(emmh32_context *context);
1302static void emmh32_update(emmh32_context *context, u8 *pOctets, int len);
1303static void emmh32_final(emmh32_context *context, u8 digest[4]);
1304static int flashpchar(struct airo_info *ai, int byte, int dwelltime);
1305
1306static void age_mic_context(miccntx *cur, miccntx *old, u8 *key, int key_len,
1307 struct crypto_sync_skcipher *tfm)
1308{
1309 /* If the current MIC context is valid and its key is the same as
1310 * the MIC register, there's nothing to do.
1311 */
1312 if (cur->valid && (memcmp(cur->key, key, key_len) == 0))
1313 return;
1314
1315 /* Age current mic Context */
1316 memcpy(old, cur, sizeof(*cur));
1317
1318 /* Initialize new context */
1319 memcpy(cur->key, key, key_len);
1320 cur->window = 33; /* Window always points to the middle */
1321 cur->rx = 0; /* Rx Sequence numbers */
1322 cur->tx = 0; /* Tx sequence numbers */
1323 cur->valid = 1; /* Key is now valid */
1324
1325 /* Give key to mic seed */
1326 emmh32_setseed(&cur->seed, key, key_len, tfm);
1327}
1328
1329/* micinit - Initialize mic seed */
1330
1331static void micinit(struct airo_info *ai)
1332{
1333 MICRid mic_rid;
1334
1335 clear_bit(JOB_MIC, &ai->jobs);
1336 PC4500_readrid(ai, RID_MIC, &mic_rid, sizeof(mic_rid), 0);
1337 up(&ai->sem);
1338
1339 ai->micstats.enabled = (le16_to_cpu(mic_rid.state) & 0x00FF) ? 1 : 0;
1340 if (!ai->micstats.enabled) {
1341 /* So next time we have a valid key and mic is enabled, we will
1342 * update the sequence number if the key is the same as before.
1343 */
1344 ai->mod[0].uCtx.valid = 0;
1345 ai->mod[0].mCtx.valid = 0;
1346 return;
1347 }
1348
1349 if (mic_rid.multicastValid) {
1350 age_mic_context(&ai->mod[0].mCtx, &ai->mod[1].mCtx,
1351 mic_rid.multicast, sizeof(mic_rid.multicast),
1352 ai->tfm);
1353 }
1354
1355 if (mic_rid.unicastValid) {
1356 age_mic_context(&ai->mod[0].uCtx, &ai->mod[1].uCtx,
1357 mic_rid.unicast, sizeof(mic_rid.unicast),
1358 ai->tfm);
1359 }
1360}
1361
1362/* micsetup - Get ready for business */
1363
1364static int micsetup(struct airo_info *ai)
1365{
1366 int i;
1367
1368 if (ai->tfm == NULL)
1369 ai->tfm = crypto_alloc_sync_skcipher("ctr(aes)", 0, 0);
1370
1371 if (IS_ERR(ai->tfm)) {
1372 airo_print_err(ai->dev->name, "failed to load transform for AES");
1373 ai->tfm = NULL;
1374 return ERROR;
1375 }
1376
1377 for (i = 0; i < NUM_MODULES; i++) {
1378 memset(&ai->mod[i].mCtx, 0, sizeof(miccntx));
1379 memset(&ai->mod[i].uCtx, 0, sizeof(miccntx));
1380 }
1381 return SUCCESS;
1382}
1383
1384static const u8 micsnap[] = {0xAA, 0xAA, 0x03, 0x00, 0x40, 0x96, 0x00, 0x02};
1385
1386/*===========================================================================
1387 * Description: Mic a packet
1388 *
1389 * Inputs: etherHead * pointer to an 802.3 frame
1390 *
1391 * Returns: BOOLEAN if successful, otherwise false.
1392 * PacketTxLen will be updated with the mic'd packets size.
1393 *
1394 * Caveats: It is assumed that the frame buffer will already
1395 * be big enough to hold the largets mic message possible.
1396 * (No memory allocation is done here).
1397 *
1398 * Author: sbraneky (10/15/01)
1399 * Merciless hacks by rwilcher (1/14/02)
1400 */
1401
1402static int encapsulate(struct airo_info *ai, etherHead *frame, MICBuffer *mic, int payLen)
1403{
1404 miccntx *context;
1405
1406 // Determine correct context
1407 // If not adhoc, always use unicast key
1408
1409 if (test_bit(FLAG_ADHOC, &ai->flags) && (frame->da[0] & 0x1))
1410 context = &ai->mod[0].mCtx;
1411 else
1412 context = &ai->mod[0].uCtx;
1413
1414 if (!context->valid)
1415 return ERROR;
1416
1417 mic->typelen = htons(payLen + 16); //Length of Mic'd packet
1418
1419 memcpy(&mic->u.snap, micsnap, sizeof(micsnap)); // Add Snap
1420
1421 // Add Tx sequence
1422 mic->seq = htonl(context->tx);
1423 context->tx += 2;
1424
1425 emmh32_init(&context->seed); // Mic the packet
1426 emmh32_update(&context->seed, frame->da, ETH_ALEN * 2); // DA, SA
1427 emmh32_update(&context->seed, (u8*)&mic->typelen, 10); // Type/Length and Snap
1428 emmh32_update(&context->seed, (u8*)&mic->seq, sizeof(mic->seq)); //SEQ
1429 emmh32_update(&context->seed, (u8*)(frame + 1), payLen); //payload
1430 emmh32_final(&context->seed, (u8*)&mic->mic);
1431
1432 /* New Type/length ?????????? */
1433 mic->typelen = 0; //Let NIC know it could be an oversized packet
1434 return SUCCESS;
1435}
1436
1437typedef enum {
1438 NONE,
1439 NOMIC,
1440 NOMICPLUMMED,
1441 SEQUENCE,
1442 INCORRECTMIC,
1443} mic_error;
1444
1445/*===========================================================================
1446 * Description: Decapsulates a MIC'd packet and returns the 802.3 packet
1447 * (removes the MIC stuff) if packet is a valid packet.
1448 *
1449 * Inputs: etherHead pointer to the 802.3 packet
1450 *
1451 * Returns: BOOLEAN - TRUE if packet should be dropped otherwise FALSE
1452 *
1453 * Author: sbraneky (10/15/01)
1454 * Merciless hacks by rwilcher (1/14/02)
1455 *---------------------------------------------------------------------------
1456 */
1457
1458static int decapsulate(struct airo_info *ai, MICBuffer *mic, etherHead *eth, u16 payLen)
1459{
1460 int i;
1461 u32 micSEQ;
1462 miccntx *context;
1463 u8 digest[4];
1464 mic_error micError = NONE;
1465
1466 // Check if the packet is a Mic'd packet
1467
1468 if (!ai->micstats.enabled) {
1469 //No Mic set or Mic OFF but we received a MIC'd packet.
1470 if (memcmp ((u8*)eth + 14, micsnap, sizeof(micsnap)) == 0) {
1471 ai->micstats.rxMICPlummed++;
1472 return ERROR;
1473 }
1474 return SUCCESS;
1475 }
1476
1477 if (ntohs(mic->typelen) == 0x888E)
1478 return SUCCESS;
1479
1480 if (memcmp (mic->u.snap, micsnap, sizeof(micsnap)) != 0) {
1481 // Mic enabled but packet isn't Mic'd
1482 ai->micstats.rxMICPlummed++;
1483 return ERROR;
1484 }
1485
1486 micSEQ = ntohl(mic->seq); //store SEQ as CPU order
1487
1488 //At this point we a have a mic'd packet and mic is enabled
1489 //Now do the mic error checking.
1490
1491 //Receive seq must be odd
1492 if ((micSEQ & 1) == 0) {
1493 ai->micstats.rxWrongSequence++;
1494 return ERROR;
1495 }
1496
1497 for (i = 0; i < NUM_MODULES; i++) {
1498 int mcast = eth->da[0] & 1;
1499 //Determine proper context
1500 context = mcast ? &ai->mod[i].mCtx : &ai->mod[i].uCtx;
1501
1502 //Make sure context is valid
1503 if (!context->valid) {
1504 if (i == 0)
1505 micError = NOMICPLUMMED;
1506 continue;
1507 }
1508 //DeMic it
1509
1510 if (!mic->typelen)
1511 mic->typelen = htons(payLen + sizeof(MICBuffer) - 2);
1512
1513 emmh32_init(&context->seed);
1514 emmh32_update(&context->seed, eth->da, ETH_ALEN*2);
1515 emmh32_update(&context->seed, (u8 *)&mic->typelen, sizeof(mic->typelen)+sizeof(mic->u.snap));
1516 emmh32_update(&context->seed, (u8 *)&mic->seq, sizeof(mic->seq));
1517 emmh32_update(&context->seed, (u8 *)(eth + 1), payLen);
1518 //Calculate MIC
1519 emmh32_final(&context->seed, digest);
1520
1521 if (memcmp(digest, &mic->mic, 4)) { //Make sure the mics match
1522 //Invalid Mic
1523 if (i == 0)
1524 micError = INCORRECTMIC;
1525 continue;
1526 }
1527
1528 //Check Sequence number if mics pass
1529 if (RxSeqValid(ai, context, mcast, micSEQ) == SUCCESS) {
1530 ai->micstats.rxSuccess++;
1531 return SUCCESS;
1532 }
1533 if (i == 0)
1534 micError = SEQUENCE;
1535 }
1536
1537 // Update statistics
1538 switch (micError) {
1539 case NOMICPLUMMED: ai->micstats.rxMICPlummed++; break;
1540 case SEQUENCE: ai->micstats.rxWrongSequence++; break;
1541 case INCORRECTMIC: ai->micstats.rxIncorrectMIC++; break;
1542 case NONE: break;
1543 case NOMIC: break;
1544 }
1545 return ERROR;
1546}
1547
1548/*===========================================================================
1549 * Description: Checks the Rx Seq number to make sure it is valid
1550 * and hasn't already been received
1551 *
1552 * Inputs: miccntx - mic context to check seq against
1553 * micSeq - the Mic seq number
1554 *
1555 * Returns: TRUE if valid otherwise FALSE.
1556 *
1557 * Author: sbraneky (10/15/01)
1558 * Merciless hacks by rwilcher (1/14/02)
1559 *---------------------------------------------------------------------------
1560 */
1561
1562static int RxSeqValid(struct airo_info *ai, miccntx *context, int mcast, u32 micSeq)
1563{
1564 u32 seq, index;
1565
1566 //Allow for the ap being rebooted - if it is then use the next
1567 //sequence number of the current sequence number - might go backwards
1568
1569 if (mcast) {
1570 if (test_bit(FLAG_UPDATE_MULTI, &ai->flags)) {
1571 clear_bit (FLAG_UPDATE_MULTI, &ai->flags);
1572 context->window = (micSeq > 33) ? micSeq : 33;
1573 context->rx = 0; // Reset rx
1574 }
1575 } else if (test_bit(FLAG_UPDATE_UNI, &ai->flags)) {
1576 clear_bit (FLAG_UPDATE_UNI, &ai->flags);
1577 context->window = (micSeq > 33) ? micSeq : 33; // Move window
1578 context->rx = 0; // Reset rx
1579 }
1580
1581 //Make sequence number relative to START of window
1582 seq = micSeq - (context->window - 33);
1583
1584 //Too old of a SEQ number to check.
1585 if ((s32)seq < 0)
1586 return ERROR;
1587
1588 if (seq > 64) {
1589 //Window is infinite forward
1590 MoveWindow(context, micSeq);
1591 return SUCCESS;
1592 }
1593
1594 // We are in the window. Now check the context rx bit to see if it was already sent
1595 seq >>= 1; //divide by 2 because we only have odd numbers
1596 index = 1 << seq; //Get an index number
1597
1598 if (!(context->rx & index)) {
1599 //micSEQ falls inside the window.
1600 //Add seqence number to the list of received numbers.
1601 context->rx |= index;
1602
1603 MoveWindow(context, micSeq);
1604
1605 return SUCCESS;
1606 }
1607 return ERROR;
1608}
1609
1610static void MoveWindow(miccntx *context, u32 micSeq)
1611{
1612 u32 shift;
1613
1614 //Move window if seq greater than the middle of the window
1615 if (micSeq > context->window) {
1616 shift = (micSeq - context->window) >> 1;
1617
1618 //Shift out old
1619 if (shift < 32)
1620 context->rx >>= shift;
1621 else
1622 context->rx = 0;
1623
1624 context->window = micSeq; //Move window
1625 }
1626}
1627
1628/*==============================================*/
1629/*========== EMMH ROUTINES ====================*/
1630/*==============================================*/
1631
1632/* mic accumulate */
1633#define MIC_ACCUM(val) \
1634 context->accum += (u64)(val) * be32_to_cpu(context->coeff[coeff_position++]);
1635
1636/* expand the key to fill the MMH coefficient array */
1637static void emmh32_setseed(emmh32_context *context, u8 *pkey, int keylen,
1638 struct crypto_sync_skcipher *tfm)
1639{
1640 /* take the keying material, expand if necessary, truncate at 16-bytes */
1641 /* run through AES counter mode to generate context->coeff[] */
1642
1643 SYNC_SKCIPHER_REQUEST_ON_STACK(req, tfm);
1644 struct scatterlist sg;
1645 u8 iv[AES_BLOCK_SIZE] = {};
1646 int ret;
1647
1648 crypto_sync_skcipher_setkey(tfm, pkey, 16);
1649
1650 memset(context->coeff, 0, sizeof(context->coeff));
1651 sg_init_one(&sg, context->coeff, sizeof(context->coeff));
1652
1653 skcipher_request_set_sync_tfm(req, tfm);
1654 skcipher_request_set_callback(req, 0, NULL, NULL);
1655 skcipher_request_set_crypt(req, &sg, &sg, sizeof(context->coeff), iv);
1656
1657 ret = crypto_skcipher_encrypt(req);
1658 WARN_ON_ONCE(ret);
1659}
1660
1661/* prepare for calculation of a new mic */
1662static void emmh32_init(emmh32_context *context)
1663{
1664 /* prepare for new mic calculation */
1665 context->accum = 0;
1666 context->position = 0;
1667}
1668
1669/* add some bytes to the mic calculation */
1670static void emmh32_update(emmh32_context *context, u8 *pOctets, int len)
1671{
1672 int coeff_position, byte_position;
1673
1674 if (len == 0) return;
1675
1676 coeff_position = context->position >> 2;
1677
1678 /* deal with partial 32-bit word left over from last update */
1679 byte_position = context->position & 3;
1680 if (byte_position) {
1681 /* have a partial word in part to deal with */
1682 do {
1683 if (len == 0) return;
1684 context->part.d8[byte_position++] = *pOctets++;
1685 context->position++;
1686 len--;
1687 } while (byte_position < 4);
1688 MIC_ACCUM(ntohl(context->part.d32));
1689 }
1690
1691 /* deal with full 32-bit words */
1692 while (len >= 4) {
1693 MIC_ACCUM(ntohl(*(__be32 *)pOctets));
1694 context->position += 4;
1695 pOctets += 4;
1696 len -= 4;
1697 }
1698
1699 /* deal with partial 32-bit word that will be left over from this update */
1700 byte_position = 0;
1701 while (len > 0) {
1702 context->part.d8[byte_position++] = *pOctets++;
1703 context->position++;
1704 len--;
1705 }
1706}
1707
1708/* mask used to zero empty bytes for final partial word */
1709static u32 mask32[4] = { 0x00000000L, 0xFF000000L, 0xFFFF0000L, 0xFFFFFF00L };
1710
1711/* calculate the mic */
1712static void emmh32_final(emmh32_context *context, u8 digest[4])
1713{
1714 int coeff_position, byte_position;
1715 u32 val;
1716
1717 u64 sum, utmp;
1718 s64 stmp;
1719
1720 coeff_position = context->position >> 2;
1721
1722 /* deal with partial 32-bit word left over from last update */
1723 byte_position = context->position & 3;
1724 if (byte_position) {
1725 /* have a partial word in part to deal with */
1726 val = ntohl(context->part.d32);
1727 MIC_ACCUM(val & mask32[byte_position]); /* zero empty bytes */
1728 }
1729
1730 /* reduce the accumulated u64 to a 32-bit MIC */
1731 sum = context->accum;
1732 stmp = (sum & 0xffffffffLL) - ((sum >> 32) * 15);
1733 utmp = (stmp & 0xffffffffLL) - ((stmp >> 32) * 15);
1734 sum = utmp & 0xffffffffLL;
1735 if (utmp > 0x10000000fLL)
1736 sum -= 15;
1737
1738 val = (u32)sum;
1739 digest[0] = (val>>24) & 0xFF;
1740 digest[1] = (val>>16) & 0xFF;
1741 digest[2] = (val>>8) & 0xFF;
1742 digest[3] = val & 0xFF;
1743}
1744
1745static int readBSSListRid(struct airo_info *ai, int first,
1746 BSSListRid *list)
1747{
1748 Cmd cmd;
1749 Resp rsp;
1750
1751 if (first == 1) {
1752 if (ai->flags & FLAG_RADIO_MASK) return -ENETDOWN;
1753 memset(&cmd, 0, sizeof(cmd));
1754 cmd.cmd = CMD_LISTBSS;
1755 if (down_interruptible(&ai->sem))
1756 return -ERESTARTSYS;
1757 ai->list_bss_task = current;
1758 issuecommand(ai, &cmd, &rsp, true);
1759 up(&ai->sem);
1760 /* Let the command take effect */
1761 schedule_timeout_uninterruptible(3 * HZ);
1762 ai->list_bss_task = NULL;
1763 }
1764 return PC4500_readrid(ai, first ? ai->bssListFirst : ai->bssListNext,
1765 list, ai->bssListRidLen, 1);
1766}
1767
1768static int readWepKeyRid(struct airo_info *ai, WepKeyRid *wkr, int temp, int lock)
1769{
1770 return PC4500_readrid(ai, temp ? RID_WEP_TEMP : RID_WEP_PERM,
1771 wkr, sizeof(*wkr), lock);
1772}
1773
1774static int writeWepKeyRid(struct airo_info *ai, WepKeyRid *wkr, int perm, int lock)
1775{
1776 int rc;
1777 rc = PC4500_writerid(ai, RID_WEP_TEMP, wkr, sizeof(*wkr), lock);
1778 if (rc!=SUCCESS)
1779 airo_print_err(ai->dev->name, "WEP_TEMP set %x", rc);
1780 if (perm) {
1781 rc = PC4500_writerid(ai, RID_WEP_PERM, wkr, sizeof(*wkr), lock);
1782 if (rc!=SUCCESS)
1783 airo_print_err(ai->dev->name, "WEP_PERM set %x", rc);
1784 }
1785 return rc;
1786}
1787
1788static int readSsidRid(struct airo_info*ai, SsidRid *ssidr)
1789{
1790 return PC4500_readrid(ai, RID_SSID, ssidr, sizeof(*ssidr), 1);
1791}
1792
1793static int writeSsidRid(struct airo_info*ai, SsidRid *pssidr, int lock)
1794{
1795 return PC4500_writerid(ai, RID_SSID, pssidr, sizeof(*pssidr), lock);
1796}
1797
1798static int readConfigRid(struct airo_info *ai, int lock)
1799{
1800 int rc;
1801 ConfigRid cfg;
1802
1803 if (ai->config.len)
1804 return SUCCESS;
1805
1806 rc = PC4500_readrid(ai, RID_ACTUALCONFIG, &cfg, sizeof(cfg), lock);
1807 if (rc != SUCCESS)
1808 return rc;
1809
1810 ai->config = cfg;
1811 return SUCCESS;
1812}
1813
1814static inline void checkThrottle(struct airo_info *ai)
1815{
1816 int i;
1817/* Old hardware had a limit on encryption speed */
1818 if (ai->config.authType != AUTH_OPEN && maxencrypt) {
1819 for (i = 0; i<8; i++) {
1820 if (ai->config.rates[i] > maxencrypt) {
1821 ai->config.rates[i] = 0;
1822 }
1823 }
1824 }
1825}
1826
1827static int writeConfigRid(struct airo_info *ai, int lock)
1828{
1829 ConfigRid cfgr;
1830
1831 if (!test_bit (FLAG_COMMIT, &ai->flags))
1832 return SUCCESS;
1833
1834 clear_bit (FLAG_COMMIT, &ai->flags);
1835 clear_bit (FLAG_RESET, &ai->flags);
1836 checkThrottle(ai);
1837 cfgr = ai->config;
1838
1839 if ((cfgr.opmode & MODE_CFG_MASK) == MODE_STA_IBSS)
1840 set_bit(FLAG_ADHOC, &ai->flags);
1841 else
1842 clear_bit(FLAG_ADHOC, &ai->flags);
1843
1844 return PC4500_writerid(ai, RID_CONFIG, &cfgr, sizeof(cfgr), lock);
1845}
1846
1847static int readStatusRid(struct airo_info *ai, StatusRid *statr, int lock)
1848{
1849 return PC4500_readrid(ai, RID_STATUS, statr, sizeof(*statr), lock);
1850}
1851
1852static int writeAPListRid(struct airo_info *ai, APListRid *aplr, int lock)
1853{
1854 return PC4500_writerid(ai, RID_APLIST, aplr, sizeof(*aplr), lock);
1855}
1856
1857static int readCapabilityRid(struct airo_info *ai, CapabilityRid *capr, int lock)
1858{
1859 return PC4500_readrid(ai, RID_CAPABILITIES, capr, sizeof(*capr), lock);
1860}
1861
1862static int readStatsRid(struct airo_info*ai, StatsRid *sr, int rid, int lock)
1863{
1864 return PC4500_readrid(ai, rid, sr, sizeof(*sr), lock);
1865}
1866
1867static void try_auto_wep(struct airo_info *ai)
1868{
1869 if (auto_wep && !test_bit(FLAG_RADIO_DOWN, &ai->flags)) {
1870 ai->expires = RUN_AT(3*HZ);
1871 wake_up_interruptible(&ai->thr_wait);
1872 }
1873}
1874
1875static int airo_open(struct net_device *dev)
1876{
1877 struct airo_info *ai = dev->ml_priv;
1878 int rc = 0;
1879
1880 if (test_bit(FLAG_FLASHING, &ai->flags))
1881 return -EIO;
1882
1883 /* Make sure the card is configured.
1884 * Wireless Extensions may postpone config changes until the card
1885 * is open (to pipeline changes and speed-up card setup). If
1886 * those changes are not yet committed, do it now - Jean II */
1887 if (test_bit(FLAG_COMMIT, &ai->flags)) {
1888 disable_MAC(ai, 1);
1889 writeConfigRid(ai, 1);
1890 }
1891
1892 if (ai->wifidev != dev) {
1893 clear_bit(JOB_DIE, &ai->jobs);
1894 ai->airo_thread_task = kthread_run(airo_thread, dev, "%s",
1895 dev->name);
1896 if (IS_ERR(ai->airo_thread_task))
1897 return (int)PTR_ERR(ai->airo_thread_task);
1898
1899 rc = request_irq(dev->irq, airo_interrupt, IRQF_SHARED,
1900 dev->name, dev);
1901 if (rc) {
1902 airo_print_err(dev->name,
1903 "register interrupt %d failed, rc %d",
1904 dev->irq, rc);
1905 set_bit(JOB_DIE, &ai->jobs);
1906 kthread_stop(ai->airo_thread_task);
1907 return rc;
1908 }
1909
1910 /* Power on the MAC controller (which may have been disabled) */
1911 clear_bit(FLAG_RADIO_DOWN, &ai->flags);
1912 enable_interrupts(ai);
1913
1914 try_auto_wep(ai);
1915 }
1916 enable_MAC(ai, 1);
1917
1918 netif_start_queue(dev);
1919 return 0;
1920}
1921
1922static netdev_tx_t mpi_start_xmit(struct sk_buff *skb,
1923 struct net_device *dev)
1924{
1925 int npacks, pending;
1926 unsigned long flags;
1927 struct airo_info *ai = dev->ml_priv;
1928
1929 if (!skb) {
1930 airo_print_err(dev->name, "%s: skb == NULL!",__func__);
1931 return NETDEV_TX_OK;
1932 }
1933 if (skb_padto(skb, ETH_ZLEN)) {
1934 dev->stats.tx_dropped++;
1935 return NETDEV_TX_OK;
1936 }
1937 npacks = skb_queue_len (&ai->txq);
1938
1939 if (npacks >= MAXTXQ - 1) {
1940 netif_stop_queue (dev);
1941 if (npacks > MAXTXQ) {
1942 dev->stats.tx_fifo_errors++;
1943 return NETDEV_TX_BUSY;
1944 }
1945 skb_queue_tail (&ai->txq, skb);
1946 return NETDEV_TX_OK;
1947 }
1948
1949 spin_lock_irqsave(&ai->aux_lock, flags);
1950 skb_queue_tail (&ai->txq, skb);
1951 pending = test_bit(FLAG_PENDING_XMIT, &ai->flags);
1952 spin_unlock_irqrestore(&ai->aux_lock, flags);
1953 netif_wake_queue (dev);
1954
1955 if (pending == 0) {
1956 set_bit(FLAG_PENDING_XMIT, &ai->flags);
1957 mpi_send_packet (dev);
1958 }
1959 return NETDEV_TX_OK;
1960}
1961
1962/*
1963 * @mpi_send_packet
1964 *
1965 * Attempt to transmit a packet. Can be called from interrupt
1966 * or transmit . return number of packets we tried to send
1967 */
1968
1969static int mpi_send_packet (struct net_device *dev)
1970{
1971 struct sk_buff *skb;
1972 unsigned char *buffer;
1973 s16 len;
1974 __le16 *payloadLen;
1975 struct airo_info *ai = dev->ml_priv;
1976 u8 *sendbuf;
1977
1978 /* get a packet to send */
1979
1980 if ((skb = skb_dequeue(&ai->txq)) == NULL) {
1981 airo_print_err(dev->name,
1982 "%s: Dequeue'd zero in send_packet()",
1983 __func__);
1984 return 0;
1985 }
1986
1987 /* check min length*/
1988 len = ETH_ZLEN < skb->len ? skb->len : ETH_ZLEN;
1989 buffer = skb->data;
1990
1991 ai->txfids[0].tx_desc.offset = 0;
1992 ai->txfids[0].tx_desc.valid = 1;
1993 ai->txfids[0].tx_desc.eoc = 1;
1994 ai->txfids[0].tx_desc.len =len+sizeof(WifiHdr);
1995
1996/*
1997 * Magic, the cards firmware needs a length count (2 bytes) in the host buffer
1998 * right after TXFID_HDR.The TXFID_HDR contains the status short so payloadlen
1999 * is immediately after it. ------------------------------------------------
2000 * |TXFIDHDR+STATUS|PAYLOADLEN|802.3HDR|PACKETDATA|
2001 * ------------------------------------------------
2002 */
2003
2004 memcpy(ai->txfids[0].virtual_host_addr,
2005 (char *)&wifictlhdr8023, sizeof(wifictlhdr8023));
2006
2007 payloadLen = (__le16 *)(ai->txfids[0].virtual_host_addr +
2008 sizeof(wifictlhdr8023));
2009 sendbuf = ai->txfids[0].virtual_host_addr +
2010 sizeof(wifictlhdr8023) + 2 ;
2011
2012 /*
2013 * Firmware automatically puts 802 header on so
2014 * we don't need to account for it in the length
2015 */
2016 if (test_bit(FLAG_MIC_CAPABLE, &ai->flags) && ai->micstats.enabled &&
2017 (ntohs(((__be16 *)buffer)[6]) != 0x888E)) {
2018 MICBuffer pMic;
2019
2020 if (encapsulate(ai, (etherHead *)buffer, &pMic, len - sizeof(etherHead)) != SUCCESS)
2021 return ERROR;
2022
2023 *payloadLen = cpu_to_le16(len-sizeof(etherHead)+sizeof(pMic));
2024 ai->txfids[0].tx_desc.len += sizeof(pMic);
2025 /* copy data into airo dma buffer */
2026 memcpy (sendbuf, buffer, sizeof(etherHead));
2027 buffer += sizeof(etherHead);
2028 sendbuf += sizeof(etherHead);
2029 memcpy (sendbuf, &pMic, sizeof(pMic));
2030 sendbuf += sizeof(pMic);
2031 memcpy (sendbuf, buffer, len - sizeof(etherHead));
2032 } else {
2033 *payloadLen = cpu_to_le16(len - sizeof(etherHead));
2034
2035 netif_trans_update(dev);
2036
2037 /* copy data into airo dma buffer */
2038 memcpy(sendbuf, buffer, len);
2039 }
2040
2041 memcpy_toio(ai->txfids[0].card_ram_off,
2042 &ai->txfids[0].tx_desc, sizeof(TxFid));
2043
2044 OUT4500(ai, EVACK, 8);
2045
2046 dev_kfree_skb_any(skb);
2047 return 1;
2048}
2049
2050static void get_tx_error(struct airo_info *ai, s32 fid)
2051{
2052 __le16 status;
2053
2054 if (fid < 0)
2055 status = ((WifiCtlHdr *)ai->txfids[0].virtual_host_addr)->ctlhdr.status;
2056 else {
2057 if (bap_setup(ai, ai->fids[fid] & 0xffff, 4, BAP0) != SUCCESS)
2058 return;
2059 bap_read(ai, &status, 2, BAP0);
2060 }
2061 if (le16_to_cpu(status) & 2) /* Too many retries */
2062 ai->dev->stats.tx_aborted_errors++;
2063 if (le16_to_cpu(status) & 4) /* Transmit lifetime exceeded */
2064 ai->dev->stats.tx_heartbeat_errors++;
2065 if (le16_to_cpu(status) & 8) /* Aid fail */
2066 { }
2067 if (le16_to_cpu(status) & 0x10) /* MAC disabled */
2068 ai->dev->stats.tx_carrier_errors++;
2069 if (le16_to_cpu(status) & 0x20) /* Association lost */
2070 { }
2071 /* We produce a TXDROP event only for retry or lifetime
2072 * exceeded, because that's the only status that really mean
2073 * that this particular node went away.
2074 * Other errors means that *we* screwed up. - Jean II */
2075 if ((le16_to_cpu(status) & 2) ||
2076 (le16_to_cpu(status) & 4)) {
2077 union iwreq_data wrqu;
2078 char junk[0x18];
2079
2080 /* Faster to skip over useless data than to do
2081 * another bap_setup(). We are at offset 0x6 and
2082 * need to go to 0x18 and read 6 bytes - Jean II */
2083 bap_read(ai, (__le16 *) junk, 0x18, BAP0);
2084
2085 /* Copy 802.11 dest address.
2086 * We use the 802.11 header because the frame may
2087 * not be 802.3 or may be mangled...
2088 * In Ad-Hoc mode, it will be the node address.
2089 * In managed mode, it will be most likely the AP addr
2090 * User space will figure out how to convert it to
2091 * whatever it needs (IP address or else).
2092 * - Jean II */
2093 memcpy(wrqu.addr.sa_data, junk + 0x12, ETH_ALEN);
2094 wrqu.addr.sa_family = ARPHRD_ETHER;
2095
2096 /* Send event to user space */
2097 wireless_send_event(ai->dev, IWEVTXDROP, &wrqu, NULL);
2098 }
2099}
2100
2101static void airo_end_xmit(struct net_device *dev, bool may_sleep)
2102{
2103 u16 status;
2104 int i;
2105 struct airo_info *priv = dev->ml_priv;
2106 struct sk_buff *skb = priv->xmit.skb;
2107 int fid = priv->xmit.fid;
2108 u32 *fids = priv->fids;
2109
2110 clear_bit(JOB_XMIT, &priv->jobs);
2111 clear_bit(FLAG_PENDING_XMIT, &priv->flags);
2112 status = transmit_802_3_packet(priv, fids[fid], skb->data, may_sleep);
2113 up(&priv->sem);
2114
2115 i = 0;
2116 if (status == SUCCESS) {
2117 netif_trans_update(dev);
2118 for (; i < MAX_FIDS / 2 && (priv->fids[i] & 0xffff0000); i++);
2119 } else {
2120 priv->fids[fid] &= 0xffff;
2121 dev->stats.tx_window_errors++;
2122 }
2123 if (i < MAX_FIDS / 2)
2124 netif_wake_queue(dev);
2125 dev_kfree_skb(skb);
2126}
2127
2128static netdev_tx_t airo_start_xmit(struct sk_buff *skb,
2129 struct net_device *dev)
2130{
2131 s16 len;
2132 int i, j;
2133 struct airo_info *priv = dev->ml_priv;
2134 u32 *fids = priv->fids;
2135
2136 if (skb == NULL) {
2137 airo_print_err(dev->name, "%s: skb == NULL!", __func__);
2138 return NETDEV_TX_OK;
2139 }
2140 if (skb_padto(skb, ETH_ZLEN)) {
2141 dev->stats.tx_dropped++;
2142 return NETDEV_TX_OK;
2143 }
2144
2145 /* Find a vacant FID */
2146 for (i = 0; i < MAX_FIDS / 2 && (fids[i] & 0xffff0000); i++);
2147 for (j = i + 1; j < MAX_FIDS / 2 && (fids[j] & 0xffff0000); j++);
2148
2149 if (j >= MAX_FIDS / 2) {
2150 netif_stop_queue(dev);
2151
2152 if (i == MAX_FIDS / 2) {
2153 dev->stats.tx_fifo_errors++;
2154 return NETDEV_TX_BUSY;
2155 }
2156 }
2157 /* check min length*/
2158 len = ETH_ZLEN < skb->len ? skb->len : ETH_ZLEN;
2159 /* Mark fid as used & save length for later */
2160 fids[i] |= (len << 16);
2161 priv->xmit.skb = skb;
2162 priv->xmit.fid = i;
2163 if (down_trylock(&priv->sem) != 0) {
2164 set_bit(FLAG_PENDING_XMIT, &priv->flags);
2165 netif_stop_queue(dev);
2166 set_bit(JOB_XMIT, &priv->jobs);
2167 wake_up_interruptible(&priv->thr_wait);
2168 } else
2169 airo_end_xmit(dev, false);
2170 return NETDEV_TX_OK;
2171}
2172
2173static void airo_end_xmit11(struct net_device *dev, bool may_sleep)
2174{
2175 u16 status;
2176 int i;
2177 struct airo_info *priv = dev->ml_priv;
2178 struct sk_buff *skb = priv->xmit11.skb;
2179 int fid = priv->xmit11.fid;
2180 u32 *fids = priv->fids;
2181
2182 clear_bit(JOB_XMIT11, &priv->jobs);
2183 clear_bit(FLAG_PENDING_XMIT11, &priv->flags);
2184 status = transmit_802_11_packet(priv, fids[fid], skb->data, may_sleep);
2185 up(&priv->sem);
2186
2187 i = MAX_FIDS / 2;
2188 if (status == SUCCESS) {
2189 netif_trans_update(dev);
2190 for (; i < MAX_FIDS && (priv->fids[i] & 0xffff0000); i++);
2191 } else {
2192 priv->fids[fid] &= 0xffff;
2193 dev->stats.tx_window_errors++;
2194 }
2195 if (i < MAX_FIDS)
2196 netif_wake_queue(dev);
2197 dev_kfree_skb(skb);
2198}
2199
2200static netdev_tx_t airo_start_xmit11(struct sk_buff *skb,
2201 struct net_device *dev)
2202{
2203 s16 len;
2204 int i, j;
2205 struct airo_info *priv = dev->ml_priv;
2206 u32 *fids = priv->fids;
2207
2208 if (test_bit(FLAG_MPI, &priv->flags)) {
2209 /* Not implemented yet for MPI350 */
2210 netif_stop_queue(dev);
2211 dev_kfree_skb_any(skb);
2212 return NETDEV_TX_OK;
2213 }
2214
2215 if (skb == NULL) {
2216 airo_print_err(dev->name, "%s: skb == NULL!", __func__);
2217 return NETDEV_TX_OK;
2218 }
2219 if (skb_padto(skb, ETH_ZLEN)) {
2220 dev->stats.tx_dropped++;
2221 return NETDEV_TX_OK;
2222 }
2223
2224 /* Find a vacant FID */
2225 for (i = MAX_FIDS / 2; i < MAX_FIDS && (fids[i] & 0xffff0000); i++);
2226 for (j = i + 1; j < MAX_FIDS && (fids[j] & 0xffff0000); j++);
2227
2228 if (j >= MAX_FIDS) {
2229 netif_stop_queue(dev);
2230
2231 if (i == MAX_FIDS) {
2232 dev->stats.tx_fifo_errors++;
2233 return NETDEV_TX_BUSY;
2234 }
2235 }
2236 /* check min length*/
2237 len = ETH_ZLEN < skb->len ? skb->len : ETH_ZLEN;
2238 /* Mark fid as used & save length for later */
2239 fids[i] |= (len << 16);
2240 priv->xmit11.skb = skb;
2241 priv->xmit11.fid = i;
2242 if (down_trylock(&priv->sem) != 0) {
2243 set_bit(FLAG_PENDING_XMIT11, &priv->flags);
2244 netif_stop_queue(dev);
2245 set_bit(JOB_XMIT11, &priv->jobs);
2246 wake_up_interruptible(&priv->thr_wait);
2247 } else
2248 airo_end_xmit11(dev, false);
2249 return NETDEV_TX_OK;
2250}
2251
2252static void airo_read_stats(struct net_device *dev)
2253{
2254 struct airo_info *ai = dev->ml_priv;
2255 StatsRid stats_rid;
2256 __le32 *vals = stats_rid.vals;
2257
2258 clear_bit(JOB_STATS, &ai->jobs);
2259 if (ai->power.event) {
2260 up(&ai->sem);
2261 return;
2262 }
2263 readStatsRid(ai, &stats_rid, RID_STATS, 0);
2264 up(&ai->sem);
2265
2266 dev->stats.rx_packets = le32_to_cpu(vals[43]) + le32_to_cpu(vals[44]) +
2267 le32_to_cpu(vals[45]);
2268 dev->stats.tx_packets = le32_to_cpu(vals[39]) + le32_to_cpu(vals[40]) +
2269 le32_to_cpu(vals[41]);
2270 dev->stats.rx_bytes = le32_to_cpu(vals[92]);
2271 dev->stats.tx_bytes = le32_to_cpu(vals[91]);
2272 dev->stats.rx_errors = le32_to_cpu(vals[0]) + le32_to_cpu(vals[2]) +
2273 le32_to_cpu(vals[3]) + le32_to_cpu(vals[4]);
2274 dev->stats.tx_errors = le32_to_cpu(vals[42]) +
2275 dev->stats.tx_fifo_errors;
2276 dev->stats.multicast = le32_to_cpu(vals[43]);
2277 dev->stats.collisions = le32_to_cpu(vals[89]);
2278
2279 /* detailed rx_errors: */
2280 dev->stats.rx_length_errors = le32_to_cpu(vals[3]);
2281 dev->stats.rx_crc_errors = le32_to_cpu(vals[4]);
2282 dev->stats.rx_frame_errors = le32_to_cpu(vals[2]);
2283 dev->stats.rx_fifo_errors = le32_to_cpu(vals[0]);
2284}
2285
2286static struct net_device_stats *airo_get_stats(struct net_device *dev)
2287{
2288 struct airo_info *local = dev->ml_priv;
2289
2290 if (!test_bit(JOB_STATS, &local->jobs)) {
2291 set_bit(JOB_STATS, &local->jobs);
2292 wake_up_interruptible(&local->thr_wait);
2293 }
2294
2295 return &dev->stats;
2296}
2297
2298static void airo_set_promisc(struct airo_info *ai, bool may_sleep)
2299{
2300 Cmd cmd;
2301 Resp rsp;
2302
2303 memset(&cmd, 0, sizeof(cmd));
2304 cmd.cmd = CMD_SETMODE;
2305 clear_bit(JOB_PROMISC, &ai->jobs);
2306 cmd.parm0=(ai->flags&IFF_PROMISC) ? PROMISC : NOPROMISC;
2307 issuecommand(ai, &cmd, &rsp, may_sleep);
2308 up(&ai->sem);
2309}
2310
2311static void airo_set_multicast_list(struct net_device *dev)
2312{
2313 struct airo_info *ai = dev->ml_priv;
2314
2315 if ((dev->flags ^ ai->flags) & IFF_PROMISC) {
2316 change_bit(FLAG_PROMISC, &ai->flags);
2317 if (down_trylock(&ai->sem) != 0) {
2318 set_bit(JOB_PROMISC, &ai->jobs);
2319 wake_up_interruptible(&ai->thr_wait);
2320 } else
2321 airo_set_promisc(ai, false);
2322 }
2323
2324 if ((dev->flags&IFF_ALLMULTI) || !netdev_mc_empty(dev)) {
2325 /* Turn on multicast. (Should be already setup...) */
2326 }
2327}
2328
2329static int airo_set_mac_address(struct net_device *dev, void *p)
2330{
2331 struct airo_info *ai = dev->ml_priv;
2332 struct sockaddr *addr = p;
2333
2334 readConfigRid(ai, 1);
2335 memcpy (ai->config.macAddr, addr->sa_data, dev->addr_len);
2336 set_bit (FLAG_COMMIT, &ai->flags);
2337 disable_MAC(ai, 1);
2338 writeConfigRid (ai, 1);
2339 enable_MAC(ai, 1);
2340 dev_addr_set(ai->dev, addr->sa_data);
2341 if (ai->wifidev)
2342 dev_addr_set(ai->wifidev, addr->sa_data);
2343 return 0;
2344}
2345
2346static LIST_HEAD(airo_devices);
2347
2348static void add_airo_dev(struct airo_info *ai)
2349{
2350 /* Upper layers already keep track of PCI devices,
2351 * so we only need to remember our non-PCI cards. */
2352 if (!ai->pci)
2353 list_add_tail(&ai->dev_list, &airo_devices);
2354}
2355
2356static void del_airo_dev(struct airo_info *ai)
2357{
2358 if (!ai->pci)
2359 list_del(&ai->dev_list);
2360}
2361
2362static int airo_close(struct net_device *dev)
2363{
2364 struct airo_info *ai = dev->ml_priv;
2365
2366 netif_stop_queue(dev);
2367
2368 if (ai->wifidev != dev) {
2369#ifdef POWER_ON_DOWN
2370 /* Shut power to the card. The idea is that the user can save
2371 * power when he doesn't need the card with "ifconfig down".
2372 * That's the method that is most friendly towards the network
2373 * stack (i.e. the network stack won't try to broadcast
2374 * anything on the interface and routes are gone. Jean II */
2375 set_bit(FLAG_RADIO_DOWN, &ai->flags);
2376 disable_MAC(ai, 1);
2377#endif
2378 disable_interrupts(ai);
2379
2380 free_irq(dev->irq, dev);
2381
2382 set_bit(JOB_DIE, &ai->jobs);
2383 kthread_stop(ai->airo_thread_task);
2384 }
2385 return 0;
2386}
2387
2388void stop_airo_card(struct net_device *dev, int freeres)
2389{
2390 struct airo_info *ai = dev->ml_priv;
2391
2392 set_bit(FLAG_RADIO_DOWN, &ai->flags);
2393 disable_MAC(ai, 1);
2394 disable_interrupts(ai);
2395 takedown_proc_entry(dev, ai);
2396 if (test_bit(FLAG_REGISTERED, &ai->flags)) {
2397 unregister_netdev(dev);
2398 if (ai->wifidev) {
2399 unregister_netdev(ai->wifidev);
2400 free_netdev(ai->wifidev);
2401 ai->wifidev = NULL;
2402 }
2403 clear_bit(FLAG_REGISTERED, &ai->flags);
2404 }
2405 /*
2406 * Clean out tx queue
2407 */
2408 if (test_bit(FLAG_MPI, &ai->flags) && !skb_queue_empty(&ai->txq)) {
2409 struct sk_buff *skb = NULL;
2410 for (;(skb = skb_dequeue(&ai->txq));)
2411 dev_kfree_skb(skb);
2412 }
2413
2414 airo_networks_free (ai);
2415
2416 kfree(ai->flash);
2417 kfree(ai->rssi);
2418 kfree(ai->SSID);
2419 if (freeres) {
2420 /* PCMCIA frees this stuff, so only for PCI and ISA */
2421 release_region(dev->base_addr, 64);
2422 if (test_bit(FLAG_MPI, &ai->flags)) {
2423 if (ai->pci)
2424 mpi_unmap_card(ai->pci);
2425 if (ai->pcimem)
2426 iounmap(ai->pcimem);
2427 if (ai->pciaux)
2428 iounmap(ai->pciaux);
2429 dma_free_coherent(&ai->pci->dev, PCI_SHARED_LEN,
2430 ai->shared, ai->shared_dma);
2431 }
2432 }
2433 crypto_free_sync_skcipher(ai->tfm);
2434 del_airo_dev(ai);
2435 free_netdev(dev);
2436}
2437
2438EXPORT_SYMBOL(stop_airo_card);
2439
2440static int wll_header_parse(const struct sk_buff *skb, unsigned char *haddr)
2441{
2442 memcpy(haddr, skb_mac_header(skb) + 10, ETH_ALEN);
2443 return ETH_ALEN;
2444}
2445
2446static void mpi_unmap_card(struct pci_dev *pci)
2447{
2448 unsigned long mem_start = pci_resource_start(pci, 1);
2449 unsigned long mem_len = pci_resource_len(pci, 1);
2450 unsigned long aux_start = pci_resource_start(pci, 2);
2451 unsigned long aux_len = AUXMEMSIZE;
2452
2453 release_mem_region(aux_start, aux_len);
2454 release_mem_region(mem_start, mem_len);
2455}
2456
2457/*************************************************************
2458 * This routine assumes that descriptors have been setup .
2459 * Run at insmod time or after reset when the descriptors
2460 * have been initialized . Returns 0 if all is well nz
2461 * otherwise . Does not allocate memory but sets up card
2462 * using previously allocated descriptors.
2463 */
2464static int mpi_init_descriptors (struct airo_info *ai)
2465{
2466 Cmd cmd;
2467 Resp rsp;
2468 int i;
2469 int rc = SUCCESS;
2470
2471 /* Alloc card RX descriptors */
2472 netif_stop_queue(ai->dev);
2473
2474 memset(&rsp, 0, sizeof(rsp));
2475 memset(&cmd, 0, sizeof(cmd));
2476
2477 cmd.cmd = CMD_ALLOCATEAUX;
2478 cmd.parm0 = FID_RX;
2479 cmd.parm1 = (ai->rxfids[0].card_ram_off - ai->pciaux);
2480 cmd.parm2 = MPI_MAX_FIDS;
2481 rc = issuecommand(ai, &cmd, &rsp, true);
2482 if (rc != SUCCESS) {
2483 airo_print_err(ai->dev->name, "Couldn't allocate RX FID");
2484 return rc;
2485 }
2486
2487 for (i = 0; i<MPI_MAX_FIDS; i++) {
2488 memcpy_toio(ai->rxfids[i].card_ram_off,
2489 &ai->rxfids[i].rx_desc, sizeof(RxFid));
2490 }
2491
2492 /* Alloc card TX descriptors */
2493
2494 memset(&rsp, 0, sizeof(rsp));
2495 memset(&cmd, 0, sizeof(cmd));
2496
2497 cmd.cmd = CMD_ALLOCATEAUX;
2498 cmd.parm0 = FID_TX;
2499 cmd.parm1 = (ai->txfids[0].card_ram_off - ai->pciaux);
2500 cmd.parm2 = MPI_MAX_FIDS;
2501
2502 for (i = 0; i<MPI_MAX_FIDS; i++) {
2503 ai->txfids[i].tx_desc.valid = 1;
2504 memcpy_toio(ai->txfids[i].card_ram_off,
2505 &ai->txfids[i].tx_desc, sizeof(TxFid));
2506 }
2507 ai->txfids[i-1].tx_desc.eoc = 1; /* Last descriptor has EOC set */
2508
2509 rc = issuecommand(ai, &cmd, &rsp, true);
2510 if (rc != SUCCESS) {
2511 airo_print_err(ai->dev->name, "Couldn't allocate TX FID");
2512 return rc;
2513 }
2514
2515 /* Alloc card Rid descriptor */
2516 memset(&rsp, 0, sizeof(rsp));
2517 memset(&cmd, 0, sizeof(cmd));
2518
2519 cmd.cmd = CMD_ALLOCATEAUX;
2520 cmd.parm0 = RID_RW;
2521 cmd.parm1 = (ai->config_desc.card_ram_off - ai->pciaux);
2522 cmd.parm2 = 1; /* Magic number... */
2523 rc = issuecommand(ai, &cmd, &rsp, true);
2524 if (rc != SUCCESS) {
2525 airo_print_err(ai->dev->name, "Couldn't allocate RID");
2526 return rc;
2527 }
2528
2529 memcpy_toio(ai->config_desc.card_ram_off,
2530 &ai->config_desc.rid_desc, sizeof(Rid));
2531
2532 return rc;
2533}
2534
2535/*
2536 * We are setting up three things here:
2537 * 1) Map AUX memory for descriptors: Rid, TxFid, or RxFid.
2538 * 2) Map PCI memory for issuing commands.
2539 * 3) Allocate memory (shared) to send and receive ethernet frames.
2540 */
2541static int mpi_map_card(struct airo_info *ai, struct pci_dev *pci)
2542{
2543 unsigned long mem_start, mem_len, aux_start, aux_len;
2544 int rc = -1;
2545 int i;
2546 dma_addr_t busaddroff;
2547 unsigned char *vpackoff;
2548 unsigned char __iomem *pciaddroff;
2549
2550 mem_start = pci_resource_start(pci, 1);
2551 mem_len = pci_resource_len(pci, 1);
2552 aux_start = pci_resource_start(pci, 2);
2553 aux_len = AUXMEMSIZE;
2554
2555 if (!request_mem_region(mem_start, mem_len, DRV_NAME)) {
2556 airo_print_err("", "Couldn't get region %x[%x]",
2557 (int)mem_start, (int)mem_len);
2558 goto out;
2559 }
2560 if (!request_mem_region(aux_start, aux_len, DRV_NAME)) {
2561 airo_print_err("", "Couldn't get region %x[%x]",
2562 (int)aux_start, (int)aux_len);
2563 goto free_region1;
2564 }
2565
2566 ai->pcimem = ioremap(mem_start, mem_len);
2567 if (!ai->pcimem) {
2568 airo_print_err("", "Couldn't map region %x[%x]",
2569 (int)mem_start, (int)mem_len);
2570 goto free_region2;
2571 }
2572 ai->pciaux = ioremap(aux_start, aux_len);
2573 if (!ai->pciaux) {
2574 airo_print_err("", "Couldn't map region %x[%x]",
2575 (int)aux_start, (int)aux_len);
2576 goto free_memmap;
2577 }
2578
2579 /* Reserve PKTSIZE for each fid and 2K for the Rids */
2580 ai->shared = dma_alloc_coherent(&pci->dev, PCI_SHARED_LEN,
2581 &ai->shared_dma, GFP_KERNEL);
2582 if (!ai->shared) {
2583 airo_print_err("", "Couldn't alloc_coherent %d",
2584 PCI_SHARED_LEN);
2585 goto free_auxmap;
2586 }
2587
2588 /*
2589 * Setup descriptor RX, TX, CONFIG
2590 */
2591 busaddroff = ai->shared_dma;
2592 pciaddroff = ai->pciaux + AUX_OFFSET;
2593 vpackoff = ai->shared;
2594
2595 /* RX descriptor setup */
2596 for (i = 0; i < MPI_MAX_FIDS; i++) {
2597 ai->rxfids[i].pending = 0;
2598 ai->rxfids[i].card_ram_off = pciaddroff;
2599 ai->rxfids[i].virtual_host_addr = vpackoff;
2600 ai->rxfids[i].rx_desc.host_addr = busaddroff;
2601 ai->rxfids[i].rx_desc.valid = 1;
2602 ai->rxfids[i].rx_desc.len = PKTSIZE;
2603 ai->rxfids[i].rx_desc.rdy = 0;
2604
2605 pciaddroff += sizeof(RxFid);
2606 busaddroff += PKTSIZE;
2607 vpackoff += PKTSIZE;
2608 }
2609
2610 /* TX descriptor setup */
2611 for (i = 0; i < MPI_MAX_FIDS; i++) {
2612 ai->txfids[i].card_ram_off = pciaddroff;
2613 ai->txfids[i].virtual_host_addr = vpackoff;
2614 ai->txfids[i].tx_desc.valid = 1;
2615 ai->txfids[i].tx_desc.host_addr = busaddroff;
2616 memcpy(ai->txfids[i].virtual_host_addr,
2617 &wifictlhdr8023, sizeof(wifictlhdr8023));
2618
2619 pciaddroff += sizeof(TxFid);
2620 busaddroff += PKTSIZE;
2621 vpackoff += PKTSIZE;
2622 }
2623 ai->txfids[i-1].tx_desc.eoc = 1; /* Last descriptor has EOC set */
2624
2625 /* Rid descriptor setup */
2626 ai->config_desc.card_ram_off = pciaddroff;
2627 ai->config_desc.virtual_host_addr = vpackoff;
2628 ai->config_desc.rid_desc.host_addr = busaddroff;
2629 ai->ridbus = busaddroff;
2630 ai->config_desc.rid_desc.rid = 0;
2631 ai->config_desc.rid_desc.len = RIDSIZE;
2632 ai->config_desc.rid_desc.valid = 1;
2633 pciaddroff += sizeof(Rid);
2634 busaddroff += RIDSIZE;
2635 vpackoff += RIDSIZE;
2636
2637 /* Tell card about descriptors */
2638 if (mpi_init_descriptors (ai) != SUCCESS)
2639 goto free_shared;
2640
2641 return 0;
2642 free_shared:
2643 dma_free_coherent(&pci->dev, PCI_SHARED_LEN, ai->shared,
2644 ai->shared_dma);
2645 free_auxmap:
2646 iounmap(ai->pciaux);
2647 free_memmap:
2648 iounmap(ai->pcimem);
2649 free_region2:
2650 release_mem_region(aux_start, aux_len);
2651 free_region1:
2652 release_mem_region(mem_start, mem_len);
2653 out:
2654 return rc;
2655}
2656
2657static const struct header_ops airo_header_ops = {
2658 .parse = wll_header_parse,
2659};
2660
2661static const struct net_device_ops airo11_netdev_ops = {
2662 .ndo_open = airo_open,
2663 .ndo_stop = airo_close,
2664 .ndo_start_xmit = airo_start_xmit11,
2665 .ndo_get_stats = airo_get_stats,
2666 .ndo_set_mac_address = airo_set_mac_address,
2667 .ndo_siocdevprivate = airo_siocdevprivate,
2668};
2669
2670static void wifi_setup(struct net_device *dev)
2671{
2672 dev->netdev_ops = &airo11_netdev_ops;
2673 dev->header_ops = &airo_header_ops;
2674 dev->wireless_handlers = &airo_handler_def;
2675
2676 dev->type = ARPHRD_IEEE80211;
2677 dev->hard_header_len = ETH_HLEN;
2678 dev->mtu = AIRO_DEF_MTU;
2679 dev->min_mtu = 68;
2680 dev->max_mtu = MIC_MSGLEN_MAX;
2681 dev->addr_len = ETH_ALEN;
2682 dev->tx_queue_len = 100;
2683
2684 eth_broadcast_addr(dev->broadcast);
2685
2686 dev->flags = IFF_BROADCAST|IFF_MULTICAST;
2687}
2688
2689static struct net_device *init_wifidev(struct airo_info *ai,
2690 struct net_device *ethdev)
2691{
2692 int err;
2693 struct net_device *dev = alloc_netdev(0, "wifi%d", NET_NAME_UNKNOWN,
2694 wifi_setup);
2695 if (!dev)
2696 return NULL;
2697 dev->ml_priv = ethdev->ml_priv;
2698 dev->irq = ethdev->irq;
2699 dev->base_addr = ethdev->base_addr;
2700 dev->wireless_data = ethdev->wireless_data;
2701 SET_NETDEV_DEV(dev, ethdev->dev.parent);
2702 eth_hw_addr_inherit(dev, ethdev);
2703 err = register_netdev(dev);
2704 if (err<0) {
2705 free_netdev(dev);
2706 return NULL;
2707 }
2708 return dev;
2709}
2710
2711static int reset_card(struct net_device *dev, int lock)
2712{
2713 struct airo_info *ai = dev->ml_priv;
2714
2715 if (lock && down_interruptible(&ai->sem))
2716 return -1;
2717 waitbusy (ai);
2718 OUT4500(ai, COMMAND, CMD_SOFTRESET);
2719 msleep(200);
2720 waitbusy (ai);
2721 msleep(200);
2722 if (lock)
2723 up(&ai->sem);
2724 return 0;
2725}
2726
2727#define AIRO_MAX_NETWORK_COUNT 64
2728static int airo_networks_allocate(struct airo_info *ai)
2729{
2730 if (ai->networks)
2731 return 0;
2732
2733 ai->networks = kcalloc(AIRO_MAX_NETWORK_COUNT, sizeof(BSSListElement),
2734 GFP_KERNEL);
2735 if (!ai->networks) {
2736 airo_print_warn("", "Out of memory allocating beacons");
2737 return -ENOMEM;
2738 }
2739
2740 return 0;
2741}
2742
2743static void airo_networks_free(struct airo_info *ai)
2744{
2745 kfree(ai->networks);
2746 ai->networks = NULL;
2747}
2748
2749static void airo_networks_initialize(struct airo_info *ai)
2750{
2751 int i;
2752
2753 INIT_LIST_HEAD(&ai->network_free_list);
2754 INIT_LIST_HEAD(&ai->network_list);
2755 for (i = 0; i < AIRO_MAX_NETWORK_COUNT; i++)
2756 list_add_tail(&ai->networks[i].list,
2757 &ai->network_free_list);
2758}
2759
2760static const struct net_device_ops airo_netdev_ops = {
2761 .ndo_open = airo_open,
2762 .ndo_stop = airo_close,
2763 .ndo_start_xmit = airo_start_xmit,
2764 .ndo_get_stats = airo_get_stats,
2765 .ndo_set_rx_mode = airo_set_multicast_list,
2766 .ndo_set_mac_address = airo_set_mac_address,
2767 .ndo_siocdevprivate = airo_siocdevprivate,
2768 .ndo_validate_addr = eth_validate_addr,
2769};
2770
2771static const struct net_device_ops mpi_netdev_ops = {
2772 .ndo_open = airo_open,
2773 .ndo_stop = airo_close,
2774 .ndo_start_xmit = mpi_start_xmit,
2775 .ndo_get_stats = airo_get_stats,
2776 .ndo_set_rx_mode = airo_set_multicast_list,
2777 .ndo_set_mac_address = airo_set_mac_address,
2778 .ndo_siocdevprivate = airo_siocdevprivate,
2779 .ndo_validate_addr = eth_validate_addr,
2780};
2781
2782
2783static struct net_device *_init_airo_card(unsigned short irq, int port,
2784 int is_pcmcia, struct pci_dev *pci,
2785 struct device *dmdev)
2786{
2787 struct net_device *dev;
2788 struct airo_info *ai;
2789 int i, rc;
2790 CapabilityRid cap_rid;
2791
2792 /* Create the network device object. */
2793 dev = alloc_netdev(sizeof(*ai), "", NET_NAME_UNKNOWN, ether_setup);
2794 if (!dev) {
2795 airo_print_err("", "Couldn't alloc_etherdev");
2796 return NULL;
2797 }
2798
2799 ai = dev->ml_priv = netdev_priv(dev);
2800 ai->wifidev = NULL;
2801 ai->flags = 1 << FLAG_RADIO_DOWN;
2802 ai->jobs = 0;
2803 ai->dev = dev;
2804 if (pci && (pci->device == 0x5000 || pci->device == 0xa504)) {
2805 airo_print_dbg("", "Found an MPI350 card");
2806 set_bit(FLAG_MPI, &ai->flags);
2807 }
2808 spin_lock_init(&ai->aux_lock);
2809 sema_init(&ai->sem, 1);
2810 ai->config.len = 0;
2811 ai->pci = pci;
2812 init_waitqueue_head (&ai->thr_wait);
2813 ai->tfm = NULL;
2814 add_airo_dev(ai);
2815 ai->APList.len = cpu_to_le16(sizeof(struct APListRid));
2816
2817 if (airo_networks_allocate (ai))
2818 goto err_out_free;
2819 airo_networks_initialize (ai);
2820
2821 skb_queue_head_init (&ai->txq);
2822
2823 /* The Airo-specific entries in the device structure. */
2824 if (test_bit(FLAG_MPI,&ai->flags))
2825 dev->netdev_ops = &mpi_netdev_ops;
2826 else
2827 dev->netdev_ops = &airo_netdev_ops;
2828 dev->wireless_handlers = &airo_handler_def;
2829 ai->wireless_data.spy_data = &ai->spy_data;
2830 dev->wireless_data = &ai->wireless_data;
2831 dev->irq = irq;
2832 dev->base_addr = port;
2833 dev->priv_flags &= ~IFF_TX_SKB_SHARING;
2834 dev->max_mtu = MIC_MSGLEN_MAX;
2835
2836 SET_NETDEV_DEV(dev, dmdev);
2837
2838 reset_card (dev, 1);
2839 msleep(400);
2840
2841 if (!is_pcmcia) {
2842 if (!request_region(dev->base_addr, 64, DRV_NAME)) {
2843 rc = -EBUSY;
2844 airo_print_err(dev->name, "Couldn't request region");
2845 goto err_out_nets;
2846 }
2847 }
2848
2849 if (test_bit(FLAG_MPI,&ai->flags)) {
2850 if (mpi_map_card(ai, pci)) {
2851 airo_print_err("", "Could not map memory");
2852 goto err_out_res;
2853 }
2854 }
2855
2856 if (probe) {
2857 if (setup_card(ai, dev, 1) != SUCCESS) {
2858 airo_print_err(dev->name, "MAC could not be enabled");
2859 rc = -EIO;
2860 goto err_out_map;
2861 }
2862 } else if (!test_bit(FLAG_MPI,&ai->flags)) {
2863 ai->bap_read = fast_bap_read;
2864 set_bit(FLAG_FLASHING, &ai->flags);
2865 }
2866
2867 strcpy(dev->name, "eth%d");
2868 rc = register_netdev(dev);
2869 if (rc) {
2870 airo_print_err(dev->name, "Couldn't register_netdev");
2871 goto err_out_map;
2872 }
2873 ai->wifidev = init_wifidev(ai, dev);
2874 if (!ai->wifidev)
2875 goto err_out_reg;
2876
2877 rc = readCapabilityRid(ai, &cap_rid, 1);
2878 if (rc != SUCCESS) {
2879 rc = -EIO;
2880 goto err_out_wifi;
2881 }
2882 /* WEP capability discovery */
2883 ai->wep_capable = (cap_rid.softCap & cpu_to_le16(0x02)) ? 1 : 0;
2884 ai->max_wep_idx = (cap_rid.softCap & cpu_to_le16(0x80)) ? 3 : 0;
2885
2886 airo_print_info(dev->name, "Firmware version %x.%x.%02d",
2887 ((le16_to_cpu(cap_rid.softVer) >> 8) & 0xF),
2888 (le16_to_cpu(cap_rid.softVer) & 0xFF),
2889 le16_to_cpu(cap_rid.softSubVer));
2890
2891 /* Test for WPA support */
2892 /* Only firmware versions 5.30.17 or better can do WPA */
2893 if (le16_to_cpu(cap_rid.softVer) > 0x530
2894 || (le16_to_cpu(cap_rid.softVer) == 0x530
2895 && le16_to_cpu(cap_rid.softSubVer) >= 17)) {
2896 airo_print_info(ai->dev->name, "WPA supported.");
2897
2898 set_bit(FLAG_WPA_CAPABLE, &ai->flags);
2899 ai->bssListFirst = RID_WPA_BSSLISTFIRST;
2900 ai->bssListNext = RID_WPA_BSSLISTNEXT;
2901 ai->bssListRidLen = sizeof(BSSListRid);
2902 } else {
2903 airo_print_info(ai->dev->name, "WPA unsupported with firmware "
2904 "versions older than 5.30.17.");
2905
2906 ai->bssListFirst = RID_BSSLISTFIRST;
2907 ai->bssListNext = RID_BSSLISTNEXT;
2908 ai->bssListRidLen = sizeof(BSSListRid) - sizeof(BSSListRidExtra);
2909 }
2910
2911 set_bit(FLAG_REGISTERED,&ai->flags);
2912 airo_print_info(dev->name, "MAC enabled %pM", dev->dev_addr);
2913
2914 /* Allocate the transmit buffers */
2915 if (probe && !test_bit(FLAG_MPI,&ai->flags))
2916 for (i = 0; i < MAX_FIDS; i++)
2917 ai->fids[i] = transmit_allocate(ai, AIRO_DEF_MTU, i>=MAX_FIDS/2);
2918
2919 if (setup_proc_entry(dev, dev->ml_priv) < 0)
2920 goto err_out_wifi;
2921
2922 return dev;
2923
2924err_out_wifi:
2925 unregister_netdev(ai->wifidev);
2926 free_netdev(ai->wifidev);
2927err_out_reg:
2928 unregister_netdev(dev);
2929err_out_map:
2930 if (test_bit(FLAG_MPI,&ai->flags) && pci) {
2931 dma_free_coherent(&pci->dev, PCI_SHARED_LEN, ai->shared,
2932 ai->shared_dma);
2933 iounmap(ai->pciaux);
2934 iounmap(ai->pcimem);
2935 mpi_unmap_card(ai->pci);
2936 }
2937err_out_res:
2938 if (!is_pcmcia)
2939 release_region(dev->base_addr, 64);
2940err_out_nets:
2941 airo_networks_free(ai);
2942err_out_free:
2943 del_airo_dev(ai);
2944 free_netdev(dev);
2945 return NULL;
2946}
2947
2948struct net_device *init_airo_card(unsigned short irq, int port, int is_pcmcia,
2949 struct device *dmdev)
2950{
2951 return _init_airo_card (irq, port, is_pcmcia, NULL, dmdev);
2952}
2953
2954EXPORT_SYMBOL(init_airo_card);
2955
2956static int waitbusy (struct airo_info *ai)
2957{
2958 int delay = 0;
2959 while ((IN4500(ai, COMMAND) & COMMAND_BUSY) && (delay < 10000)) {
2960 udelay (10);
2961 if ((++delay % 20) == 0)
2962 OUT4500(ai, EVACK, EV_CLEARCOMMANDBUSY);
2963 }
2964 return delay < 10000;
2965}
2966
2967int reset_airo_card(struct net_device *dev)
2968{
2969 int i;
2970 struct airo_info *ai = dev->ml_priv;
2971
2972 if (reset_card (dev, 1))
2973 return -1;
2974
2975 if (setup_card(ai, dev, 1) != SUCCESS) {
2976 airo_print_err(dev->name, "MAC could not be enabled");
2977 return -1;
2978 }
2979 airo_print_info(dev->name, "MAC enabled %pM", dev->dev_addr);
2980 /* Allocate the transmit buffers if needed */
2981 if (!test_bit(FLAG_MPI,&ai->flags))
2982 for (i = 0; i < MAX_FIDS; i++)
2983 ai->fids[i] = transmit_allocate (ai, AIRO_DEF_MTU, i>=MAX_FIDS/2);
2984
2985 enable_interrupts(ai);
2986 netif_wake_queue(dev);
2987 return 0;
2988}
2989
2990EXPORT_SYMBOL(reset_airo_card);
2991
2992static void airo_send_event(struct net_device *dev)
2993{
2994 struct airo_info *ai = dev->ml_priv;
2995 union iwreq_data wrqu;
2996 StatusRid status_rid;
2997
2998 clear_bit(JOB_EVENT, &ai->jobs);
2999 PC4500_readrid(ai, RID_STATUS, &status_rid, sizeof(status_rid), 0);
3000 up(&ai->sem);
3001 wrqu.data.length = 0;
3002 wrqu.data.flags = 0;
3003 memcpy(wrqu.ap_addr.sa_data, status_rid.bssid[0], ETH_ALEN);
3004 wrqu.ap_addr.sa_family = ARPHRD_ETHER;
3005
3006 /* Send event to user space */
3007 wireless_send_event(dev, SIOCGIWAP, &wrqu, NULL);
3008}
3009
3010static void airo_process_scan_results (struct airo_info *ai)
3011{
3012 union iwreq_data wrqu;
3013 BSSListRid bss;
3014 int rc;
3015 BSSListElement * loop_net;
3016 BSSListElement * tmp_net;
3017
3018 /* Blow away current list of scan results */
3019 list_for_each_entry_safe (loop_net, tmp_net, &ai->network_list, list) {
3020 list_move_tail (&loop_net->list, &ai->network_free_list);
3021 /* Don't blow away ->list, just BSS data */
3022 memset (loop_net, 0, sizeof (loop_net->bss));
3023 }
3024
3025 /* Try to read the first entry of the scan result */
3026 rc = PC4500_readrid(ai, ai->bssListFirst, &bss, ai->bssListRidLen, 0);
3027 if ((rc) || (bss.index == cpu_to_le16(0xffff))) {
3028 /* No scan results */
3029 goto out;
3030 }
3031
3032 /* Read and parse all entries */
3033 tmp_net = NULL;
3034 while ((!rc) && (bss.index != cpu_to_le16(0xffff))) {
3035 /* Grab a network off the free list */
3036 if (!list_empty(&ai->network_free_list)) {
3037 tmp_net = list_entry(ai->network_free_list.next,
3038 BSSListElement, list);
3039 list_del(ai->network_free_list.next);
3040 }
3041
3042 if (tmp_net != NULL) {
3043 memcpy(tmp_net, &bss, sizeof(tmp_net->bss));
3044 list_add_tail(&tmp_net->list, &ai->network_list);
3045 tmp_net = NULL;
3046 }
3047
3048 /* Read next entry */
3049 rc = PC4500_readrid(ai, ai->bssListNext,
3050 &bss, ai->bssListRidLen, 0);
3051 }
3052
3053out:
3054 /* write APList back (we cleared it in airo_set_scan) */
3055 disable_MAC(ai, 2);
3056 writeAPListRid(ai, &ai->APList, 0);
3057 enable_MAC(ai, 0);
3058
3059 ai->scan_timeout = 0;
3060 clear_bit(JOB_SCAN_RESULTS, &ai->jobs);
3061 up(&ai->sem);
3062
3063 /* Send an empty event to user space.
3064 * We don't send the received data on
3065 * the event because it would require
3066 * us to do complex transcoding, and
3067 * we want to minimise the work done in
3068 * the irq handler. Use a request to
3069 * extract the data - Jean II */
3070 wrqu.data.length = 0;
3071 wrqu.data.flags = 0;
3072 wireless_send_event(ai->dev, SIOCGIWSCAN, &wrqu, NULL);
3073}
3074
3075static int airo_thread(void *data)
3076{
3077 struct net_device *dev = data;
3078 struct airo_info *ai = dev->ml_priv;
3079 int locked;
3080
3081 set_freezable();
3082 while (1) {
3083 /* make swsusp happy with our thread */
3084 try_to_freeze();
3085
3086 if (test_bit(JOB_DIE, &ai->jobs))
3087 break;
3088
3089 if (ai->jobs) {
3090 locked = down_interruptible(&ai->sem);
3091 } else {
3092 wait_queue_entry_t wait;
3093
3094 init_waitqueue_entry(&wait, current);
3095 add_wait_queue(&ai->thr_wait, &wait);
3096 for (;;) {
3097 set_current_state(TASK_INTERRUPTIBLE);
3098 if (ai->jobs)
3099 break;
3100 if (ai->expires || ai->scan_timeout) {
3101 if (ai->scan_timeout &&
3102 time_after_eq(jiffies, ai->scan_timeout)) {
3103 set_bit(JOB_SCAN_RESULTS, &ai->jobs);
3104 break;
3105 } else if (ai->expires &&
3106 time_after_eq(jiffies, ai->expires)) {
3107 set_bit(JOB_AUTOWEP, &ai->jobs);
3108 break;
3109 }
3110 if (!kthread_should_stop() &&
3111 !freezing(current)) {
3112 unsigned long wake_at;
3113 if (!ai->expires || !ai->scan_timeout) {
3114 wake_at = max(ai->expires,
3115 ai->scan_timeout);
3116 } else {
3117 wake_at = min(ai->expires,
3118 ai->scan_timeout);
3119 }
3120 schedule_timeout(wake_at - jiffies);
3121 continue;
3122 }
3123 } else if (!kthread_should_stop() &&
3124 !freezing(current)) {
3125 schedule();
3126 continue;
3127 }
3128 break;
3129 }
3130 __set_current_state(TASK_RUNNING);
3131 remove_wait_queue(&ai->thr_wait, &wait);
3132 locked = 1;
3133 }
3134
3135 if (locked)
3136 continue;
3137
3138 if (test_bit(JOB_DIE, &ai->jobs)) {
3139 up(&ai->sem);
3140 break;
3141 }
3142
3143 if (ai->power.event || test_bit(FLAG_FLASHING, &ai->flags)) {
3144 up(&ai->sem);
3145 continue;
3146 }
3147
3148 if (test_bit(JOB_XMIT, &ai->jobs))
3149 airo_end_xmit(dev, true);
3150 else if (test_bit(JOB_XMIT11, &ai->jobs))
3151 airo_end_xmit11(dev, true);
3152 else if (test_bit(JOB_STATS, &ai->jobs))
3153 airo_read_stats(dev);
3154 else if (test_bit(JOB_PROMISC, &ai->jobs))
3155 airo_set_promisc(ai, true);
3156 else if (test_bit(JOB_MIC, &ai->jobs))
3157 micinit(ai);
3158 else if (test_bit(JOB_EVENT, &ai->jobs))
3159 airo_send_event(dev);
3160 else if (test_bit(JOB_AUTOWEP, &ai->jobs))
3161 timer_func(dev);
3162 else if (test_bit(JOB_SCAN_RESULTS, &ai->jobs))
3163 airo_process_scan_results(ai);
3164 else /* Shouldn't get here, but we make sure to unlock */
3165 up(&ai->sem);
3166 }
3167
3168 return 0;
3169}
3170
3171static int header_len(__le16 ctl)
3172{
3173 u16 fc = le16_to_cpu(ctl);
3174 switch (fc & 0xc) {
3175 case 4:
3176 if ((fc & 0xe0) == 0xc0)
3177 return 10; /* one-address control packet */
3178 return 16; /* two-address control packet */
3179 case 8:
3180 if ((fc & 0x300) == 0x300)
3181 return 30; /* WDS packet */
3182 }
3183 return 24;
3184}
3185
3186static void airo_handle_cisco_mic(struct airo_info *ai)
3187{
3188 if (test_bit(FLAG_MIC_CAPABLE, &ai->flags)) {
3189 set_bit(JOB_MIC, &ai->jobs);
3190 wake_up_interruptible(&ai->thr_wait);
3191 }
3192}
3193
3194/* Airo Status codes */
3195#define STAT_NOBEACON 0x8000 /* Loss of sync - missed beacons */
3196#define STAT_MAXRETRIES 0x8001 /* Loss of sync - max retries */
3197#define STAT_MAXARL 0x8002 /* Loss of sync - average retry level exceeded*/
3198#define STAT_FORCELOSS 0x8003 /* Loss of sync - host request */
3199#define STAT_TSFSYNC 0x8004 /* Loss of sync - TSF synchronization */
3200#define STAT_DEAUTH 0x8100 /* low byte is 802.11 reason code */
3201#define STAT_DISASSOC 0x8200 /* low byte is 802.11 reason code */
3202#define STAT_ASSOC_FAIL 0x8400 /* low byte is 802.11 reason code */
3203#define STAT_AUTH_FAIL 0x0300 /* low byte is 802.11 reason code */
3204#define STAT_ASSOC 0x0400 /* Associated */
3205#define STAT_REASSOC 0x0600 /* Reassociated? Only on firmware >= 5.30.17 */
3206
3207static void airo_print_status(const char *devname, u16 status)
3208{
3209 u8 reason = status & 0xFF;
3210
3211 switch (status & 0xFF00) {
3212 case STAT_NOBEACON:
3213 switch (status) {
3214 case STAT_NOBEACON:
3215 airo_print_dbg(devname, "link lost (missed beacons)");
3216 break;
3217 case STAT_MAXRETRIES:
3218 case STAT_MAXARL:
3219 airo_print_dbg(devname, "link lost (max retries)");
3220 break;
3221 case STAT_FORCELOSS:
3222 airo_print_dbg(devname, "link lost (local choice)");
3223 break;
3224 case STAT_TSFSYNC:
3225 airo_print_dbg(devname, "link lost (TSF sync lost)");
3226 break;
3227 default:
3228 airo_print_dbg(devname, "unknown status %x\n", status);
3229 break;
3230 }
3231 break;
3232 case STAT_DEAUTH:
3233 airo_print_dbg(devname, "deauthenticated (reason: %d)", reason);
3234 break;
3235 case STAT_DISASSOC:
3236 airo_print_dbg(devname, "disassociated (reason: %d)", reason);
3237 break;
3238 case STAT_ASSOC_FAIL:
3239 airo_print_dbg(devname, "association failed (reason: %d)",
3240 reason);
3241 break;
3242 case STAT_AUTH_FAIL:
3243 airo_print_dbg(devname, "authentication failed (reason: %d)",
3244 reason);
3245 break;
3246 case STAT_ASSOC:
3247 case STAT_REASSOC:
3248 break;
3249 default:
3250 airo_print_dbg(devname, "unknown status %x\n", status);
3251 break;
3252 }
3253}
3254
3255static void airo_handle_link(struct airo_info *ai)
3256{
3257 union iwreq_data wrqu;
3258 int scan_forceloss = 0;
3259 u16 status;
3260
3261 /* Get new status and acknowledge the link change */
3262 status = le16_to_cpu(IN4500(ai, LINKSTAT));
3263 OUT4500(ai, EVACK, EV_LINK);
3264
3265 if ((status == STAT_FORCELOSS) && (ai->scan_timeout > 0))
3266 scan_forceloss = 1;
3267
3268 airo_print_status(ai->dev->name, status);
3269
3270 if ((status == STAT_ASSOC) || (status == STAT_REASSOC)) {
3271 if (auto_wep)
3272 ai->expires = 0;
3273 if (ai->list_bss_task)
3274 wake_up_process(ai->list_bss_task);
3275 set_bit(FLAG_UPDATE_UNI, &ai->flags);
3276 set_bit(FLAG_UPDATE_MULTI, &ai->flags);
3277
3278 set_bit(JOB_EVENT, &ai->jobs);
3279 wake_up_interruptible(&ai->thr_wait);
3280
3281 netif_carrier_on(ai->dev);
3282 } else if (!scan_forceloss) {
3283 if (auto_wep && !ai->expires) {
3284 ai->expires = RUN_AT(3*HZ);
3285 wake_up_interruptible(&ai->thr_wait);
3286 }
3287
3288 /* Send event to user space */
3289 eth_zero_addr(wrqu.ap_addr.sa_data);
3290 wrqu.ap_addr.sa_family = ARPHRD_ETHER;
3291 wireless_send_event(ai->dev, SIOCGIWAP, &wrqu, NULL);
3292 netif_carrier_off(ai->dev);
3293 } else {
3294 netif_carrier_off(ai->dev);
3295 }
3296}
3297
3298static void airo_handle_rx(struct airo_info *ai)
3299{
3300 struct sk_buff *skb = NULL;
3301 __le16 fc, v, *buffer, tmpbuf[4];
3302 u16 len, hdrlen = 0, gap, fid;
3303 struct rx_hdr hdr;
3304 int success = 0;
3305
3306 if (test_bit(FLAG_MPI, &ai->flags)) {
3307 if (test_bit(FLAG_802_11, &ai->flags))
3308 mpi_receive_802_11(ai);
3309 else
3310 mpi_receive_802_3(ai);
3311 OUT4500(ai, EVACK, EV_RX);
3312 return;
3313 }
3314
3315 fid = IN4500(ai, RXFID);
3316
3317 /* Get the packet length */
3318 if (test_bit(FLAG_802_11, &ai->flags)) {
3319 bap_setup (ai, fid, 4, BAP0);
3320 bap_read (ai, (__le16*)&hdr, sizeof(hdr), BAP0);
3321 /* Bad CRC. Ignore packet */
3322 if (le16_to_cpu(hdr.status) & 2)
3323 hdr.len = 0;
3324 if (ai->wifidev == NULL)
3325 hdr.len = 0;
3326 } else {
3327 bap_setup(ai, fid, 0x36, BAP0);
3328 bap_read(ai, &hdr.len, 2, BAP0);
3329 }
3330 len = le16_to_cpu(hdr.len);
3331
3332 if (len > AIRO_DEF_MTU) {
3333 airo_print_err(ai->dev->name, "Bad size %d", len);
3334 goto done;
3335 }
3336 if (len == 0)
3337 goto done;
3338
3339 if (test_bit(FLAG_802_11, &ai->flags)) {
3340 bap_read(ai, &fc, sizeof (fc), BAP0);
3341 hdrlen = header_len(fc);
3342 } else
3343 hdrlen = ETH_ALEN * 2;
3344
3345 skb = dev_alloc_skb(len + hdrlen + 2 + 2);
3346 if (!skb) {
3347 ai->dev->stats.rx_dropped++;
3348 goto done;
3349 }
3350
3351 skb_reserve(skb, 2); /* This way the IP header is aligned */
3352 buffer = skb_put(skb, len + hdrlen);
3353 if (test_bit(FLAG_802_11, &ai->flags)) {
3354 buffer[0] = fc;
3355 bap_read(ai, buffer + 1, hdrlen - 2, BAP0);
3356 if (hdrlen == 24)
3357 bap_read(ai, tmpbuf, 6, BAP0);
3358
3359 bap_read(ai, &v, sizeof(v), BAP0);
3360 gap = le16_to_cpu(v);
3361 if (gap) {
3362 if (gap <= 8) {
3363 bap_read(ai, tmpbuf, gap, BAP0);
3364 } else {
3365 airo_print_err(ai->dev->name, "gaplen too "
3366 "big. Problems will follow...");
3367 }
3368 }
3369 bap_read(ai, buffer + hdrlen/2, len, BAP0);
3370 } else {
3371 MICBuffer micbuf;
3372
3373 bap_read(ai, buffer, ETH_ALEN * 2, BAP0);
3374 if (ai->micstats.enabled) {
3375 bap_read(ai, (__le16 *) &micbuf, sizeof (micbuf), BAP0);
3376 if (ntohs(micbuf.typelen) > 0x05DC)
3377 bap_setup(ai, fid, 0x44, BAP0);
3378 else {
3379 if (len <= sizeof (micbuf)) {
3380 dev_kfree_skb_irq(skb);
3381 goto done;
3382 }
3383
3384 len -= sizeof(micbuf);
3385 skb_trim(skb, len + hdrlen);
3386 }
3387 }
3388
3389 bap_read(ai, buffer + ETH_ALEN, len, BAP0);
3390 if (decapsulate(ai, &micbuf, (etherHead*) buffer, len))
3391 dev_kfree_skb_irq (skb);
3392 else
3393 success = 1;
3394 }
3395
3396#ifdef WIRELESS_SPY
3397 if (success && (ai->spy_data.spy_number > 0)) {
3398 char *sa;
3399 struct iw_quality wstats;
3400
3401 /* Prepare spy data : addr + qual */
3402 if (!test_bit(FLAG_802_11, &ai->flags)) {
3403 sa = (char *) buffer + 6;
3404 bap_setup(ai, fid, 8, BAP0);
3405 bap_read(ai, (__le16 *) hdr.rssi, 2, BAP0);
3406 } else
3407 sa = (char *) buffer + 10;
3408 wstats.qual = hdr.rssi[0];
3409 if (ai->rssi)
3410 wstats.level = 0x100 - ai->rssi[hdr.rssi[1]].rssidBm;
3411 else
3412 wstats.level = (hdr.rssi[1] + 321) / 2;
3413 wstats.noise = ai->wstats.qual.noise;
3414 wstats.updated = IW_QUAL_LEVEL_UPDATED
3415 | IW_QUAL_QUAL_UPDATED
3416 | IW_QUAL_DBM;
3417 /* Update spy records */
3418 wireless_spy_update(ai->dev, sa, &wstats);
3419 }
3420#endif /* WIRELESS_SPY */
3421
3422done:
3423 OUT4500(ai, EVACK, EV_RX);
3424
3425 if (success) {
3426 if (test_bit(FLAG_802_11, &ai->flags)) {
3427 skb_reset_mac_header(skb);
3428 skb->pkt_type = PACKET_OTHERHOST;
3429 skb->dev = ai->wifidev;
3430 skb->protocol = htons(ETH_P_802_2);
3431 } else
3432 skb->protocol = eth_type_trans(skb, ai->dev);
3433 skb->ip_summed = CHECKSUM_NONE;
3434
3435 netif_rx(skb);
3436 }
3437}
3438
3439static void airo_handle_tx(struct airo_info *ai, u16 status)
3440{
3441 int i, index = -1;
3442 u16 fid;
3443
3444 if (test_bit(FLAG_MPI, &ai->flags)) {
3445 unsigned long flags;
3446
3447 if (status & EV_TXEXC)
3448 get_tx_error(ai, -1);
3449
3450 spin_lock_irqsave(&ai->aux_lock, flags);
3451 if (!skb_queue_empty(&ai->txq)) {
3452 spin_unlock_irqrestore(&ai->aux_lock, flags);
3453 mpi_send_packet(ai->dev);
3454 } else {
3455 clear_bit(FLAG_PENDING_XMIT, &ai->flags);
3456 spin_unlock_irqrestore(&ai->aux_lock, flags);
3457 netif_wake_queue(ai->dev);
3458 }
3459 OUT4500(ai, EVACK, status & (EV_TX | EV_TXCPY | EV_TXEXC));
3460 return;
3461 }
3462
3463 fid = IN4500(ai, TXCOMPLFID);
3464
3465 for (i = 0; i < MAX_FIDS; i++) {
3466 if ((ai->fids[i] & 0xffff) == fid)
3467 index = i;
3468 }
3469
3470 if (index != -1) {
3471 if (status & EV_TXEXC)
3472 get_tx_error(ai, index);
3473
3474 OUT4500(ai, EVACK, status & (EV_TX | EV_TXEXC));
3475
3476 /* Set up to be used again */
3477 ai->fids[index] &= 0xffff;
3478 if (index < MAX_FIDS / 2) {
3479 if (!test_bit(FLAG_PENDING_XMIT, &ai->flags))
3480 netif_wake_queue(ai->dev);
3481 } else {
3482 if (!test_bit(FLAG_PENDING_XMIT11, &ai->flags))
3483 netif_wake_queue(ai->wifidev);
3484 }
3485 } else {
3486 OUT4500(ai, EVACK, status & (EV_TX | EV_TXCPY | EV_TXEXC));
3487 airo_print_err(ai->dev->name, "Unallocated FID was used to xmit");
3488 }
3489}
3490
3491static irqreturn_t airo_interrupt(int irq, void *dev_id)
3492{
3493 struct net_device *dev = dev_id;
3494 u16 status, savedInterrupts = 0;
3495 struct airo_info *ai = dev->ml_priv;
3496 int handled = 0;
3497
3498 if (!netif_device_present(dev))
3499 return IRQ_NONE;
3500
3501 for (;;) {
3502 status = IN4500(ai, EVSTAT);
3503 if (!(status & STATUS_INTS) || (status == 0xffff))
3504 break;
3505
3506 handled = 1;
3507
3508 if (status & EV_AWAKE) {
3509 OUT4500(ai, EVACK, EV_AWAKE);
3510 OUT4500(ai, EVACK, EV_AWAKE);
3511 }
3512
3513 if (!savedInterrupts) {
3514 savedInterrupts = IN4500(ai, EVINTEN);
3515 OUT4500(ai, EVINTEN, 0);
3516 }
3517
3518 if (status & EV_MIC) {
3519 OUT4500(ai, EVACK, EV_MIC);
3520 airo_handle_cisco_mic(ai);
3521 }
3522
3523 if (status & EV_LINK) {
3524 /* Link status changed */
3525 airo_handle_link(ai);
3526 }
3527
3528 /* Check to see if there is something to receive */
3529 if (status & EV_RX)
3530 airo_handle_rx(ai);
3531
3532 /* Check to see if a packet has been transmitted */
3533 if (status & (EV_TX | EV_TXCPY | EV_TXEXC))
3534 airo_handle_tx(ai, status);
3535
3536 if (status & ~STATUS_INTS & ~IGNORE_INTS) {
3537 airo_print_warn(ai->dev->name, "Got weird status %x",
3538 status & ~STATUS_INTS & ~IGNORE_INTS);
3539 }
3540 }
3541
3542 if (savedInterrupts)
3543 OUT4500(ai, EVINTEN, savedInterrupts);
3544
3545 return IRQ_RETVAL(handled);
3546}
3547
3548/*
3549 * Routines to talk to the card
3550 */
3551
3552/*
3553 * This was originally written for the 4500, hence the name
3554 * NOTE: If use with 8bit mode and SMP bad things will happen!
3555 * Why would some one do 8 bit IO in an SMP machine?!?
3556 */
3557static void OUT4500(struct airo_info *ai, u16 reg, u16 val)
3558{
3559 if (test_bit(FLAG_MPI,&ai->flags))
3560 reg <<= 1;
3561 if (!do8bitIO)
3562 outw(val, ai->dev->base_addr + reg);
3563 else {
3564 outb(val & 0xff, ai->dev->base_addr + reg);
3565 outb(val >> 8, ai->dev->base_addr + reg + 1);
3566 }
3567}
3568
3569static u16 IN4500(struct airo_info *ai, u16 reg)
3570{
3571 unsigned short rc;
3572
3573 if (test_bit(FLAG_MPI,&ai->flags))
3574 reg <<= 1;
3575 if (!do8bitIO)
3576 rc = inw(ai->dev->base_addr + reg);
3577 else {
3578 rc = inb(ai->dev->base_addr + reg);
3579 rc += ((int)inb(ai->dev->base_addr + reg + 1)) << 8;
3580 }
3581 return rc;
3582}
3583
3584static int enable_MAC(struct airo_info *ai, int lock)
3585{
3586 int rc;
3587 Cmd cmd;
3588 Resp rsp;
3589
3590 /* FLAG_RADIO_OFF : Radio disabled via /proc or Wireless Extensions
3591 * FLAG_RADIO_DOWN : Radio disabled via "ifconfig ethX down"
3592 * Note : we could try to use !netif_running(dev) in enable_MAC()
3593 * instead of this flag, but I don't trust it *within* the
3594 * open/close functions, and testing both flags together is
3595 * "cheaper" - Jean II */
3596 if (ai->flags & FLAG_RADIO_MASK) return SUCCESS;
3597
3598 if (lock && down_interruptible(&ai->sem))
3599 return -ERESTARTSYS;
3600
3601 if (!test_bit(FLAG_ENABLED, &ai->flags)) {
3602 memset(&cmd, 0, sizeof(cmd));
3603 cmd.cmd = MAC_ENABLE;
3604 rc = issuecommand(ai, &cmd, &rsp, true);
3605 if (rc == SUCCESS)
3606 set_bit(FLAG_ENABLED, &ai->flags);
3607 } else
3608 rc = SUCCESS;
3609
3610 if (lock)
3611 up(&ai->sem);
3612
3613 if (rc)
3614 airo_print_err(ai->dev->name, "Cannot enable MAC");
3615 else if ((rsp.status & 0xFF00) != 0) {
3616 airo_print_err(ai->dev->name, "Bad MAC enable reason=%x, "
3617 "rid=%x, offset=%d", rsp.rsp0, rsp.rsp1, rsp.rsp2);
3618 rc = ERROR;
3619 }
3620 return rc;
3621}
3622
3623static void disable_MAC(struct airo_info *ai, int lock)
3624{
3625 Cmd cmd;
3626 Resp rsp;
3627
3628 if (lock == 1 && down_interruptible(&ai->sem))
3629 return;
3630
3631 if (test_bit(FLAG_ENABLED, &ai->flags)) {
3632 if (lock != 2) /* lock == 2 means don't disable carrier */
3633 netif_carrier_off(ai->dev);
3634 memset(&cmd, 0, sizeof(cmd));
3635 cmd.cmd = MAC_DISABLE; // disable in case already enabled
3636 issuecommand(ai, &cmd, &rsp, true);
3637 clear_bit(FLAG_ENABLED, &ai->flags);
3638 }
3639 if (lock == 1)
3640 up(&ai->sem);
3641}
3642
3643static void enable_interrupts(struct airo_info *ai)
3644{
3645 /* Enable the interrupts */
3646 OUT4500(ai, EVINTEN, STATUS_INTS);
3647}
3648
3649static void disable_interrupts(struct airo_info *ai)
3650{
3651 OUT4500(ai, EVINTEN, 0);
3652}
3653
3654static void mpi_receive_802_3(struct airo_info *ai)
3655{
3656 RxFid rxd;
3657 int len = 0;
3658 struct sk_buff *skb;
3659 char *buffer;
3660 int off = 0;
3661 MICBuffer micbuf;
3662
3663 memcpy_fromio(&rxd, ai->rxfids[0].card_ram_off, sizeof(rxd));
3664 /* Make sure we got something */
3665 if (rxd.rdy && rxd.valid == 0) {
3666 len = rxd.len + 12;
3667 if (len < 12 || len > 2048)
3668 goto badrx;
3669
3670 skb = dev_alloc_skb(len);
3671 if (!skb) {
3672 ai->dev->stats.rx_dropped++;
3673 goto badrx;
3674 }
3675 buffer = skb_put(skb, len);
3676 memcpy(buffer, ai->rxfids[0].virtual_host_addr, ETH_ALEN * 2);
3677 if (ai->micstats.enabled) {
3678 memcpy(&micbuf,
3679 ai->rxfids[0].virtual_host_addr + ETH_ALEN * 2,
3680 sizeof(micbuf));
3681 if (ntohs(micbuf.typelen) <= 0x05DC) {
3682 if (len <= sizeof(micbuf) + ETH_ALEN * 2)
3683 goto badmic;
3684
3685 off = sizeof(micbuf);
3686 skb_trim (skb, len - off);
3687 }
3688 }
3689 memcpy(buffer + ETH_ALEN * 2,
3690 ai->rxfids[0].virtual_host_addr + ETH_ALEN * 2 + off,
3691 len - ETH_ALEN * 2 - off);
3692 if (decapsulate (ai, &micbuf, (etherHead*)buffer, len - off - ETH_ALEN * 2)) {
3693badmic:
3694 dev_kfree_skb_irq (skb);
3695 goto badrx;
3696 }
3697#ifdef WIRELESS_SPY
3698 if (ai->spy_data.spy_number > 0) {
3699 char *sa;
3700 struct iw_quality wstats;
3701 /* Prepare spy data : addr + qual */
3702 sa = buffer + ETH_ALEN;
3703 wstats.qual = 0; /* XXX Where do I get that info from ??? */
3704 wstats.level = 0;
3705 wstats.updated = 0;
3706 /* Update spy records */
3707 wireless_spy_update(ai->dev, sa, &wstats);
3708 }
3709#endif /* WIRELESS_SPY */
3710
3711 skb->ip_summed = CHECKSUM_NONE;
3712 skb->protocol = eth_type_trans(skb, ai->dev);
3713 netif_rx(skb);
3714 }
3715badrx:
3716 if (rxd.valid == 0) {
3717 rxd.valid = 1;
3718 rxd.rdy = 0;
3719 rxd.len = PKTSIZE;
3720 memcpy_toio(ai->rxfids[0].card_ram_off, &rxd, sizeof(rxd));
3721 }
3722}
3723
3724static void mpi_receive_802_11(struct airo_info *ai)
3725{
3726 RxFid rxd;
3727 struct sk_buff *skb = NULL;
3728 u16 len, hdrlen = 0;
3729 __le16 fc;
3730 struct rx_hdr hdr;
3731 u16 gap;
3732 u16 *buffer;
3733 char *ptr = ai->rxfids[0].virtual_host_addr + 4;
3734
3735 memcpy_fromio(&rxd, ai->rxfids[0].card_ram_off, sizeof(rxd));
3736 memcpy ((char *)&hdr, ptr, sizeof(hdr));
3737 ptr += sizeof(hdr);
3738 /* Bad CRC. Ignore packet */
3739 if (le16_to_cpu(hdr.status) & 2)
3740 hdr.len = 0;
3741 if (ai->wifidev == NULL)
3742 hdr.len = 0;
3743 len = le16_to_cpu(hdr.len);
3744 if (len > AIRO_DEF_MTU) {
3745 airo_print_err(ai->dev->name, "Bad size %d", len);
3746 goto badrx;
3747 }
3748 if (len == 0)
3749 goto badrx;
3750
3751 fc = get_unaligned((__le16 *)ptr);
3752 hdrlen = header_len(fc);
3753
3754 skb = dev_alloc_skb(len + hdrlen + 2);
3755 if (!skb) {
3756 ai->dev->stats.rx_dropped++;
3757 goto badrx;
3758 }
3759 buffer = skb_put(skb, len + hdrlen);
3760 memcpy ((char *)buffer, ptr, hdrlen);
3761 ptr += hdrlen;
3762 if (hdrlen == 24)
3763 ptr += 6;
3764 gap = get_unaligned_le16(ptr);
3765 ptr += sizeof(__le16);
3766 if (gap) {
3767 if (gap <= 8)
3768 ptr += gap;
3769 else
3770 airo_print_err(ai->dev->name,
3771 "gaplen too big. Problems will follow...");
3772 }
3773 memcpy ((char *)buffer + hdrlen, ptr, len);
3774 ptr += len;
3775#ifdef IW_WIRELESS_SPY /* defined in iw_handler.h */
3776 if (ai->spy_data.spy_number > 0) {
3777 char *sa;
3778 struct iw_quality wstats;
3779 /* Prepare spy data : addr + qual */
3780 sa = (char*)buffer + 10;
3781 wstats.qual = hdr.rssi[0];
3782 if (ai->rssi)
3783 wstats.level = 0x100 - ai->rssi[hdr.rssi[1]].rssidBm;
3784 else
3785 wstats.level = (hdr.rssi[1] + 321) / 2;
3786 wstats.noise = ai->wstats.qual.noise;
3787 wstats.updated = IW_QUAL_QUAL_UPDATED
3788 | IW_QUAL_LEVEL_UPDATED
3789 | IW_QUAL_DBM;
3790 /* Update spy records */
3791 wireless_spy_update(ai->dev, sa, &wstats);
3792 }
3793#endif /* IW_WIRELESS_SPY */
3794 skb_reset_mac_header(skb);
3795 skb->pkt_type = PACKET_OTHERHOST;
3796 skb->dev = ai->wifidev;
3797 skb->protocol = htons(ETH_P_802_2);
3798 skb->ip_summed = CHECKSUM_NONE;
3799 netif_rx(skb);
3800
3801badrx:
3802 if (rxd.valid == 0) {
3803 rxd.valid = 1;
3804 rxd.rdy = 0;
3805 rxd.len = PKTSIZE;
3806 memcpy_toio(ai->rxfids[0].card_ram_off, &rxd, sizeof(rxd));
3807 }
3808}
3809
3810static inline void set_auth_type(struct airo_info *local, int auth_type)
3811{
3812 local->config.authType = auth_type;
3813 /* Cache the last auth type used (of AUTH_OPEN and AUTH_ENCRYPT).
3814 * Used by airo_set_auth()
3815 */
3816 if (auth_type == AUTH_OPEN || auth_type == AUTH_ENCRYPT)
3817 local->last_auth = auth_type;
3818}
3819
3820static int noinline_for_stack airo_readconfig(struct airo_info *ai,
3821 struct net_device *dev, int lock)
3822{
3823 int i, status;
3824 /* large variables, so don't inline this function,
3825 * maybe change to kmalloc
3826 */
3827 tdsRssiRid rssi_rid;
3828 CapabilityRid cap_rid;
3829
3830 kfree(ai->SSID);
3831 ai->SSID = NULL;
3832 // general configuration (read/modify/write)
3833 status = readConfigRid(ai, lock);
3834 if (status != SUCCESS) return ERROR;
3835
3836 status = readCapabilityRid(ai, &cap_rid, lock);
3837 if (status != SUCCESS) return ERROR;
3838
3839 status = PC4500_readrid(ai, RID_RSSI, &rssi_rid, sizeof(rssi_rid), lock);
3840 if (status == SUCCESS) {
3841 if (ai->rssi || (ai->rssi = kmalloc(512, GFP_KERNEL)) != NULL)
3842 memcpy(ai->rssi, (u8*)&rssi_rid + 2, 512); /* Skip RID length member */
3843 }
3844 else {
3845 kfree(ai->rssi);
3846 ai->rssi = NULL;
3847 if (cap_rid.softCap & cpu_to_le16(8))
3848 ai->config.rmode |= RXMODE_NORMALIZED_RSSI;
3849 else
3850 airo_print_warn(ai->dev->name, "unknown received signal "
3851 "level scale");
3852 }
3853 ai->config.opmode = adhoc ? MODE_STA_IBSS : MODE_STA_ESS;
3854 set_auth_type(ai, AUTH_OPEN);
3855 ai->config.modulation = MOD_CCK;
3856
3857 if (le16_to_cpu(cap_rid.len) >= sizeof(cap_rid) &&
3858 (cap_rid.extSoftCap & cpu_to_le16(1)) &&
3859 micsetup(ai) == SUCCESS) {
3860 ai->config.opmode |= MODE_MIC;
3861 set_bit(FLAG_MIC_CAPABLE, &ai->flags);
3862 }
3863
3864 /* Save off the MAC */
3865 eth_hw_addr_set(dev, ai->config.macAddr);
3866
3867 /* Check to see if there are any insmod configured
3868 rates to add */
3869 if (rates[0]) {
3870 memset(ai->config.rates, 0, sizeof(ai->config.rates));
3871 for (i = 0; i < 8 && rates[i]; i++) {
3872 ai->config.rates[i] = rates[i];
3873 }
3874 }
3875 set_bit (FLAG_COMMIT, &ai->flags);
3876
3877 return SUCCESS;
3878}
3879
3880
3881static u16 setup_card(struct airo_info *ai, struct net_device *dev, int lock)
3882{
3883 Cmd cmd;
3884 Resp rsp;
3885 int status;
3886 SsidRid mySsid;
3887 __le16 lastindex;
3888 WepKeyRid wkr;
3889 int rc;
3890
3891 memset(&mySsid, 0, sizeof(mySsid));
3892 kfree (ai->flash);
3893 ai->flash = NULL;
3894
3895 /* The NOP is the first step in getting the card going */
3896 cmd.cmd = NOP;
3897 cmd.parm0 = cmd.parm1 = cmd.parm2 = 0;
3898 if (lock && down_interruptible(&ai->sem))
3899 return ERROR;
3900 if (issuecommand(ai, &cmd, &rsp, true) != SUCCESS) {
3901 if (lock)
3902 up(&ai->sem);
3903 return ERROR;
3904 }
3905 disable_MAC(ai, 0);
3906
3907 // Let's figure out if we need to use the AUX port
3908 if (!test_bit(FLAG_MPI,&ai->flags)) {
3909 cmd.cmd = CMD_ENABLEAUX;
3910 if (issuecommand(ai, &cmd, &rsp, true) != SUCCESS) {
3911 if (lock)
3912 up(&ai->sem);
3913 airo_print_err(ai->dev->name, "Error checking for AUX port");
3914 return ERROR;
3915 }
3916 if (!aux_bap || rsp.status & 0xff00) {
3917 ai->bap_read = fast_bap_read;
3918 airo_print_dbg(ai->dev->name, "Doing fast bap_reads");
3919 } else {
3920 ai->bap_read = aux_bap_read;
3921 airo_print_dbg(ai->dev->name, "Doing AUX bap_reads");
3922 }
3923 }
3924 if (lock)
3925 up(&ai->sem);
3926 if (ai->config.len == 0) {
3927 status = airo_readconfig(ai, dev, lock);
3928 if (status != SUCCESS)
3929 return ERROR;
3930 }
3931
3932 /* Setup the SSIDs if present */
3933 if (ssids[0]) {
3934 int i;
3935 for (i = 0; i < 3 && ssids[i]; i++) {
3936 size_t len = strlen(ssids[i]);
3937 if (len > 32)
3938 len = 32;
3939 mySsid.ssids[i].len = cpu_to_le16(len);
3940 memcpy(mySsid.ssids[i].ssid, ssids[i], len);
3941 }
3942 mySsid.len = cpu_to_le16(sizeof(mySsid));
3943 }
3944
3945 status = writeConfigRid(ai, lock);
3946 if (status != SUCCESS) return ERROR;
3947
3948 /* Set up the SSID list */
3949 if (ssids[0]) {
3950 status = writeSsidRid(ai, &mySsid, lock);
3951 if (status != SUCCESS) return ERROR;
3952 }
3953
3954 status = enable_MAC(ai, lock);
3955 if (status != SUCCESS)
3956 return ERROR;
3957
3958 /* Grab the initial wep key, we gotta save it for auto_wep */
3959 rc = readWepKeyRid(ai, &wkr, 1, lock);
3960 if (rc == SUCCESS) do {
3961 lastindex = wkr.kindex;
3962 if (wkr.kindex == cpu_to_le16(0xffff)) {
3963 ai->defindex = wkr.mac[0];
3964 }
3965 rc = readWepKeyRid(ai, &wkr, 0, lock);
3966 } while (lastindex != wkr.kindex);
3967
3968 try_auto_wep(ai);
3969
3970 return SUCCESS;
3971}
3972
3973static u16 issuecommand(struct airo_info *ai, Cmd *pCmd, Resp *pRsp,
3974 bool may_sleep)
3975{
3976 // Im really paranoid about letting it run forever!
3977 int max_tries = 600000;
3978
3979 if (IN4500(ai, EVSTAT) & EV_CMD)
3980 OUT4500(ai, EVACK, EV_CMD);
3981
3982 OUT4500(ai, PARAM0, pCmd->parm0);
3983 OUT4500(ai, PARAM1, pCmd->parm1);
3984 OUT4500(ai, PARAM2, pCmd->parm2);
3985 OUT4500(ai, COMMAND, pCmd->cmd);
3986
3987 while (max_tries-- && (IN4500(ai, EVSTAT) & EV_CMD) == 0) {
3988 if ((IN4500(ai, COMMAND)) == pCmd->cmd)
3989 // PC4500 didn't notice command, try again
3990 OUT4500(ai, COMMAND, pCmd->cmd);
3991 if (may_sleep && (max_tries & 255) == 0)
3992 cond_resched();
3993 }
3994
3995 if (max_tries == -1) {
3996 airo_print_err(ai->dev->name,
3997 "Max tries exceeded when issuing command");
3998 if (IN4500(ai, COMMAND) & COMMAND_BUSY)
3999 OUT4500(ai, EVACK, EV_CLEARCOMMANDBUSY);
4000 return ERROR;
4001 }
4002
4003 // command completed
4004 pRsp->status = IN4500(ai, STATUS);
4005 pRsp->rsp0 = IN4500(ai, RESP0);
4006 pRsp->rsp1 = IN4500(ai, RESP1);
4007 pRsp->rsp2 = IN4500(ai, RESP2);
4008 if ((pRsp->status & 0xff00)!=0 && pCmd->cmd != CMD_SOFTRESET)
4009 airo_print_err(ai->dev->name,
4010 "cmd:%x status:%x rsp0:%x rsp1:%x rsp2:%x",
4011 pCmd->cmd, pRsp->status, pRsp->rsp0, pRsp->rsp1,
4012 pRsp->rsp2);
4013
4014 // clear stuck command busy if necessary
4015 if (IN4500(ai, COMMAND) & COMMAND_BUSY) {
4016 OUT4500(ai, EVACK, EV_CLEARCOMMANDBUSY);
4017 }
4018 // acknowledge processing the status/response
4019 OUT4500(ai, EVACK, EV_CMD);
4020
4021 return SUCCESS;
4022}
4023
4024/* Sets up the bap to start exchange data. whichbap should
4025 * be one of the BAP0 or BAP1 defines. Locks should be held before
4026 * calling! */
4027static int bap_setup(struct airo_info *ai, u16 rid, u16 offset, int whichbap)
4028{
4029 int timeout = 50;
4030 int max_tries = 3;
4031
4032 OUT4500(ai, SELECT0+whichbap, rid);
4033 OUT4500(ai, OFFSET0+whichbap, offset);
4034 while (1) {
4035 int status = IN4500(ai, OFFSET0+whichbap);
4036 if (status & BAP_BUSY) {
4037 /* This isn't really a timeout, but its kinda
4038 close */
4039 if (timeout--) {
4040 continue;
4041 }
4042 } else if (status & BAP_ERR) {
4043 /* invalid rid or offset */
4044 airo_print_err(ai->dev->name, "BAP error %x %d",
4045 status, whichbap);
4046 return ERROR;
4047 } else if (status & BAP_DONE) { // success
4048 return SUCCESS;
4049 }
4050 if (!(max_tries--)) {
4051 airo_print_err(ai->dev->name,
4052 "BAP setup error too many retries\n");
4053 return ERROR;
4054 }
4055 // -- PC4500 missed it, try again
4056 OUT4500(ai, SELECT0+whichbap, rid);
4057 OUT4500(ai, OFFSET0+whichbap, offset);
4058 timeout = 50;
4059 }
4060}
4061
4062/* should only be called by aux_bap_read. This aux function and the
4063 following use concepts not documented in the developers guide. I
4064 got them from a patch given to my by Aironet */
4065static u16 aux_setup(struct airo_info *ai, u16 page,
4066 u16 offset, u16 *len)
4067{
4068 u16 next;
4069
4070 OUT4500(ai, AUXPAGE, page);
4071 OUT4500(ai, AUXOFF, 0);
4072 next = IN4500(ai, AUXDATA);
4073 *len = IN4500(ai, AUXDATA)&0xff;
4074 if (offset != 4) OUT4500(ai, AUXOFF, offset);
4075 return next;
4076}
4077
4078/* requires call to bap_setup() first */
4079static int aux_bap_read(struct airo_info *ai, __le16 *pu16Dst,
4080 int bytelen, int whichbap)
4081{
4082 u16 len;
4083 u16 page;
4084 u16 offset;
4085 u16 next;
4086 int words;
4087 int i;
4088 unsigned long flags;
4089
4090 spin_lock_irqsave(&ai->aux_lock, flags);
4091 page = IN4500(ai, SWS0+whichbap);
4092 offset = IN4500(ai, SWS2+whichbap);
4093 next = aux_setup(ai, page, offset, &len);
4094 words = (bytelen+1)>>1;
4095
4096 for (i = 0; i<words;) {
4097 int count;
4098 count = (len>>1) < (words-i) ? (len>>1) : (words-i);
4099 if (!do8bitIO)
4100 insw(ai->dev->base_addr+DATA0+whichbap,
4101 pu16Dst+i, count);
4102 else
4103 insb(ai->dev->base_addr+DATA0+whichbap,
4104 pu16Dst+i, count << 1);
4105 i += count;
4106 if (i<words) {
4107 next = aux_setup(ai, next, 4, &len);
4108 }
4109 }
4110 spin_unlock_irqrestore(&ai->aux_lock, flags);
4111 return SUCCESS;
4112}
4113
4114
4115/* requires call to bap_setup() first */
4116static int fast_bap_read(struct airo_info *ai, __le16 *pu16Dst,
4117 int bytelen, int whichbap)
4118{
4119 bytelen = (bytelen + 1) & (~1); // round up to even value
4120 if (!do8bitIO)
4121 insw(ai->dev->base_addr+DATA0+whichbap, pu16Dst, bytelen>>1);
4122 else
4123 insb(ai->dev->base_addr+DATA0+whichbap, pu16Dst, bytelen);
4124 return SUCCESS;
4125}
4126
4127/* requires call to bap_setup() first */
4128static int bap_write(struct airo_info *ai, const __le16 *pu16Src,
4129 int bytelen, int whichbap)
4130{
4131 bytelen = (bytelen + 1) & (~1); // round up to even value
4132 if (!do8bitIO)
4133 outsw(ai->dev->base_addr+DATA0+whichbap,
4134 pu16Src, bytelen>>1);
4135 else
4136 outsb(ai->dev->base_addr+DATA0+whichbap, pu16Src, bytelen);
4137 return SUCCESS;
4138}
4139
4140static int PC4500_accessrid(struct airo_info *ai, u16 rid, u16 accmd)
4141{
4142 Cmd cmd; /* for issuing commands */
4143 Resp rsp; /* response from commands */
4144 u16 status;
4145
4146 memset(&cmd, 0, sizeof(cmd));
4147 cmd.cmd = accmd;
4148 cmd.parm0 = rid;
4149 status = issuecommand(ai, &cmd, &rsp, true);
4150 if (status != 0) return status;
4151 if ((rsp.status & 0x7F00) != 0) {
4152 return (accmd << 8) + (rsp.rsp0 & 0xFF);
4153 }
4154 return 0;
4155}
4156
4157/* Note, that we are using BAP1 which is also used by transmit, so
4158 * we must get a lock. */
4159static int PC4500_readrid(struct airo_info *ai, u16 rid, void *pBuf, int len, int lock)
4160{
4161 u16 status;
4162 int rc = SUCCESS;
4163
4164 if (lock) {
4165 if (down_interruptible(&ai->sem))
4166 return ERROR;
4167 }
4168 if (test_bit(FLAG_MPI,&ai->flags)) {
4169 Cmd cmd;
4170 Resp rsp;
4171
4172 memset(&cmd, 0, sizeof(cmd));
4173 memset(&rsp, 0, sizeof(rsp));
4174 ai->config_desc.rid_desc.valid = 1;
4175 ai->config_desc.rid_desc.len = RIDSIZE;
4176 ai->config_desc.rid_desc.rid = 0;
4177 ai->config_desc.rid_desc.host_addr = ai->ridbus;
4178
4179 cmd.cmd = CMD_ACCESS;
4180 cmd.parm0 = rid;
4181
4182 memcpy_toio(ai->config_desc.card_ram_off,
4183 &ai->config_desc.rid_desc, sizeof(Rid));
4184
4185 rc = issuecommand(ai, &cmd, &rsp, true);
4186
4187 if (rsp.status & 0x7f00)
4188 rc = rsp.rsp0;
4189 if (!rc)
4190 memcpy(pBuf, ai->config_desc.virtual_host_addr, len);
4191 goto done;
4192 } else {
4193 if ((status = PC4500_accessrid(ai, rid, CMD_ACCESS))!=SUCCESS) {
4194 rc = status;
4195 goto done;
4196 }
4197 if (bap_setup(ai, rid, 0, BAP1) != SUCCESS) {
4198 rc = ERROR;
4199 goto done;
4200 }
4201 // read the rid length field
4202 bap_read(ai, pBuf, 2, BAP1);
4203 // length for remaining part of rid
4204 len = min(len, (int)le16_to_cpu(*(__le16*)pBuf)) - 2;
4205
4206 if (len <= 2) {
4207 airo_print_err(ai->dev->name,
4208 "Rid %x has a length of %d which is too short",
4209 (int)rid, (int)len);
4210 rc = ERROR;
4211 goto done;
4212 }
4213 // read remainder of the rid
4214 rc = bap_read(ai, ((__le16*)pBuf)+1, len, BAP1);
4215 }
4216done:
4217 if (lock)
4218 up(&ai->sem);
4219 return rc;
4220}
4221
4222/* Note, that we are using BAP1 which is also used by transmit, so
4223 * make sure this isn't called when a transmit is happening */
4224static int PC4500_writerid(struct airo_info *ai, u16 rid,
4225 const void *pBuf, int len, int lock)
4226{
4227 u16 status;
4228 int rc = SUCCESS;
4229
4230 *(__le16*)pBuf = cpu_to_le16((u16)len);
4231
4232 if (lock) {
4233 if (down_interruptible(&ai->sem))
4234 return ERROR;
4235 }
4236 if (test_bit(FLAG_MPI,&ai->flags)) {
4237 Cmd cmd;
4238 Resp rsp;
4239
4240 if (test_bit(FLAG_ENABLED, &ai->flags) && (RID_WEP_TEMP != rid))
4241 airo_print_err(ai->dev->name,
4242 "%s: MAC should be disabled (rid=%04x)",
4243 __func__, rid);
4244 memset(&cmd, 0, sizeof(cmd));
4245 memset(&rsp, 0, sizeof(rsp));
4246
4247 ai->config_desc.rid_desc.valid = 1;
4248 ai->config_desc.rid_desc.len = *((u16 *)pBuf);
4249 ai->config_desc.rid_desc.rid = 0;
4250
4251 cmd.cmd = CMD_WRITERID;
4252 cmd.parm0 = rid;
4253
4254 memcpy_toio(ai->config_desc.card_ram_off,
4255 &ai->config_desc.rid_desc, sizeof(Rid));
4256
4257 if (len < 4 || len > 2047) {
4258 airo_print_err(ai->dev->name, "%s: len=%d", __func__, len);
4259 rc = -1;
4260 } else {
4261 memcpy(ai->config_desc.virtual_host_addr,
4262 pBuf, len);
4263
4264 rc = issuecommand(ai, &cmd, &rsp, true);
4265 if ((rc & 0xff00) != 0) {
4266 airo_print_err(ai->dev->name, "%s: Write rid Error %d",
4267 __func__, rc);
4268 airo_print_err(ai->dev->name, "%s: Cmd=%04x",
4269 __func__, cmd.cmd);
4270 }
4271
4272 if ((rsp.status & 0x7f00))
4273 rc = rsp.rsp0;
4274 }
4275 } else {
4276 // --- first access so that we can write the rid data
4277 if ((status = PC4500_accessrid(ai, rid, CMD_ACCESS)) != 0) {
4278 rc = status;
4279 goto done;
4280 }
4281 // --- now write the rid data
4282 if (bap_setup(ai, rid, 0, BAP1) != SUCCESS) {
4283 rc = ERROR;
4284 goto done;
4285 }
4286 bap_write(ai, pBuf, len, BAP1);
4287 // ---now commit the rid data
4288 rc = PC4500_accessrid(ai, rid, 0x100|CMD_ACCESS);
4289 }
4290done:
4291 if (lock)
4292 up(&ai->sem);
4293 return rc;
4294}
4295
4296/* Allocates a FID to be used for transmitting packets. We only use
4297 one for now. */
4298static u16 transmit_allocate(struct airo_info *ai, int lenPayload, int raw)
4299{
4300 unsigned int loop = 3000;
4301 Cmd cmd;
4302 Resp rsp;
4303 u16 txFid;
4304 __le16 txControl;
4305
4306 cmd.cmd = CMD_ALLOCATETX;
4307 cmd.parm0 = lenPayload;
4308 if (down_interruptible(&ai->sem))
4309 return ERROR;
4310 if (issuecommand(ai, &cmd, &rsp, true) != SUCCESS) {
4311 txFid = ERROR;
4312 goto done;
4313 }
4314 if ((rsp.status & 0xFF00) != 0) {
4315 txFid = ERROR;
4316 goto done;
4317 }
4318 /* wait for the allocate event/indication
4319 * It makes me kind of nervous that this can just sit here and spin,
4320 * but in practice it only loops like four times. */
4321 while (((IN4500(ai, EVSTAT) & EV_ALLOC) == 0) && --loop);
4322 if (!loop) {
4323 txFid = ERROR;
4324 goto done;
4325 }
4326
4327 // get the allocated fid and acknowledge
4328 txFid = IN4500(ai, TXALLOCFID);
4329 OUT4500(ai, EVACK, EV_ALLOC);
4330
4331 /* The CARD is pretty cool since it converts the ethernet packet
4332 * into 802.11. Also note that we don't release the FID since we
4333 * will be using the same one over and over again. */
4334 /* We only have to setup the control once since we are not
4335 * releasing the fid. */
4336 if (raw)
4337 txControl = cpu_to_le16(TXCTL_TXOK | TXCTL_TXEX | TXCTL_802_11
4338 | TXCTL_ETHERNET | TXCTL_NORELEASE);
4339 else
4340 txControl = cpu_to_le16(TXCTL_TXOK | TXCTL_TXEX | TXCTL_802_3
4341 | TXCTL_ETHERNET | TXCTL_NORELEASE);
4342 if (bap_setup(ai, txFid, 0x0008, BAP1) != SUCCESS)
4343 txFid = ERROR;
4344 else
4345 bap_write(ai, &txControl, sizeof(txControl), BAP1);
4346
4347done:
4348 up(&ai->sem);
4349
4350 return txFid;
4351}
4352
4353/* In general BAP1 is dedicated to transmiting packets. However,
4354 since we need a BAP when accessing RIDs, we also use BAP1 for that.
4355 Make sure the BAP1 spinlock is held when this is called. */
4356static int transmit_802_3_packet(struct airo_info *ai, int len, char *pPacket,
4357 bool may_sleep)
4358{
4359 __le16 payloadLen;
4360 Cmd cmd;
4361 Resp rsp;
4362 int miclen = 0;
4363 u16 txFid = len;
4364 MICBuffer pMic;
4365
4366 len >>= 16;
4367
4368 if (len <= ETH_ALEN * 2) {
4369 airo_print_warn(ai->dev->name, "Short packet %d", len);
4370 return ERROR;
4371 }
4372 len -= ETH_ALEN * 2;
4373
4374 if (test_bit(FLAG_MIC_CAPABLE, &ai->flags) && ai->micstats.enabled &&
4375 (ntohs(((__be16 *)pPacket)[6]) != 0x888E)) {
4376 if (encapsulate(ai, (etherHead *)pPacket,&pMic, len) != SUCCESS)
4377 return ERROR;
4378 miclen = sizeof(pMic);
4379 }
4380 // packet is destination[6], source[6], payload[len-12]
4381 // write the payload length and dst/src/payload
4382 if (bap_setup(ai, txFid, 0x0036, BAP1) != SUCCESS) return ERROR;
4383 /* The hardware addresses aren't counted as part of the payload, so
4384 * we have to subtract the 12 bytes for the addresses off */
4385 payloadLen = cpu_to_le16(len + miclen);
4386 bap_write(ai, &payloadLen, sizeof(payloadLen), BAP1);
4387 bap_write(ai, (__le16*)pPacket, sizeof(etherHead), BAP1);
4388 if (miclen)
4389 bap_write(ai, (__le16*)&pMic, miclen, BAP1);
4390 bap_write(ai, (__le16*)(pPacket + sizeof(etherHead)), len, BAP1);
4391 // issue the transmit command
4392 memset(&cmd, 0, sizeof(cmd));
4393 cmd.cmd = CMD_TRANSMIT;
4394 cmd.parm0 = txFid;
4395 if (issuecommand(ai, &cmd, &rsp, may_sleep) != SUCCESS)
4396 return ERROR;
4397 if ((rsp.status & 0xFF00) != 0) return ERROR;
4398 return SUCCESS;
4399}
4400
4401static int transmit_802_11_packet(struct airo_info *ai, int len, char *pPacket,
4402 bool may_sleep)
4403{
4404 __le16 fc, payloadLen;
4405 Cmd cmd;
4406 Resp rsp;
4407 int hdrlen;
4408 static u8 tail[(30-10) + 2 + 6] = {[30-10] = 6};
4409 /* padding of header to full size + le16 gaplen (6) + gaplen bytes */
4410 u16 txFid = len;
4411 len >>= 16;
4412
4413 fc = *(__le16*)pPacket;
4414 hdrlen = header_len(fc);
4415
4416 if (len < hdrlen) {
4417 airo_print_warn(ai->dev->name, "Short packet %d", len);
4418 return ERROR;
4419 }
4420
4421 /* packet is 802.11 header + payload
4422 * write the payload length and dst/src/payload */
4423 if (bap_setup(ai, txFid, 6, BAP1) != SUCCESS) return ERROR;
4424 /* The 802.11 header aren't counted as part of the payload, so
4425 * we have to subtract the header bytes off */
4426 payloadLen = cpu_to_le16(len-hdrlen);
4427 bap_write(ai, &payloadLen, sizeof(payloadLen), BAP1);
4428 if (bap_setup(ai, txFid, 0x0014, BAP1) != SUCCESS) return ERROR;
4429 bap_write(ai, (__le16 *)pPacket, hdrlen, BAP1);
4430 bap_write(ai, (__le16 *)(tail + (hdrlen - 10)), 38 - hdrlen, BAP1);
4431
4432 bap_write(ai, (__le16 *)(pPacket + hdrlen), len - hdrlen, BAP1);
4433 // issue the transmit command
4434 memset(&cmd, 0, sizeof(cmd));
4435 cmd.cmd = CMD_TRANSMIT;
4436 cmd.parm0 = txFid;
4437 if (issuecommand(ai, &cmd, &rsp, may_sleep) != SUCCESS)
4438 return ERROR;
4439 if ((rsp.status & 0xFF00) != 0) return ERROR;
4440 return SUCCESS;
4441}
4442
4443/*
4444 * This is the proc_fs routines. It is a bit messier than I would
4445 * like! Feel free to clean it up!
4446 */
4447
4448static ssize_t proc_read(struct file *file,
4449 char __user *buffer,
4450 size_t len,
4451 loff_t *offset);
4452
4453static ssize_t proc_write(struct file *file,
4454 const char __user *buffer,
4455 size_t len,
4456 loff_t *offset);
4457static int proc_close(struct inode *inode, struct file *file);
4458
4459static int proc_stats_open(struct inode *inode, struct file *file);
4460static int proc_statsdelta_open(struct inode *inode, struct file *file);
4461static int proc_status_open(struct inode *inode, struct file *file);
4462static int proc_SSID_open(struct inode *inode, struct file *file);
4463static int proc_APList_open(struct inode *inode, struct file *file);
4464static int proc_BSSList_open(struct inode *inode, struct file *file);
4465static int proc_config_open(struct inode *inode, struct file *file);
4466static int proc_wepkey_open(struct inode *inode, struct file *file);
4467
4468static const struct proc_ops proc_statsdelta_ops = {
4469 .proc_read = proc_read,
4470 .proc_open = proc_statsdelta_open,
4471 .proc_release = proc_close,
4472 .proc_lseek = default_llseek,
4473};
4474
4475static const struct proc_ops proc_stats_ops = {
4476 .proc_read = proc_read,
4477 .proc_open = proc_stats_open,
4478 .proc_release = proc_close,
4479 .proc_lseek = default_llseek,
4480};
4481
4482static const struct proc_ops proc_status_ops = {
4483 .proc_read = proc_read,
4484 .proc_open = proc_status_open,
4485 .proc_release = proc_close,
4486 .proc_lseek = default_llseek,
4487};
4488
4489static const struct proc_ops proc_SSID_ops = {
4490 .proc_read = proc_read,
4491 .proc_write = proc_write,
4492 .proc_open = proc_SSID_open,
4493 .proc_release = proc_close,
4494 .proc_lseek = default_llseek,
4495};
4496
4497static const struct proc_ops proc_BSSList_ops = {
4498 .proc_read = proc_read,
4499 .proc_write = proc_write,
4500 .proc_open = proc_BSSList_open,
4501 .proc_release = proc_close,
4502 .proc_lseek = default_llseek,
4503};
4504
4505static const struct proc_ops proc_APList_ops = {
4506 .proc_read = proc_read,
4507 .proc_write = proc_write,
4508 .proc_open = proc_APList_open,
4509 .proc_release = proc_close,
4510 .proc_lseek = default_llseek,
4511};
4512
4513static const struct proc_ops proc_config_ops = {
4514 .proc_read = proc_read,
4515 .proc_write = proc_write,
4516 .proc_open = proc_config_open,
4517 .proc_release = proc_close,
4518 .proc_lseek = default_llseek,
4519};
4520
4521static const struct proc_ops proc_wepkey_ops = {
4522 .proc_read = proc_read,
4523 .proc_write = proc_write,
4524 .proc_open = proc_wepkey_open,
4525 .proc_release = proc_close,
4526 .proc_lseek = default_llseek,
4527};
4528
4529static struct proc_dir_entry *airo_entry;
4530
4531struct proc_data {
4532 int release_buffer;
4533 int readlen;
4534 char *rbuffer;
4535 int writelen;
4536 int maxwritelen;
4537 char *wbuffer;
4538 void (*on_close) (struct inode *, struct file *);
4539};
4540
4541static int setup_proc_entry(struct net_device *dev,
4542 struct airo_info *apriv)
4543{
4544 struct proc_dir_entry *entry;
4545
4546 /* First setup the device directory */
4547 strcpy(apriv->proc_name, dev->name);
4548 apriv->proc_entry = proc_mkdir_mode(apriv->proc_name, airo_perm,
4549 airo_entry);
4550 if (!apriv->proc_entry)
4551 return -ENOMEM;
4552 proc_set_user(apriv->proc_entry, proc_kuid, proc_kgid);
4553
4554 /* Setup the StatsDelta */
4555 entry = proc_create_data("StatsDelta", 0444 & proc_perm,
4556 apriv->proc_entry, &proc_statsdelta_ops, dev);
4557 if (!entry)
4558 goto fail;
4559 proc_set_user(entry, proc_kuid, proc_kgid);
4560
4561 /* Setup the Stats */
4562 entry = proc_create_data("Stats", 0444 & proc_perm,
4563 apriv->proc_entry, &proc_stats_ops, dev);
4564 if (!entry)
4565 goto fail;
4566 proc_set_user(entry, proc_kuid, proc_kgid);
4567
4568 /* Setup the Status */
4569 entry = proc_create_data("Status", 0444 & proc_perm,
4570 apriv->proc_entry, &proc_status_ops, dev);
4571 if (!entry)
4572 goto fail;
4573 proc_set_user(entry, proc_kuid, proc_kgid);
4574
4575 /* Setup the Config */
4576 entry = proc_create_data("Config", proc_perm,
4577 apriv->proc_entry, &proc_config_ops, dev);
4578 if (!entry)
4579 goto fail;
4580 proc_set_user(entry, proc_kuid, proc_kgid);
4581
4582 /* Setup the SSID */
4583 entry = proc_create_data("SSID", proc_perm,
4584 apriv->proc_entry, &proc_SSID_ops, dev);
4585 if (!entry)
4586 goto fail;
4587 proc_set_user(entry, proc_kuid, proc_kgid);
4588
4589 /* Setup the APList */
4590 entry = proc_create_data("APList", proc_perm,
4591 apriv->proc_entry, &proc_APList_ops, dev);
4592 if (!entry)
4593 goto fail;
4594 proc_set_user(entry, proc_kuid, proc_kgid);
4595
4596 /* Setup the BSSList */
4597 entry = proc_create_data("BSSList", proc_perm,
4598 apriv->proc_entry, &proc_BSSList_ops, dev);
4599 if (!entry)
4600 goto fail;
4601 proc_set_user(entry, proc_kuid, proc_kgid);
4602
4603 /* Setup the WepKey */
4604 entry = proc_create_data("WepKey", proc_perm,
4605 apriv->proc_entry, &proc_wepkey_ops, dev);
4606 if (!entry)
4607 goto fail;
4608 proc_set_user(entry, proc_kuid, proc_kgid);
4609 return 0;
4610
4611fail:
4612 remove_proc_subtree(apriv->proc_name, airo_entry);
4613 return -ENOMEM;
4614}
4615
4616static int takedown_proc_entry(struct net_device *dev,
4617 struct airo_info *apriv)
4618{
4619 remove_proc_subtree(apriv->proc_name, airo_entry);
4620 return 0;
4621}
4622
4623/*
4624 * What we want from the proc_fs is to be able to efficiently read
4625 * and write the configuration. To do this, we want to read the
4626 * configuration when the file is opened and write it when the file is
4627 * closed. So basically we allocate a read buffer at open and fill it
4628 * with data, and allocate a write buffer and read it at close.
4629 */
4630
4631/*
4632 * The read routine is generic, it relies on the preallocated rbuffer
4633 * to supply the data.
4634 */
4635static ssize_t proc_read(struct file *file,
4636 char __user *buffer,
4637 size_t len,
4638 loff_t *offset)
4639{
4640 struct proc_data *priv = file->private_data;
4641
4642 if (!priv->rbuffer)
4643 return -EINVAL;
4644
4645 return simple_read_from_buffer(buffer, len, offset, priv->rbuffer,
4646 priv->readlen);
4647}
4648
4649/*
4650 * The write routine is generic, it fills in a preallocated rbuffer
4651 * to supply the data.
4652 */
4653static ssize_t proc_write(struct file *file,
4654 const char __user *buffer,
4655 size_t len,
4656 loff_t *offset)
4657{
4658 ssize_t ret;
4659 struct proc_data *priv = file->private_data;
4660
4661 if (!priv->wbuffer)
4662 return -EINVAL;
4663
4664 ret = simple_write_to_buffer(priv->wbuffer, priv->maxwritelen, offset,
4665 buffer, len);
4666 if (ret > 0)
4667 priv->writelen = max_t(int, priv->writelen, *offset);
4668
4669 return ret;
4670}
4671
4672static int proc_status_open(struct inode *inode, struct file *file)
4673{
4674 struct proc_data *data;
4675 struct net_device *dev = pde_data(inode);
4676 struct airo_info *apriv = dev->ml_priv;
4677 CapabilityRid cap_rid;
4678 StatusRid status_rid;
4679 u16 mode;
4680 int i;
4681
4682 if ((file->private_data = kzalloc(sizeof(struct proc_data), GFP_KERNEL)) == NULL)
4683 return -ENOMEM;
4684 data = file->private_data;
4685 if ((data->rbuffer = kmalloc(2048, GFP_KERNEL)) == NULL) {
4686 kfree (file->private_data);
4687 return -ENOMEM;
4688 }
4689
4690 readStatusRid(apriv, &status_rid, 1);
4691 readCapabilityRid(apriv, &cap_rid, 1);
4692
4693 mode = le16_to_cpu(status_rid.mode);
4694
4695 i = sprintf(data->rbuffer, "Status: %s%s%s%s%s%s%s%s%s\n",
4696 mode & 1 ? "CFG ": "",
4697 mode & 2 ? "ACT ": "",
4698 mode & 0x10 ? "SYN ": "",
4699 mode & 0x20 ? "LNK ": "",
4700 mode & 0x40 ? "LEAP ": "",
4701 mode & 0x80 ? "PRIV ": "",
4702 mode & 0x100 ? "KEY ": "",
4703 mode & 0x200 ? "WEP ": "",
4704 mode & 0x8000 ? "ERR ": "");
4705 sprintf(data->rbuffer+i, "Mode: %x\n"
4706 "Signal Strength: %d\n"
4707 "Signal Quality: %d\n"
4708 "SSID: %-.*s\n"
4709 "AP: %-.16s\n"
4710 "Freq: %d\n"
4711 "BitRate: %dmbs\n"
4712 "Driver Version: %s\n"
4713 "Device: %s\nManufacturer: %s\nFirmware Version: %s\n"
4714 "Radio type: %x\nCountry: %x\nHardware Version: %x\n"
4715 "Software Version: %x\nSoftware Subversion: %x\n"
4716 "Boot block version: %x\n",
4717 le16_to_cpu(status_rid.mode),
4718 le16_to_cpu(status_rid.normalizedSignalStrength),
4719 le16_to_cpu(status_rid.signalQuality),
4720 le16_to_cpu(status_rid.SSIDlen),
4721 status_rid.SSID,
4722 status_rid.apName,
4723 le16_to_cpu(status_rid.channel),
4724 le16_to_cpu(status_rid.currentXmitRate) / 2,
4725 version,
4726 cap_rid.prodName,
4727 cap_rid.manName,
4728 cap_rid.prodVer,
4729 le16_to_cpu(cap_rid.radioType),
4730 le16_to_cpu(cap_rid.country),
4731 le16_to_cpu(cap_rid.hardVer),
4732 le16_to_cpu(cap_rid.softVer),
4733 le16_to_cpu(cap_rid.softSubVer),
4734 le16_to_cpu(cap_rid.bootBlockVer));
4735 data->readlen = strlen(data->rbuffer);
4736 return 0;
4737}
4738
4739static int proc_stats_rid_open(struct inode*, struct file*, u16);
4740static int proc_statsdelta_open(struct inode *inode,
4741 struct file *file)
4742{
4743 if (file->f_mode&FMODE_WRITE) {
4744 return proc_stats_rid_open(inode, file, RID_STATSDELTACLEAR);
4745 }
4746 return proc_stats_rid_open(inode, file, RID_STATSDELTA);
4747}
4748
4749static int proc_stats_open(struct inode *inode, struct file *file)
4750{
4751 return proc_stats_rid_open(inode, file, RID_STATS);
4752}
4753
4754static int proc_stats_rid_open(struct inode *inode,
4755 struct file *file,
4756 u16 rid)
4757{
4758 struct proc_data *data;
4759 struct net_device *dev = pde_data(inode);
4760 struct airo_info *apriv = dev->ml_priv;
4761 StatsRid stats;
4762 int i, j;
4763 __le32 *vals = stats.vals;
4764 int len;
4765
4766 if ((file->private_data = kzalloc(sizeof(struct proc_data), GFP_KERNEL)) == NULL)
4767 return -ENOMEM;
4768 data = file->private_data;
4769 if ((data->rbuffer = kmalloc(4096, GFP_KERNEL)) == NULL) {
4770 kfree (file->private_data);
4771 return -ENOMEM;
4772 }
4773
4774 readStatsRid(apriv, &stats, rid, 1);
4775 len = le16_to_cpu(stats.len);
4776
4777 j = 0;
4778 for (i = 0; statsLabels[i]!=(char *)-1 && i*4<len; i++) {
4779 if (!statsLabels[i]) continue;
4780 if (j+strlen(statsLabels[i])+16>4096) {
4781 airo_print_warn(apriv->dev->name,
4782 "Potentially disastrous buffer overflow averted!");
4783 break;
4784 }
4785 j+=sprintf(data->rbuffer+j, "%s: %u\n", statsLabels[i],
4786 le32_to_cpu(vals[i]));
4787 }
4788 if (i*4 >= len) {
4789 airo_print_warn(apriv->dev->name, "Got a short rid");
4790 }
4791 data->readlen = j;
4792 return 0;
4793}
4794
4795static int get_dec_u16(char *buffer, int *start, int limit)
4796{
4797 u16 value;
4798 int valid = 0;
4799 for (value = 0; *start < limit && buffer[*start] >= '0' &&
4800 buffer[*start] <= '9'; (*start)++) {
4801 valid = 1;
4802 value *= 10;
4803 value += buffer[*start] - '0';
4804 }
4805 if (!valid) return -1;
4806 return value;
4807}
4808
4809static int airo_config_commit(struct net_device *dev,
4810 struct iw_request_info *info,
4811 union iwreq_data *wrqu,
4812 char *extra);
4813
4814static inline int sniffing_mode(struct airo_info *ai)
4815{
4816 return (le16_to_cpu(ai->config.rmode) & le16_to_cpu(RXMODE_MASK)) >=
4817 le16_to_cpu(RXMODE_RFMON);
4818}
4819
4820static void proc_config_on_close(struct inode *inode, struct file *file)
4821{
4822 struct proc_data *data = file->private_data;
4823 struct net_device *dev = pde_data(inode);
4824 struct airo_info *ai = dev->ml_priv;
4825 char *line;
4826
4827 if (!data->writelen) return;
4828
4829 readConfigRid(ai, 1);
4830 set_bit (FLAG_COMMIT, &ai->flags);
4831
4832 line = data->wbuffer;
4833 while (line[0]) {
4834/*** Mode processing */
4835 if (!strncmp(line, "Mode: ", 6)) {
4836 line += 6;
4837 if (sniffing_mode(ai))
4838 set_bit (FLAG_RESET, &ai->flags);
4839 ai->config.rmode &= ~RXMODE_FULL_MASK;
4840 clear_bit (FLAG_802_11, &ai->flags);
4841 ai->config.opmode &= ~MODE_CFG_MASK;
4842 ai->config.scanMode = SCANMODE_ACTIVE;
4843 if (line[0] == 'a') {
4844 ai->config.opmode |= MODE_STA_IBSS;
4845 } else {
4846 ai->config.opmode |= MODE_STA_ESS;
4847 if (line[0] == 'r') {
4848 ai->config.rmode |= RXMODE_RFMON | RXMODE_DISABLE_802_3_HEADER;
4849 ai->config.scanMode = SCANMODE_PASSIVE;
4850 set_bit (FLAG_802_11, &ai->flags);
4851 } else if (line[0] == 'y') {
4852 ai->config.rmode |= RXMODE_RFMON_ANYBSS | RXMODE_DISABLE_802_3_HEADER;
4853 ai->config.scanMode = SCANMODE_PASSIVE;
4854 set_bit (FLAG_802_11, &ai->flags);
4855 } else if (line[0] == 'l')
4856 ai->config.rmode |= RXMODE_LANMON;
4857 }
4858 set_bit (FLAG_COMMIT, &ai->flags);
4859 }
4860
4861/*** Radio status */
4862 else if (!strncmp(line,"Radio: ", 7)) {
4863 line += 7;
4864 if (!strncmp(line,"off", 3)) {
4865 set_bit (FLAG_RADIO_OFF, &ai->flags);
4866 } else {
4867 clear_bit (FLAG_RADIO_OFF, &ai->flags);
4868 }
4869 }
4870/*** NodeName processing */
4871 else if (!strncmp(line, "NodeName: ", 10)) {
4872 int j;
4873
4874 line += 10;
4875 memset(ai->config.nodeName, 0, 16);
4876/* Do the name, assume a space between the mode and node name */
4877 for (j = 0; j < 16 && line[j] != '\n'; j++) {
4878 ai->config.nodeName[j] = line[j];
4879 }
4880 set_bit (FLAG_COMMIT, &ai->flags);
4881 }
4882
4883/*** PowerMode processing */
4884 else if (!strncmp(line, "PowerMode: ", 11)) {
4885 line += 11;
4886 if (!strncmp(line, "PSPCAM", 6)) {
4887 ai->config.powerSaveMode = POWERSAVE_PSPCAM;
4888 set_bit (FLAG_COMMIT, &ai->flags);
4889 } else if (!strncmp(line, "PSP", 3)) {
4890 ai->config.powerSaveMode = POWERSAVE_PSP;
4891 set_bit (FLAG_COMMIT, &ai->flags);
4892 } else {
4893 ai->config.powerSaveMode = POWERSAVE_CAM;
4894 set_bit (FLAG_COMMIT, &ai->flags);
4895 }
4896 } else if (!strncmp(line, "DataRates: ", 11)) {
4897 int v, i = 0, k = 0; /* i is index into line,
4898 k is index to rates */
4899
4900 line += 11;
4901 while ((v = get_dec_u16(line, &i, 3))!=-1) {
4902 ai->config.rates[k++] = (u8)v;
4903 line += i + 1;
4904 i = 0;
4905 }
4906 set_bit (FLAG_COMMIT, &ai->flags);
4907 } else if (!strncmp(line, "Channel: ", 9)) {
4908 int v, i = 0;
4909 line += 9;
4910 v = get_dec_u16(line, &i, i+3);
4911 if (v != -1) {
4912 ai->config.channelSet = cpu_to_le16(v);
4913 set_bit (FLAG_COMMIT, &ai->flags);
4914 }
4915 } else if (!strncmp(line, "XmitPower: ", 11)) {
4916 int v, i = 0;
4917 line += 11;
4918 v = get_dec_u16(line, &i, i+3);
4919 if (v != -1) {
4920 ai->config.txPower = cpu_to_le16(v);
4921 set_bit (FLAG_COMMIT, &ai->flags);
4922 }
4923 } else if (!strncmp(line, "WEP: ", 5)) {
4924 line += 5;
4925 switch(line[0]) {
4926 case 's':
4927 set_auth_type(ai, AUTH_SHAREDKEY);
4928 break;
4929 case 'e':
4930 set_auth_type(ai, AUTH_ENCRYPT);
4931 break;
4932 default:
4933 set_auth_type(ai, AUTH_OPEN);
4934 break;
4935 }
4936 set_bit (FLAG_COMMIT, &ai->flags);
4937 } else if (!strncmp(line, "LongRetryLimit: ", 16)) {
4938 int v, i = 0;
4939
4940 line += 16;
4941 v = get_dec_u16(line, &i, 3);
4942 v = (v<0) ? 0 : ((v>255) ? 255 : v);
4943 ai->config.longRetryLimit = cpu_to_le16(v);
4944 set_bit (FLAG_COMMIT, &ai->flags);
4945 } else if (!strncmp(line, "ShortRetryLimit: ", 17)) {
4946 int v, i = 0;
4947
4948 line += 17;
4949 v = get_dec_u16(line, &i, 3);
4950 v = (v<0) ? 0 : ((v>255) ? 255 : v);
4951 ai->config.shortRetryLimit = cpu_to_le16(v);
4952 set_bit (FLAG_COMMIT, &ai->flags);
4953 } else if (!strncmp(line, "RTSThreshold: ", 14)) {
4954 int v, i = 0;
4955
4956 line += 14;
4957 v = get_dec_u16(line, &i, 4);
4958 v = (v<0) ? 0 : ((v>AIRO_DEF_MTU) ? AIRO_DEF_MTU : v);
4959 ai->config.rtsThres = cpu_to_le16(v);
4960 set_bit (FLAG_COMMIT, &ai->flags);
4961 } else if (!strncmp(line, "TXMSDULifetime: ", 16)) {
4962 int v, i = 0;
4963
4964 line += 16;
4965 v = get_dec_u16(line, &i, 5);
4966 v = (v<0) ? 0 : v;
4967 ai->config.txLifetime = cpu_to_le16(v);
4968 set_bit (FLAG_COMMIT, &ai->flags);
4969 } else if (!strncmp(line, "RXMSDULifetime: ", 16)) {
4970 int v, i = 0;
4971
4972 line += 16;
4973 v = get_dec_u16(line, &i, 5);
4974 v = (v<0) ? 0 : v;
4975 ai->config.rxLifetime = cpu_to_le16(v);
4976 set_bit (FLAG_COMMIT, &ai->flags);
4977 } else if (!strncmp(line, "TXDiversity: ", 13)) {
4978 ai->config.txDiversity =
4979 (line[13]=='l') ? 1 :
4980 ((line[13]=='r')? 2: 3);
4981 set_bit (FLAG_COMMIT, &ai->flags);
4982 } else if (!strncmp(line, "RXDiversity: ", 13)) {
4983 ai->config.rxDiversity =
4984 (line[13]=='l') ? 1 :
4985 ((line[13]=='r')? 2: 3);
4986 set_bit (FLAG_COMMIT, &ai->flags);
4987 } else if (!strncmp(line, "FragThreshold: ", 15)) {
4988 int v, i = 0;
4989
4990 line += 15;
4991 v = get_dec_u16(line, &i, 4);
4992 v = (v<256) ? 256 : ((v>AIRO_DEF_MTU) ? AIRO_DEF_MTU : v);
4993 v = v & 0xfffe; /* Make sure its even */
4994 ai->config.fragThresh = cpu_to_le16(v);
4995 set_bit (FLAG_COMMIT, &ai->flags);
4996 } else if (!strncmp(line, "Modulation: ", 12)) {
4997 line += 12;
4998 switch(*line) {
4999 case 'd': ai->config.modulation = MOD_DEFAULT; set_bit(FLAG_COMMIT, &ai->flags); break;

3289 more lines aren’t shown here.

drivers/net/wireless/cisco/airo.h+0−10
@@ -1,10 +0,0 @@
1/* SPDX-License-Identifier: GPL-2.0 */
2#ifndef _AIRO_H_
3#define _AIRO_H_
4
5struct net_device *init_airo_card(unsigned short irq, int port, int is_pcmcia,
6 struct device *dmdev);
7int reset_airo_card(struct net_device *dev);
8void stop_airo_card(struct net_device *dev, int freeres);
9
10#endif /* _AIRO_H_ */
drivers/net/wireless/cisco/airo_cs.c+0−218
@@ -1,218 +0,0 @@
1/*======================================================================
2
3 Aironet driver for 4500 and 4800 series cards
4
5 This code is released under both the GPL version 2 and BSD licenses.
6 Either license may be used. The respective licenses are found at
7 the end of this file.
8
9 This code was developed by Benjamin Reed <breed@users.sourceforge.net>
10 including portions of which come from the Aironet PC4500
11 Developer's Reference Manual and used with permission. Copyright
12 (C) 1999 Benjamin Reed. All Rights Reserved. Permission to use
13 code in the Developer's manual was granted for this driver by
14 Aironet.
15
16 In addition this module was derived from dummy_cs.
17 The initial developer of dummy_cs is David A. Hinds
18 <dahinds@users.sourceforge.net>. Portions created by David A. Hinds
19 are Copyright (C) 1999 David A. Hinds. All Rights Reserved.
20
21======================================================================*/
22
23#ifdef __IN_PCMCIA_PACKAGE__
24#include <pcmcia/k_compat.h>
25#endif
26#include <linux/kernel.h>
27#include <linux/module.h>
28#include <linux/ptrace.h>
29#include <linux/slab.h>
30#include <linux/string.h>
31#include <linux/timer.h>
32#include <linux/netdevice.h>
33
34#include <pcmcia/cistpl.h>
35#include <pcmcia/cisreg.h>
36#include <pcmcia/ds.h>
37
38#include <linux/io.h>
39
40#include "airo.h"
41
42
43/*====================================================================*/
44
45MODULE_AUTHOR("Benjamin Reed");
46MODULE_DESCRIPTION("Support for Cisco/Aironet 802.11 wireless ethernet "
47 "cards. This is the module that links the PCMCIA card "
48 "with the airo module.");
49MODULE_LICENSE("Dual BSD/GPL");
50
51/*====================================================================*/
52
53static int airo_config(struct pcmcia_device *link);
54static void airo_release(struct pcmcia_device *link);
55
56static void airo_detach(struct pcmcia_device *p_dev);
57
58struct local_info {
59 struct net_device *eth_dev;
60};
61
62static int airo_probe(struct pcmcia_device *p_dev)
63{
64 struct local_info *local;
65
66 dev_dbg(&p_dev->dev, "airo_attach()\n");
67
68 /* Allocate space for private device-specific data */
69 local = kzalloc(sizeof(*local), GFP_KERNEL);
70 if (!local)
71 return -ENOMEM;
72
73 p_dev->priv = local;
74
75 return airo_config(p_dev);
76} /* airo_attach */
77
78static void airo_detach(struct pcmcia_device *link)
79{
80 dev_dbg(&link->dev, "airo_detach\n");
81
82 airo_release(link);
83
84 if (((struct local_info *)link->priv)->eth_dev) {
85 stop_airo_card(((struct local_info *)link->priv)->eth_dev,
86 0);
87 }
88 ((struct local_info *)link->priv)->eth_dev = NULL;
89
90 kfree(link->priv);
91} /* airo_detach */
92
93static int airo_cs_config_check(struct pcmcia_device *p_dev, void *priv_data)
94{
95 if (p_dev->config_index == 0)
96 return -EINVAL;
97
98 return pcmcia_request_io(p_dev);
99}
100
101
102static int airo_config(struct pcmcia_device *link)
103{
104 int ret;
105
106 dev_dbg(&link->dev, "airo_config\n");
107
108 link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP |
109 CONF_AUTO_AUDIO | CONF_AUTO_SET_IO;
110
111 ret = pcmcia_loop_config(link, airo_cs_config_check, NULL);
112 if (ret)
113 goto failed;
114
115 if (!link->irq)
116 goto failed;
117
118 ret = pcmcia_enable_device(link);
119 if (ret)
120 goto failed;
121 ((struct local_info *)link->priv)->eth_dev =
122 init_airo_card(link->irq,
123 link->resource[0]->start, 1, &link->dev);
124 if (!((struct local_info *)link->priv)->eth_dev)
125 goto failed;
126
127 return 0;
128
129 failed:
130 airo_release(link);
131 return -ENODEV;
132} /* airo_config */
133
134static void airo_release(struct pcmcia_device *link)
135{
136 dev_dbg(&link->dev, "airo_release\n");
137 pcmcia_disable_device(link);
138}
139
140static int airo_suspend(struct pcmcia_device *link)
141{
142 struct local_info *local = link->priv;
143
144 netif_device_detach(local->eth_dev);
145
146 return 0;
147}
148
149static int airo_resume(struct pcmcia_device *link)
150{
151 struct local_info *local = link->priv;
152
153 if (link->open) {
154 reset_airo_card(local->eth_dev);
155 netif_device_attach(local->eth_dev);
156 }
157
158 return 0;
159}
160
161static const struct pcmcia_device_id airo_ids[] = {
162 PCMCIA_DEVICE_MANF_CARD(0x015f, 0x000a),
163 PCMCIA_DEVICE_MANF_CARD(0x015f, 0x0005),
164 PCMCIA_DEVICE_MANF_CARD(0x015f, 0x0007),
165 PCMCIA_DEVICE_MANF_CARD(0x0105, 0x0007),
166 PCMCIA_DEVICE_NULL,
167};
168MODULE_DEVICE_TABLE(pcmcia, airo_ids);
169
170static struct pcmcia_driver airo_driver = {
171 .owner = THIS_MODULE,
172 .name = "airo_cs",
173 .probe = airo_probe,
174 .remove = airo_detach,
175 .id_table = airo_ids,
176 .suspend = airo_suspend,
177 .resume = airo_resume,
178};
179module_pcmcia_driver(airo_driver);
180
181/*
182 This program is free software; you can redistribute it and/or
183 modify it under the terms of the GNU General Public License
184 as published by the Free Software Foundation; either version 2
185 of the License, or (at your option) any later version.
186
187 This program is distributed in the hope that it will be useful,
188 but WITHOUT ANY WARRANTY; without even the implied warranty of
189 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
190 GNU General Public License for more details.
191
192 In addition:
193
194 Redistribution and use in source and binary forms, with or without
195 modification, are permitted provided that the following conditions
196 are met:
197
198 1. Redistributions of source code must retain the above copyright
199 notice, this list of conditions and the following disclaimer.
200 2. Redistributions in binary form must reproduce the above copyright
201 notice, this list of conditions and the following disclaimer in the
202 documentation and/or other materials provided with the distribution.
203 3. The name of the author may not be used to endorse or promote
204 products derived from this software without specific prior written
205 permission.
206
207 THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
208 IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
209 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
210 ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
211 INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
212 (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
213 SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
214 HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
215 STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
216 IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
217 POSSIBILITY OF SUCH DAMAGE.
218*/
drivers/net/wireless/intel/iwlegacy/4965-mac.c+0−6
@@ -4231,8 +4231,6 @@ il4965_rx_handle(struct il_priv *il) · 4230 unmodified lines
4231 fill_rx = 1;4231 fill_rx = 1;
4232 4232
4233 while (i != r) {4233 while (i != r) {
4234 int len;
4235
4236 rxb = rxq->queue[i];4234 rxb = rxq->queue[i];
4237 4235
4238 /* If an RXB doesn't have a Rx queue slot associated with it,4236 /* If an RXB doesn't have a Rx queue slot associated with it,
@@ -4246,10 +4244,6 @@ il4965_rx_handle(struct il_priv *il) · 7 unmodified lines
4246 PAGE_SIZE << il->hw_params.rx_page_order,4244 PAGE_SIZE << il->hw_params.rx_page_order,
4247 DMA_FROM_DEVICE);4245 DMA_FROM_DEVICE);
4248 pkt = rxb_addr(rxb);4246 pkt = rxb_addr(rxb);
4249
4250 len = le32_to_cpu(pkt->len_n_flags) & IL_RX_FRAME_SIZE_MSK;
4251 len += sizeof(u32); /* account for status word */
4252
4253 reclaim = il_need_reclaim(il, pkt);4247 reclaim = il_need_reclaim(il, pkt);
4254 4248
4255 /* Based on type of command response or notification,4249 /* Based on type of command response or notification,
drivers/net/wireless/intersil/Kconfig+0−2
@@ -12,8 +12,6 @@ config WLAN_VENDOR_INTERSIL · 11 unmodified lines
12 12
13if WLAN_VENDOR_INTERSIL13if WLAN_VENDOR_INTERSIL
14 14
15source "drivers/net/wireless/intersil/hostap/Kconfig"
16source "drivers/net/wireless/intersil/orinoco/Kconfig"
17source "drivers/net/wireless/intersil/p54/Kconfig"15source "drivers/net/wireless/intersil/p54/Kconfig"
18 16
19endif # WLAN_VENDOR_INTERSIL17endif # WLAN_VENDOR_INTERSIL
drivers/net/wireless/intersil/Makefile+0−2
@@ -1,4 +1,2 @@
1# SPDX-License-Identifier: GPL-2.0-only1# SPDX-License-Identifier: GPL-2.0-only
2obj-$(CONFIG_HOSTAP) += hostap/
3obj-$(CONFIG_HERMES) += orinoco/
4obj-$(CONFIG_P54_COMMON) += p54/2obj-$(CONFIG_P54_COMMON) += p54/
drivers/net/wireless/intersil/hostap/Kconfig+0−95
@@ -1,95 +0,0 @@
1# SPDX-License-Identifier: GPL-2.0-only
2config HOSTAP
3 tristate "IEEE 802.11 for Host AP (Prism2/2.5/3 and WEP/TKIP/CCMP)"
4 select WIRELESS_EXT
5 select WEXT_SPY
6 select WEXT_PRIV
7 select CRYPTO
8 select CRYPTO_MICHAEL_MIC
9 select CRC32
10 select LIB80211
11 select LIB80211_CRYPT_WEP
12 select LIB80211_CRYPT_TKIP
13 select LIB80211_CRYPT_CCMP
14 help
15 Shared driver code for IEEE 802.11b wireless cards based on
16 Intersil Prism2/2.5/3 chipset. This driver supports so called
17 Host AP mode that allows the card to act as an IEEE 802.11
18 access point.
19
20 See <http://hostap.epitest.fi/> for more information about the
21 Host AP driver configuration and tools. This site includes
22 information and tools (hostapd and wpa_supplicant) for WPA/WPA2
23 support.
24
25 This option includes the base Host AP driver code that is shared by
26 different hardware models. You will also need to enable support for
27 PLX/PCI/CS version of the driver to actually use the driver.
28
29 The driver can be compiled as a module and it will be called
30 hostap.
31
32config HOSTAP_FIRMWARE
33 bool "Support downloading firmware images with Host AP driver"
34 depends on HOSTAP
35 help
36 Configure Host AP driver to include support for firmware image
37 download. This option by itself only enables downloading to the
38 volatile memory, i.e. the card RAM. This option is required to
39 support cards that don't have firmware in flash, such as D-Link
40 DWL-520 rev E and D-Link DWL-650 rev P.
41
42 Firmware image downloading needs a user space tool, prism2_srec.
43 It is available from http://hostap.epitest.fi/.
44
45config HOSTAP_FIRMWARE_NVRAM
46 bool "Support for non-volatile firmware download"
47 depends on HOSTAP_FIRMWARE
48 help
49 Allow Host AP driver to write firmware images to the non-volatile
50 card memory, i.e. flash memory that survives power cycling.
51 Enable this option if you want to be able to change card firmware
52 permanently.
53
54 Firmware image downloading needs a user space tool, prism2_srec.
55 It is available from http://hostap.epitest.fi/.
56
57config HOSTAP_PLX
58 tristate "Host AP driver for Prism2/2.5/3 in PLX9052 PCI adaptors"
59 depends on PCI && HOSTAP && HAS_IOPORT
60 help
61 Host AP driver's version for Prism2/2.5/3 PC Cards in PLX9052 based
62 PCI adaptors.
63
64 "Host AP support for Prism2/2.5/3 IEEE 802.11b" is required for this
65 driver and its help text includes more information about the Host AP
66 driver.
67
68 The driver can be compiled as a module and will be named
69 hostap_plx.
70
71config HOSTAP_PCI
72 tristate "Host AP driver for Prism2.5 PCI adaptors"
73 depends on PCI && HOSTAP
74 help
75 Host AP driver's version for Prism2.5 PCI adaptors.
76
77 "Host AP support for Prism2/2.5/3 IEEE 802.11b" is required for this
78 driver and its help text includes more information about the Host AP
79 driver.
80
81 The driver can be compiled as a module and will be named
82 hostap_pci.
83
84config HOSTAP_CS
85 tristate "Host AP driver for Prism2/2.5/3 PC Cards"
86 depends on PCMCIA && HOSTAP
87 help
88 Host AP driver's version for Prism2/2.5/3 PC Cards.
89
90 "Host AP support for Prism2/2.5/3 IEEE 802.11b" is required for this
91 driver and its help text includes more information about the Host AP
92 driver.
93
94 The driver can be compiled as a module and will be named
95 hostap_cs.
drivers/net/wireless/intersil/hostap/Makefile+0−8
@@ -1,8 +0,0 @@
1# SPDX-License-Identifier: GPL-2.0
2hostap-y := hostap_80211_rx.o hostap_80211_tx.o hostap_ap.o hostap_info.o \
3 hostap_ioctl.o hostap_main.o hostap_proc.o
4obj-$(CONFIG_HOSTAP) += hostap.o
5
6obj-$(CONFIG_HOSTAP_CS) += hostap_cs.o
7obj-$(CONFIG_HOSTAP_PLX) += hostap_plx.o
8obj-$(CONFIG_HOSTAP_PCI) += hostap_pci.o
drivers/net/wireless/intersil/hostap/hostap.h+0−98
@@ -1,98 +0,0 @@
1/* SPDX-License-Identifier: GPL-2.0 */
2#ifndef HOSTAP_H
3#define HOSTAP_H
4
5#include <linux/ethtool.h>
6#include <linux/kernel.h>
7
8#include "hostap_wlan.h"
9#include "hostap_ap.h"
10
11static const long __maybe_unused freq_list[] = {
12 2412, 2417, 2422, 2427, 2432, 2437, 2442,
13 2447, 2452, 2457, 2462, 2467, 2472, 2484
14};
15#define FREQ_COUNT ARRAY_SIZE(freq_list)
16
17/* hostap.c */
18
19extern struct proc_dir_entry *hostap_proc;
20
21u16 hostap_tx_callback_register(local_info_t *local,
22 void (*func)(struct sk_buff *, int ok, void *),
23 void *data);
24int hostap_tx_callback_unregister(local_info_t *local, u16 idx);
25int hostap_set_word(struct net_device *dev, int rid, u16 val);
26int hostap_set_string(struct net_device *dev, int rid, const char *val);
27u16 hostap_get_porttype(local_info_t *local);
28int hostap_set_encryption(local_info_t *local);
29int hostap_set_antsel(local_info_t *local);
30int hostap_set_roaming(local_info_t *local);
31int hostap_set_auth_algs(local_info_t *local);
32void hostap_dump_rx_header(const char *name,
33 const struct hfa384x_rx_frame *rx);
34void hostap_dump_tx_header(const char *name,
35 const struct hfa384x_tx_frame *tx);
36extern const struct header_ops hostap_80211_ops;
37int hostap_80211_get_hdrlen(__le16 fc);
38struct net_device_stats *hostap_get_stats(struct net_device *dev);
39void hostap_setup_dev(struct net_device *dev, local_info_t *local,
40 int type);
41void hostap_set_multicast_list_queue(struct work_struct *work);
42int hostap_set_hostapd(local_info_t *local, int val, int rtnl_locked);
43int hostap_set_hostapd_sta(local_info_t *local, int val, int rtnl_locked);
44void hostap_cleanup(local_info_t *local);
45void hostap_cleanup_handler(void *data);
46struct net_device * hostap_add_interface(struct local_info *local,
47 int type, int rtnl_locked,
48 const char *prefix, const char *name);
49void hostap_remove_interface(struct net_device *dev, int rtnl_locked,
50 int remove_from_list);
51int prism2_update_comms_qual(struct net_device *dev);
52int prism2_sta_send_mgmt(local_info_t *local, u8 *dst, u16 stype,
53 u8 *body, size_t bodylen);
54int prism2_sta_deauth(local_info_t *local, u16 reason);
55int prism2_wds_add(local_info_t *local, u8 *remote_addr,
56 int rtnl_locked);
57int prism2_wds_del(local_info_t *local, u8 *remote_addr,
58 int rtnl_locked, int do_not_remove);
59
60
61/* hostap_ap.c */
62
63int ap_control_add_mac(struct mac_restrictions *mac_restrictions, u8 *mac);
64int ap_control_del_mac(struct mac_restrictions *mac_restrictions, u8 *mac);
65void ap_control_flush_macs(struct mac_restrictions *mac_restrictions);
66int ap_control_kick_mac(struct ap_data *ap, struct net_device *dev, u8 *mac);
67void ap_control_kickall(struct ap_data *ap);
68void * ap_crypt_get_ptrs(struct ap_data *ap, u8 *addr, int permanent,
69 struct lib80211_crypt_data ***crypt);
70int prism2_ap_get_sta_qual(local_info_t *local, struct sockaddr addr[],
71 struct iw_quality qual[], int buf_size,
72 int aplist);
73int prism2_ap_translate_scan(struct net_device *dev,
74 struct iw_request_info *info, char *buffer);
75int prism2_hostapd(struct ap_data *ap, struct prism2_hostapd_param *param);
76
77
78/* hostap_proc.c */
79
80void hostap_init_proc(local_info_t *local);
81void hostap_remove_proc(local_info_t *local);
82
83
84/* hostap_info.c */
85
86void hostap_info_init(local_info_t *local);
87void hostap_info_process(local_info_t *local, struct sk_buff *skb);
88
89
90/* hostap_ioctl.c */
91
92extern const struct iw_handler_def hostap_iw_handler_def;
93extern const struct ethtool_ops prism2_ethtool_ops;
94
95int hostap_siocdevprivate(struct net_device *dev, struct ifreq *ifr,
96 void __user *data, int cmd);
97
98#endif /* HOSTAP_H */
drivers/net/wireless/intersil/hostap/hostap_80211.h+0−97
@@ -1,97 +0,0 @@
1/* SPDX-License-Identifier: GPL-2.0 */
2#ifndef HOSTAP_80211_H
3#define HOSTAP_80211_H
4
5#include <linux/types.h>
6#include <linux/skbuff.h>
7#include <linux/netdevice.h>
8
9struct hostap_ieee80211_mgmt {
10 __le16 frame_control;
11 __le16 duration;
12 u8 da[6];
13 u8 sa[6];
14 u8 bssid[6];
15 __le16 seq_ctrl;
16 union {
17 struct {
18 __le16 auth_alg;
19 __le16 auth_transaction;
20 __le16 status_code;
21 /* possibly followed by Challenge text */
22 u8 variable[0];
23 } __packed auth;
24 struct {
25 __le16 reason_code;
26 } __packed deauth;
27 struct {
28 __le16 capab_info;
29 __le16 listen_interval;
30 /* followed by SSID and Supported rates */
31 u8 variable[0];
32 } __packed assoc_req;
33 struct {
34 __le16 capab_info;
35 __le16 status_code;
36 __le16 aid;
37 /* followed by Supported rates */
38 u8 variable[0];
39 } __packed assoc_resp, reassoc_resp;
40 struct {
41 __le16 capab_info;
42 __le16 listen_interval;
43 u8 current_ap[6];
44 /* followed by SSID and Supported rates */
45 u8 variable[0];
46 } __packed reassoc_req;
47 struct {
48 __le16 reason_code;
49 } __packed disassoc;
50 struct {
51 } __packed probe_req;
52 struct {
53 u8 timestamp[8];
54 __le16 beacon_int;
55 __le16 capab_info;
56 /* followed by some of SSID, Supported rates,
57 * FH Params, DS Params, CF Params, IBSS Params, TIM */
58 u8 variable[0];
59 } __packed beacon, probe_resp;
60 } u;
61} __packed;
62
63
64#define IEEE80211_MGMT_HDR_LEN 24
65#define IEEE80211_DATA_HDR3_LEN 24
66#define IEEE80211_DATA_HDR4_LEN 30
67
68
69struct hostap_80211_rx_status {
70 u32 mac_time;
71 u8 signal;
72 u8 noise;
73 u16 rate; /* in 100 kbps */
74};
75
76/* prism2_rx_80211 'type' argument */
77enum {
78 PRISM2_RX_MONITOR, PRISM2_RX_MGMT, PRISM2_RX_NON_ASSOC,
79 PRISM2_RX_NULLFUNC_ACK
80};
81
82int prism2_rx_80211(struct net_device *dev, struct sk_buff *skb,
83 struct hostap_80211_rx_status *rx_stats, int type);
84void hostap_80211_rx(struct net_device *dev, struct sk_buff *skb,
85 struct hostap_80211_rx_status *rx_stats);
86void hostap_dump_rx_80211(const char *name, struct sk_buff *skb,
87 struct hostap_80211_rx_status *rx_stats);
88
89void hostap_dump_tx_80211(const char *name, struct sk_buff *skb);
90netdev_tx_t hostap_data_start_xmit(struct sk_buff *skb,
91 struct net_device *dev);
92netdev_tx_t hostap_mgmt_start_xmit(struct sk_buff *skb,
93 struct net_device *dev);
94netdev_tx_t hostap_master_start_xmit(struct sk_buff *skb,
95 struct net_device *dev);
96
97#endif /* HOSTAP_80211_H */
drivers/net/wireless/intersil/hostap/hostap_80211_rx.c+0−1116
@@ -1,1116 +0,0 @@
1// SPDX-License-Identifier: GPL-2.0
2#include <linux/etherdevice.h>
3#include <linux/slab.h>
4#include <linux/export.h>
5#include <net/lib80211.h>
6#include <linux/if_arp.h>
7
8#include "hostap_80211.h"
9#include "hostap.h"
10#include "hostap_ap.h"
11
12/* See IEEE 802.1H for LLC/SNAP encapsulation/decapsulation */
13/* Ethernet-II snap header (RFC1042 for most EtherTypes) */
14static unsigned char rfc1042_header[] =
15{ 0xaa, 0xaa, 0x03, 0x00, 0x00, 0x00 };
16/* Bridge-Tunnel header (for EtherTypes ETH_P_AARP and ETH_P_IPX) */
17static unsigned char bridge_tunnel_header[] =
18{ 0xaa, 0xaa, 0x03, 0x00, 0x00, 0xf8 };
19/* No encapsulation header if EtherType < 0x600 (=length) */
20
21void hostap_dump_rx_80211(const char *name, struct sk_buff *skb,
22 struct hostap_80211_rx_status *rx_stats)
23{
24 struct ieee80211_hdr *hdr;
25 u16 fc;
26
27 hdr = (struct ieee80211_hdr *) skb->data;
28
29 printk(KERN_DEBUG "%s: RX signal=%d noise=%d rate=%d len=%d "
30 "jiffies=%ld\n",
31 name, rx_stats->signal, rx_stats->noise, rx_stats->rate,
32 skb->len, jiffies);
33
34 if (skb->len < 2)
35 return;
36
37 fc = le16_to_cpu(hdr->frame_control);
38 printk(KERN_DEBUG " FC=0x%04x (type=%d:%d)%s%s",
39 fc, (fc & IEEE80211_FCTL_FTYPE) >> 2,
40 (fc & IEEE80211_FCTL_STYPE) >> 4,
41 fc & IEEE80211_FCTL_TODS ? " [ToDS]" : "",
42 fc & IEEE80211_FCTL_FROMDS ? " [FromDS]" : "");
43
44 if (skb->len < IEEE80211_DATA_HDR3_LEN) {
45 printk("\n");
46 return;
47 }
48
49 printk(" dur=0x%04x seq=0x%04x\n", le16_to_cpu(hdr->duration_id),
50 le16_to_cpu(hdr->seq_ctrl));
51
52 printk(KERN_DEBUG " A1=%pM", hdr->addr1);
53 printk(" A2=%pM", hdr->addr2);
54 printk(" A3=%pM", hdr->addr3);
55 if (skb->len >= 30)
56 printk(" A4=%pM", hdr->addr4);
57 printk("\n");
58}
59
60
61/* Send RX frame to netif with 802.11 (and possible prism) header.
62 * Called from hardware or software IRQ context. */
63int prism2_rx_80211(struct net_device *dev, struct sk_buff *skb,
64 struct hostap_80211_rx_status *rx_stats, int type)
65{
66 struct hostap_interface *iface;
67 local_info_t *local;
68 int hdrlen, phdrlen, head_need, tail_need;
69 u16 fc;
70 int prism_header, ret;
71 struct ieee80211_hdr *fhdr;
72
73 iface = netdev_priv(dev);
74 local = iface->local;
75
76 if (dev->type == ARPHRD_IEEE80211_PRISM) {
77 if (local->monitor_type == PRISM2_MONITOR_PRISM) {
78 prism_header = 1;
79 phdrlen = sizeof(struct linux_wlan_ng_prism_hdr);
80 } else { /* local->monitor_type == PRISM2_MONITOR_CAPHDR */
81 prism_header = 2;
82 phdrlen = sizeof(struct linux_wlan_ng_cap_hdr);
83 }
84 } else if (dev->type == ARPHRD_IEEE80211_RADIOTAP) {
85 prism_header = 3;
86 phdrlen = sizeof(struct hostap_radiotap_rx);
87 } else {
88 prism_header = 0;
89 phdrlen = 0;
90 }
91
92 fhdr = (struct ieee80211_hdr *) skb->data;
93 fc = le16_to_cpu(fhdr->frame_control);
94
95 if (type == PRISM2_RX_MGMT && (fc & IEEE80211_FCTL_VERS)) {
96 printk(KERN_DEBUG "%s: dropped management frame with header "
97 "version %d\n", dev->name, fc & IEEE80211_FCTL_VERS);
98 dev_kfree_skb_any(skb);
99 return 0;
100 }
101
102 hdrlen = hostap_80211_get_hdrlen(fhdr->frame_control);
103
104 /* check if there is enough room for extra data; if not, expand skb
105 * buffer to be large enough for the changes */
106 head_need = phdrlen;
107 tail_need = 0;
108#ifdef PRISM2_ADD_BOGUS_CRC
109 tail_need += 4;
110#endif /* PRISM2_ADD_BOGUS_CRC */
111
112 head_need -= skb_headroom(skb);
113 tail_need -= skb_tailroom(skb);
114
115 if (head_need > 0 || tail_need > 0) {
116 if (pskb_expand_head(skb, head_need > 0 ? head_need : 0,
117 tail_need > 0 ? tail_need : 0,
118 GFP_ATOMIC)) {
119 printk(KERN_DEBUG "%s: prism2_rx_80211 failed to "
120 "reallocate skb buffer\n", dev->name);
121 dev_kfree_skb_any(skb);
122 return 0;
123 }
124 }
125
126 /* We now have an skb with enough head and tail room, so just insert
127 * the extra data */
128
129#ifdef PRISM2_ADD_BOGUS_CRC
130 memset(skb_put(skb, 4), 0xff, 4); /* Prism2 strips CRC */
131#endif /* PRISM2_ADD_BOGUS_CRC */
132
133 if (prism_header == 1) {
134 struct linux_wlan_ng_prism_hdr *hdr;
135 hdr = skb_push(skb, phdrlen);
136 memset(hdr, 0, phdrlen);
137 hdr->msgcode = LWNG_CAP_DID_BASE;
138 hdr->msglen = sizeof(*hdr);
139 memcpy(hdr->devname, dev->name, sizeof(hdr->devname));
140#define LWNG_SETVAL(f,i,s,l,d) \
141hdr->f.did = LWNG_CAP_DID_BASE | (i << 12); \
142hdr->f.status = s; hdr->f.len = l; hdr->f.data = d
143 LWNG_SETVAL(hosttime, 1, 0, 4, jiffies);
144 LWNG_SETVAL(mactime, 2, 0, 4, rx_stats->mac_time);
145 LWNG_SETVAL(channel, 3, 1 /* no value */, 4, 0);
146 LWNG_SETVAL(rssi, 4, 1 /* no value */, 4, 0);
147 LWNG_SETVAL(sq, 5, 1 /* no value */, 4, 0);
148 LWNG_SETVAL(signal, 6, 0, 4, rx_stats->signal);
149 LWNG_SETVAL(noise, 7, 0, 4, rx_stats->noise);
150 LWNG_SETVAL(rate, 8, 0, 4, rx_stats->rate / 5);
151 LWNG_SETVAL(istx, 9, 0, 4, 0);
152 LWNG_SETVAL(frmlen, 10, 0, 4, skb->len - phdrlen);
153#undef LWNG_SETVAL
154 } else if (prism_header == 2) {
155 struct linux_wlan_ng_cap_hdr *hdr;
156 hdr = skb_push(skb, phdrlen);
157 memset(hdr, 0, phdrlen);
158 hdr->version = htonl(LWNG_CAPHDR_VERSION);
159 hdr->length = htonl(phdrlen);
160 hdr->mactime = __cpu_to_be64(rx_stats->mac_time);
161 hdr->hosttime = __cpu_to_be64(jiffies);
162 hdr->phytype = htonl(4); /* dss_dot11_b */
163 hdr->channel = htonl(local->channel);
164 hdr->datarate = htonl(rx_stats->rate);
165 hdr->antenna = htonl(0); /* unknown */
166 hdr->priority = htonl(0); /* unknown */
167 hdr->ssi_type = htonl(3); /* raw */
168 hdr->ssi_signal = htonl(rx_stats->signal);
169 hdr->ssi_noise = htonl(rx_stats->noise);
170 hdr->preamble = htonl(0); /* unknown */
171 hdr->encoding = htonl(1); /* cck */
172 } else if (prism_header == 3) {
173 struct hostap_radiotap_rx *hdr;
174 hdr = skb_push(skb, phdrlen);
175 memset(hdr, 0, phdrlen);
176 hdr->hdr.it_len = cpu_to_le16(phdrlen);
177 hdr->hdr.it_present =
178 cpu_to_le32((1 << IEEE80211_RADIOTAP_TSFT) |
179 (1 << IEEE80211_RADIOTAP_CHANNEL) |
180 (1 << IEEE80211_RADIOTAP_RATE) |
181 (1 << IEEE80211_RADIOTAP_DBM_ANTSIGNAL) |
182 (1 << IEEE80211_RADIOTAP_DBM_ANTNOISE));
183 hdr->tsft = cpu_to_le64(rx_stats->mac_time);
184 hdr->chan_freq = cpu_to_le16(freq_list[local->channel - 1]);
185 hdr->chan_flags = cpu_to_le16(IEEE80211_CHAN_CCK |
186 IEEE80211_CHAN_2GHZ);
187 hdr->rate = rx_stats->rate / 5;
188 hdr->dbm_antsignal = rx_stats->signal;
189 hdr->dbm_antnoise = rx_stats->noise;
190 }
191
192 ret = skb->len - phdrlen;
193 skb->dev = dev;
194 skb_reset_mac_header(skb);
195 skb_pull(skb, hdrlen);
196 if (prism_header)
197 skb_pull(skb, phdrlen);
198 skb->pkt_type = PACKET_OTHERHOST;
199 skb->protocol = cpu_to_be16(ETH_P_802_2);
200 memset(skb->cb, 0, sizeof(skb->cb));
201 netif_rx(skb);
202
203 return ret;
204}
205
206
207/* Called only as a tasklet (software IRQ) */
208static void monitor_rx(struct net_device *dev, struct sk_buff *skb,
209 struct hostap_80211_rx_status *rx_stats)
210{
211 int len;
212
213 len = prism2_rx_80211(dev, skb, rx_stats, PRISM2_RX_MONITOR);
214 dev->stats.rx_packets++;
215 dev->stats.rx_bytes += len;
216}
217
218
219/* Called only as a tasklet (software IRQ) */
220static struct prism2_frag_entry *
221prism2_frag_cache_find(local_info_t *local, unsigned int seq,
222 unsigned int frag, u8 *src, u8 *dst)
223{
224 struct prism2_frag_entry *entry;
225 int i;
226
227 for (i = 0; i < PRISM2_FRAG_CACHE_LEN; i++) {
228 entry = &local->frag_cache[i];
229 if (entry->skb != NULL &&
230 time_after(jiffies, entry->first_frag_time + 2 * HZ)) {
231 printk(KERN_DEBUG "%s: expiring fragment cache entry "
232 "seq=%u last_frag=%u\n",
233 local->dev->name, entry->seq, entry->last_frag);
234 dev_kfree_skb(entry->skb);
235 entry->skb = NULL;
236 }
237
238 if (entry->skb != NULL && entry->seq == seq &&
239 (entry->last_frag + 1 == frag || frag == -1) &&
240 memcmp(entry->src_addr, src, ETH_ALEN) == 0 &&
241 memcmp(entry->dst_addr, dst, ETH_ALEN) == 0)
242 return entry;
243 }
244
245 return NULL;
246}
247
248
249/* Called only as a tasklet (software IRQ) */
250static struct sk_buff *
251prism2_frag_cache_get(local_info_t *local, struct ieee80211_hdr *hdr)
252{
253 struct sk_buff *skb = NULL;
254 u16 sc;
255 unsigned int frag, seq;
256 struct prism2_frag_entry *entry;
257
258 sc = le16_to_cpu(hdr->seq_ctrl);
259 frag = sc & IEEE80211_SCTL_FRAG;
260 seq = (sc & IEEE80211_SCTL_SEQ) >> 4;
261
262 if (frag == 0) {
263 /* Reserve enough space to fit maximum frame length */
264 skb = dev_alloc_skb(local->dev->mtu +
265 sizeof(struct ieee80211_hdr) +
266 8 /* LLC */ +
267 2 /* alignment */ +
268 8 /* WEP */ + ETH_ALEN /* WDS */);
269 if (skb == NULL)
270 return NULL;
271
272 entry = &local->frag_cache[local->frag_next_idx];
273 local->frag_next_idx++;
274 if (local->frag_next_idx >= PRISM2_FRAG_CACHE_LEN)
275 local->frag_next_idx = 0;
276
277 if (entry->skb != NULL)
278 dev_kfree_skb(entry->skb);
279
280 entry->first_frag_time = jiffies;
281 entry->seq = seq;
282 entry->last_frag = frag;
283 entry->skb = skb;
284 memcpy(entry->src_addr, hdr->addr2, ETH_ALEN);
285 memcpy(entry->dst_addr, hdr->addr1, ETH_ALEN);
286 } else {
287 /* received a fragment of a frame for which the head fragment
288 * should have already been received */
289 entry = prism2_frag_cache_find(local, seq, frag, hdr->addr2,
290 hdr->addr1);
291 if (entry != NULL) {
292 entry->last_frag = frag;
293 skb = entry->skb;
294 }
295 }
296
297 return skb;
298}
299
300
301/* Called only as a tasklet (software IRQ) */
302static int prism2_frag_cache_invalidate(local_info_t *local,
303 struct ieee80211_hdr *hdr)
304{
305 u16 sc;
306 unsigned int seq;
307 struct prism2_frag_entry *entry;
308
309 sc = le16_to_cpu(hdr->seq_ctrl);
310 seq = (sc & IEEE80211_SCTL_SEQ) >> 4;
311
312 entry = prism2_frag_cache_find(local, seq, -1, hdr->addr2, hdr->addr1);
313
314 if (entry == NULL) {
315 printk(KERN_DEBUG "%s: could not invalidate fragment cache "
316 "entry (seq=%u)\n",
317 local->dev->name, seq);
318 return -1;
319 }
320
321 entry->skb = NULL;
322 return 0;
323}
324
325
326static struct hostap_bss_info *__hostap_get_bss(local_info_t *local, u8 *bssid,
327 u8 *ssid, size_t ssid_len)
328{
329 struct list_head *ptr;
330 struct hostap_bss_info *bss;
331
332 list_for_each(ptr, &local->bss_list) {
333 bss = list_entry(ptr, struct hostap_bss_info, list);
334 if (memcmp(bss->bssid, bssid, ETH_ALEN) == 0 &&
335 (ssid == NULL ||
336 (ssid_len == bss->ssid_len &&
337 memcmp(ssid, bss->ssid, ssid_len) == 0))) {
338 list_move(&bss->list, &local->bss_list);
339 return bss;
340 }
341 }
342
343 return NULL;
344}
345
346
347static struct hostap_bss_info *__hostap_add_bss(local_info_t *local, u8 *bssid,
348 u8 *ssid, size_t ssid_len)
349{
350 struct hostap_bss_info *bss;
351
352 if (local->num_bss_info >= HOSTAP_MAX_BSS_COUNT) {
353 bss = list_entry(local->bss_list.prev,
354 struct hostap_bss_info, list);
355 list_del(&bss->list);
356 local->num_bss_info--;
357 } else {
358 bss = kmalloc(sizeof(*bss), GFP_ATOMIC);
359 if (bss == NULL)
360 return NULL;
361 }
362
363 memset(bss, 0, sizeof(*bss));
364 memcpy(bss->bssid, bssid, ETH_ALEN);
365 memcpy(bss->ssid, ssid, ssid_len);
366 bss->ssid_len = ssid_len;
367 local->num_bss_info++;
368 list_add(&bss->list, &local->bss_list);
369 return bss;
370}
371
372
373static void __hostap_expire_bss(local_info_t *local)
374{
375 struct hostap_bss_info *bss;
376
377 while (local->num_bss_info > 0) {
378 bss = list_entry(local->bss_list.prev,
379 struct hostap_bss_info, list);
380 if (!time_after(jiffies, bss->last_update + 60 * HZ))
381 break;
382
383 list_del(&bss->list);
384 local->num_bss_info--;
385 kfree(bss);
386 }
387}
388
389
390/* Both IEEE 802.11 Beacon and Probe Response frames have similar structure, so
391 * the same routine can be used to parse both of them. */
392static void hostap_rx_sta_beacon(local_info_t *local, struct sk_buff *skb,
393 int stype)
394{
395 struct hostap_ieee80211_mgmt *mgmt;
396 int left, chan = 0;
397 u8 *pos;
398 u8 *ssid = NULL, *wpa = NULL, *rsn = NULL;
399 size_t ssid_len = 0, wpa_len = 0, rsn_len = 0;
400 struct hostap_bss_info *bss;
401
402 if (skb->len < IEEE80211_MGMT_HDR_LEN + sizeof(mgmt->u.beacon))
403 return;
404
405 mgmt = (struct hostap_ieee80211_mgmt *) skb->data;
406 pos = mgmt->u.beacon.variable;
407 left = skb->len - (pos - skb->data);
408
409 while (left >= 2) {
410 if (2 + pos[1] > left)
411 return; /* parse failed */
412 switch (*pos) {
413 case WLAN_EID_SSID:
414 ssid = pos + 2;
415 ssid_len = pos[1];
416 break;
417 case WLAN_EID_VENDOR_SPECIFIC:
418 if (pos[1] >= 4 &&
419 pos[2] == 0x00 && pos[3] == 0x50 &&
420 pos[4] == 0xf2 && pos[5] == 1) {
421 wpa = pos;
422 wpa_len = pos[1] + 2;
423 }
424 break;
425 case WLAN_EID_RSN:
426 rsn = pos;
427 rsn_len = pos[1] + 2;
428 break;
429 case WLAN_EID_DS_PARAMS:
430 if (pos[1] >= 1)
431 chan = pos[2];
432 break;
433 }
434 left -= 2 + pos[1];
435 pos += 2 + pos[1];
436 }
437
438 if (wpa_len > MAX_WPA_IE_LEN)
439 wpa_len = MAX_WPA_IE_LEN;
440 if (rsn_len > MAX_WPA_IE_LEN)
441 rsn_len = MAX_WPA_IE_LEN;
442 if (ssid_len > sizeof(bss->ssid))
443 ssid_len = sizeof(bss->ssid);
444
445 spin_lock(&local->lock);
446 bss = __hostap_get_bss(local, mgmt->bssid, ssid, ssid_len);
447 if (bss == NULL)
448 bss = __hostap_add_bss(local, mgmt->bssid, ssid, ssid_len);
449 if (bss) {
450 bss->last_update = jiffies;
451 bss->count++;
452 bss->capab_info = le16_to_cpu(mgmt->u.beacon.capab_info);
453 if (wpa) {
454 memcpy(bss->wpa_ie, wpa, wpa_len);
455 bss->wpa_ie_len = wpa_len;
456 } else
457 bss->wpa_ie_len = 0;
458 if (rsn) {
459 memcpy(bss->rsn_ie, rsn, rsn_len);
460 bss->rsn_ie_len = rsn_len;
461 } else
462 bss->rsn_ie_len = 0;
463 bss->chan = chan;
464 }
465 __hostap_expire_bss(local);
466 spin_unlock(&local->lock);
467}
468
469
470static int
471hostap_rx_frame_mgmt(local_info_t *local, struct sk_buff *skb,
472 struct hostap_80211_rx_status *rx_stats, u16 type,
473 u16 stype)
474{
475 if (local->iw_mode == IW_MODE_MASTER)
476 hostap_update_sta_ps(local, (struct ieee80211_hdr *) skb->data);
477
478 if (local->hostapd && type == IEEE80211_FTYPE_MGMT) {
479 if (stype == IEEE80211_STYPE_BEACON &&
480 local->iw_mode == IW_MODE_MASTER) {
481 struct sk_buff *skb2;
482 /* Process beacon frames also in kernel driver to
483 * update STA(AP) table statistics */
484 skb2 = skb_clone(skb, GFP_ATOMIC);
485 if (skb2)
486 hostap_rx(skb2->dev, skb2, rx_stats);
487 }
488
489 /* send management frames to the user space daemon for
490 * processing */
491 local->apdevstats.rx_packets++;
492 local->apdevstats.rx_bytes += skb->len;
493 if (local->apdev == NULL)
494 return -1;
495 prism2_rx_80211(local->apdev, skb, rx_stats, PRISM2_RX_MGMT);
496 return 0;
497 }
498
499 if (local->iw_mode == IW_MODE_MASTER) {
500 if (type != IEEE80211_FTYPE_MGMT &&
501 type != IEEE80211_FTYPE_CTL) {
502 printk(KERN_DEBUG "%s: unknown management frame "
503 "(type=0x%02x, stype=0x%02x) dropped\n",
504 skb->dev->name, type >> 2, stype >> 4);
505 return -1;
506 }
507
508 hostap_rx(skb->dev, skb, rx_stats);
509 return 0;
510 } else if (type == IEEE80211_FTYPE_MGMT &&
511 (stype == IEEE80211_STYPE_BEACON ||
512 stype == IEEE80211_STYPE_PROBE_RESP)) {
513 hostap_rx_sta_beacon(local, skb, stype);
514 return -1;
515 } else if (type == IEEE80211_FTYPE_MGMT &&
516 (stype == IEEE80211_STYPE_ASSOC_RESP ||
517 stype == IEEE80211_STYPE_REASSOC_RESP)) {
518 /* Ignore (Re)AssocResp silently since these are not currently
519 * needed but are still received when WPA/RSN mode is enabled.
520 */
521 return -1;
522 } else {
523 printk(KERN_DEBUG "%s: hostap_rx_frame_mgmt: dropped unhandled"
524 " management frame in non-Host AP mode (type=%d:%d)\n",
525 skb->dev->name, type >> 2, stype >> 4);
526 return -1;
527 }
528}
529
530
531/* Called only as a tasklet (software IRQ) */
532static struct net_device *prism2_rx_get_wds(local_info_t *local,
533 u8 *addr)
534{
535 struct hostap_interface *iface = NULL;
536 struct list_head *ptr;
537
538 read_lock_bh(&local->iface_lock);
539 list_for_each(ptr, &local->hostap_interfaces) {
540 iface = list_entry(ptr, struct hostap_interface, list);
541 if (iface->type == HOSTAP_INTERFACE_WDS &&
542 memcmp(iface->u.wds.remote_addr, addr, ETH_ALEN) == 0)
543 break;
544 iface = NULL;
545 }
546 read_unlock_bh(&local->iface_lock);
547
548 return iface ? iface->dev : NULL;
549}
550
551
552static int
553hostap_rx_frame_wds(local_info_t *local, struct ieee80211_hdr *hdr, u16 fc,
554 struct net_device **wds)
555{
556 /* FIX: is this really supposed to accept WDS frames only in Master
557 * mode? What about Repeater or Managed with WDS frames? */
558 if ((fc & (IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS)) !=
559 (IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS) &&
560 (local->iw_mode != IW_MODE_MASTER || !(fc & IEEE80211_FCTL_TODS)))
561 return 0; /* not a WDS frame */
562
563 /* Possible WDS frame: either IEEE 802.11 compliant (if FromDS)
564 * or own non-standard frame with 4th address after payload */
565 if (!ether_addr_equal(hdr->addr1, local->dev->dev_addr) &&
566 (hdr->addr1[0] != 0xff || hdr->addr1[1] != 0xff ||
567 hdr->addr1[2] != 0xff || hdr->addr1[3] != 0xff ||
568 hdr->addr1[4] != 0xff || hdr->addr1[5] != 0xff)) {
569 /* RA (or BSSID) is not ours - drop */
570 PDEBUG(DEBUG_EXTRA2, "%s: received WDS frame with "
571 "not own or broadcast %s=%pM\n",
572 local->dev->name,
573 fc & IEEE80211_FCTL_FROMDS ? "RA" : "BSSID",
574 hdr->addr1);
575 return -1;
576 }
577
578 /* check if the frame came from a registered WDS connection */
579 *wds = prism2_rx_get_wds(local, hdr->addr2);
580 if (*wds == NULL && fc & IEEE80211_FCTL_FROMDS &&
581 (local->iw_mode != IW_MODE_INFRA ||
582 !(local->wds_type & HOSTAP_WDS_AP_CLIENT) ||
583 memcmp(hdr->addr2, local->bssid, ETH_ALEN) != 0)) {
584 /* require that WDS link has been registered with TA or the
585 * frame is from current AP when using 'AP client mode' */
586 PDEBUG(DEBUG_EXTRA, "%s: received WDS[4 addr] frame "
587 "from unknown TA=%pM\n",
588 local->dev->name, hdr->addr2);
589 if (local->ap && local->ap->autom_ap_wds)
590 hostap_wds_link_oper(local, hdr->addr2, WDS_ADD);
591 return -1;
592 }
593
594 if (*wds && !(fc & IEEE80211_FCTL_FROMDS) && local->ap &&
595 hostap_is_sta_assoc(local->ap, hdr->addr2)) {
596 /* STA is actually associated with us even though it has a
597 * registered WDS link. Assume it is in 'AP client' mode.
598 * Since this is a 3-addr frame, assume it is not (bogus) WDS
599 * frame and process it like any normal ToDS frame from
600 * associated STA. */
601 *wds = NULL;
602 }
603
604 return 0;
605}
606
607
608static int hostap_is_eapol_frame(local_info_t *local, struct sk_buff *skb)
609{
610 struct net_device *dev = local->dev;
611 u16 fc, ethertype;
612 struct ieee80211_hdr *hdr;
613 u8 *pos;
614
615 if (skb->len < 24)
616 return 0;
617
618 hdr = (struct ieee80211_hdr *) skb->data;
619 fc = le16_to_cpu(hdr->frame_control);
620
621 /* check that the frame is unicast frame to us */
622 if ((fc & (IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS)) ==
623 IEEE80211_FCTL_TODS &&
624 ether_addr_equal(hdr->addr1, dev->dev_addr) &&
625 ether_addr_equal(hdr->addr3, dev->dev_addr)) {
626 /* ToDS frame with own addr BSSID and DA */
627 } else if ((fc & (IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS)) ==
628 IEEE80211_FCTL_FROMDS &&
629 ether_addr_equal(hdr->addr1, dev->dev_addr)) {
630 /* FromDS frame with own addr as DA */
631 } else
632 return 0;
633
634 if (skb->len < 24 + 8)
635 return 0;
636
637 /* check for port access entity Ethernet type */
638 pos = skb->data + 24;
639 ethertype = (pos[6] << 8) | pos[7];
640 if (ethertype == ETH_P_PAE)
641 return 1;
642
643 return 0;
644}
645
646
647/* Called only as a tasklet (software IRQ) */
648static int
649hostap_rx_frame_decrypt(local_info_t *local, struct sk_buff *skb,
650 struct lib80211_crypt_data *crypt)
651{
652 struct ieee80211_hdr *hdr;
653 int res, hdrlen;
654
655 if (crypt == NULL || crypt->ops->decrypt_mpdu == NULL)
656 return 0;
657
658 hdr = (struct ieee80211_hdr *) skb->data;
659 hdrlen = hostap_80211_get_hdrlen(hdr->frame_control);
660
661 if (local->tkip_countermeasures &&
662 strcmp(crypt->ops->name, "TKIP") == 0) {
663 if (net_ratelimit()) {
664 printk(KERN_DEBUG "%s: TKIP countermeasures: dropped "
665 "received packet from %pM\n",
666 local->dev->name, hdr->addr2);
667 }
668 return -1;
669 }
670
671 atomic_inc(&crypt->refcnt);
672 res = crypt->ops->decrypt_mpdu(skb, hdrlen, crypt->priv);
673 atomic_dec(&crypt->refcnt);
674 if (res < 0) {
675 printk(KERN_DEBUG "%s: decryption failed (SA=%pM) res=%d\n",
676 local->dev->name, hdr->addr2, res);
677 local->comm_tallies.rx_discards_wep_undecryptable++;
678 return -1;
679 }
680
681 return res;
682}
683
684
685/* Called only as a tasklet (software IRQ) */
686static int
687hostap_rx_frame_decrypt_msdu(local_info_t *local, struct sk_buff *skb,
688 int keyidx, struct lib80211_crypt_data *crypt)
689{
690 struct ieee80211_hdr *hdr;
691 int res, hdrlen;
692
693 if (crypt == NULL || crypt->ops->decrypt_msdu == NULL)
694 return 0;
695
696 hdr = (struct ieee80211_hdr *) skb->data;
697 hdrlen = hostap_80211_get_hdrlen(hdr->frame_control);
698
699 atomic_inc(&crypt->refcnt);
700 res = crypt->ops->decrypt_msdu(skb, keyidx, hdrlen, crypt->priv);
701 atomic_dec(&crypt->refcnt);
702 if (res < 0) {
703 printk(KERN_DEBUG "%s: MSDU decryption/MIC verification failed"
704 " (SA=%pM keyidx=%d)\n",
705 local->dev->name, hdr->addr2, keyidx);
706 return -1;
707 }
708
709 return 0;
710}
711
712
713/* All received frames are sent to this function. @skb contains the frame in
714 * IEEE 802.11 format, i.e., in the format it was sent over air.
715 * This function is called only as a tasklet (software IRQ). */
716void hostap_80211_rx(struct net_device *dev, struct sk_buff *skb,
717 struct hostap_80211_rx_status *rx_stats)
718{
719 struct hostap_interface *iface;
720 local_info_t *local;
721 struct ieee80211_hdr *hdr;
722 size_t hdrlen;
723 u16 fc, type, stype, sc;
724 struct net_device *wds = NULL;
725 unsigned int frag;
726 u8 *payload;
727 struct sk_buff *skb2 = NULL;
728 u16 ethertype;
729 int frame_authorized = 0;
730 int from_assoc_ap = 0;
731 u8 dst[ETH_ALEN];
732 u8 src[ETH_ALEN];
733 struct lib80211_crypt_data *crypt = NULL;
734 void *sta = NULL;
735 int keyidx = 0;
736
737 iface = netdev_priv(dev);
738 local = iface->local;
739 iface->stats.rx_packets++;
740 iface->stats.rx_bytes += skb->len;
741
742 /* dev is the master radio device; change this to be the default
743 * virtual interface (this may be changed to WDS device below) */
744 dev = local->ddev;
745 iface = netdev_priv(dev);
746
747 hdr = (struct ieee80211_hdr *) skb->data;
748
749 if (skb->len < 10)
750 goto rx_dropped;
751
752 fc = le16_to_cpu(hdr->frame_control);
753 type = fc & IEEE80211_FCTL_FTYPE;
754 stype = fc & IEEE80211_FCTL_STYPE;
755 sc = le16_to_cpu(hdr->seq_ctrl);
756 frag = sc & IEEE80211_SCTL_FRAG;
757 hdrlen = hostap_80211_get_hdrlen(hdr->frame_control);
758
759 /* Put this code here so that we avoid duplicating it in all
760 * Rx paths. - Jean II */
761#ifdef IW_WIRELESS_SPY /* defined in iw_handler.h */
762 /* If spy monitoring on */
763 if (iface->spy_data.spy_number > 0) {
764 struct iw_quality wstats;
765 wstats.level = rx_stats->signal;
766 wstats.noise = rx_stats->noise;
767 wstats.updated = IW_QUAL_LEVEL_UPDATED | IW_QUAL_NOISE_UPDATED
768 | IW_QUAL_QUAL_INVALID | IW_QUAL_DBM;
769 /* Update spy records */
770 wireless_spy_update(dev, hdr->addr2, &wstats);
771 }
772#endif /* IW_WIRELESS_SPY */
773 hostap_update_rx_stats(local->ap, hdr, rx_stats);
774
775 if (local->iw_mode == IW_MODE_MONITOR) {
776 monitor_rx(dev, skb, rx_stats);
777 return;
778 }
779
780 if (local->host_decrypt) {
781 int idx = 0;
782 if (skb->len >= hdrlen + 3)
783 idx = skb->data[hdrlen + 3] >> 6;
784 crypt = local->crypt_info.crypt[idx];
785 sta = NULL;
786
787 /* Use station specific key to override default keys if the
788 * receiver address is a unicast address ("individual RA"). If
789 * bcrx_sta_key parameter is set, station specific key is used
790 * even with broad/multicast targets (this is against IEEE
791 * 802.11, but makes it easier to use different keys with
792 * stations that do not support WEP key mapping). */
793
794 if (!(hdr->addr1[0] & 0x01) || local->bcrx_sta_key)
795 (void) hostap_handle_sta_crypto(local, hdr, &crypt,
796 &sta);
797
798 /* allow NULL decrypt to indicate an station specific override
799 * for default encryption */
800 if (crypt && (crypt->ops == NULL ||
801 crypt->ops->decrypt_mpdu == NULL))
802 crypt = NULL;
803
804 if (!crypt && (fc & IEEE80211_FCTL_PROTECTED)) {
805#if 0
806 /* This seems to be triggered by some (multicast?)
807 * frames from other than current BSS, so just drop the
808 * frames silently instead of filling system log with
809 * these reports. */
810 printk(KERN_DEBUG "%s: WEP decryption failed (not set)"
811 " (SA=%pM)\n",
812 local->dev->name, hdr->addr2);
813#endif
814 local->comm_tallies.rx_discards_wep_undecryptable++;
815 goto rx_dropped;
816 }
817 }
818
819 if (type != IEEE80211_FTYPE_DATA) {
820 if (type == IEEE80211_FTYPE_MGMT &&
821 stype == IEEE80211_STYPE_AUTH &&
822 fc & IEEE80211_FCTL_PROTECTED && local->host_decrypt &&
823 (keyidx = hostap_rx_frame_decrypt(local, skb, crypt)) < 0)
824 {
825 printk(KERN_DEBUG "%s: failed to decrypt mgmt::auth "
826 "from %pM\n", dev->name, hdr->addr2);
827 /* TODO: could inform hostapd about this so that it
828 * could send auth failure report */
829 goto rx_dropped;
830 }
831
832 if (hostap_rx_frame_mgmt(local, skb, rx_stats, type, stype))
833 goto rx_dropped;
834 else
835 goto rx_exit;
836 }
837
838 /* Data frame - extract src/dst addresses */
839 if (skb->len < IEEE80211_DATA_HDR3_LEN)
840 goto rx_dropped;
841
842 switch (fc & (IEEE80211_FCTL_FROMDS | IEEE80211_FCTL_TODS)) {
843 case IEEE80211_FCTL_FROMDS:
844 memcpy(dst, hdr->addr1, ETH_ALEN);
845 memcpy(src, hdr->addr3, ETH_ALEN);
846 break;
847 case IEEE80211_FCTL_TODS:
848 memcpy(dst, hdr->addr3, ETH_ALEN);
849 memcpy(src, hdr->addr2, ETH_ALEN);
850 break;
851 case IEEE80211_FCTL_FROMDS | IEEE80211_FCTL_TODS:
852 if (skb->len < IEEE80211_DATA_HDR4_LEN)
853 goto rx_dropped;
854 memcpy(dst, hdr->addr3, ETH_ALEN);
855 memcpy(src, hdr->addr4, ETH_ALEN);
856 break;
857 default:
858 memcpy(dst, hdr->addr1, ETH_ALEN);
859 memcpy(src, hdr->addr2, ETH_ALEN);
860 break;
861 }
862
863 if (hostap_rx_frame_wds(local, hdr, fc, &wds))
864 goto rx_dropped;
865 if (wds)
866 skb->dev = dev = wds;
867
868 if (local->iw_mode == IW_MODE_MASTER && !wds &&
869 (fc & (IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS)) ==
870 IEEE80211_FCTL_FROMDS &&
871 local->stadev &&
872 memcmp(hdr->addr2, local->assoc_ap_addr, ETH_ALEN) == 0) {
873 /* Frame from BSSID of the AP for which we are a client */
874 skb->dev = dev = local->stadev;
875 from_assoc_ap = 1;
876 }
877
878 if ((local->iw_mode == IW_MODE_MASTER ||
879 local->iw_mode == IW_MODE_REPEAT) &&
880 !from_assoc_ap) {
881 switch (hostap_handle_sta_rx(local, dev, skb, rx_stats,
882 wds != NULL)) {
883 case AP_RX_CONTINUE_NOT_AUTHORIZED:
884 frame_authorized = 0;
885 break;
886 case AP_RX_CONTINUE:
887 frame_authorized = 1;
888 break;
889 case AP_RX_DROP:
890 goto rx_dropped;
891 case AP_RX_EXIT:
892 goto rx_exit;
893 }
894 }
895
896 /* Nullfunc frames may have PS-bit set, so they must be passed to
897 * hostap_handle_sta_rx() before being dropped here. */
898 if (stype != IEEE80211_STYPE_DATA &&
899 stype != IEEE80211_STYPE_DATA_CFACK &&
900 stype != IEEE80211_STYPE_DATA_CFPOLL &&
901 stype != IEEE80211_STYPE_DATA_CFACKPOLL) {
902 if (stype != IEEE80211_STYPE_NULLFUNC)
903 printk(KERN_DEBUG "%s: RX: dropped data frame "
904 "with no data (type=0x%02x, subtype=0x%02x)\n",
905 dev->name, type >> 2, stype >> 4);
906 goto rx_dropped;
907 }
908
909 /* skb: hdr + (possibly fragmented, possibly encrypted) payload */
910
911 if (local->host_decrypt && (fc & IEEE80211_FCTL_PROTECTED) &&
912 (keyidx = hostap_rx_frame_decrypt(local, skb, crypt)) < 0)
913 goto rx_dropped;
914 hdr = (struct ieee80211_hdr *) skb->data;
915
916 /* skb: hdr + (possibly fragmented) plaintext payload */
917
918 if (local->host_decrypt && (fc & IEEE80211_FCTL_PROTECTED) &&
919 (frag != 0 || (fc & IEEE80211_FCTL_MOREFRAGS))) {
920 int flen;
921 struct sk_buff *frag_skb =
922 prism2_frag_cache_get(local, hdr);
923 if (!frag_skb) {
924 printk(KERN_DEBUG "%s: Rx cannot get skb from "
925 "fragment cache (morefrag=%d seq=%u frag=%u)\n",
926 dev->name, (fc & IEEE80211_FCTL_MOREFRAGS) != 0,
927 (sc & IEEE80211_SCTL_SEQ) >> 4, frag);
928 goto rx_dropped;
929 }
930
931 flen = skb->len;
932 if (frag != 0)
933 flen -= hdrlen;
934
935 if (frag_skb->tail + flen > frag_skb->end) {
936 printk(KERN_WARNING "%s: host decrypted and "
937 "reassembled frame did not fit skb\n",
938 dev->name);
939 prism2_frag_cache_invalidate(local, hdr);
940 goto rx_dropped;
941 }
942
943 if (frag == 0) {
944 /* copy first fragment (including full headers) into
945 * beginning of the fragment cache skb */
946 skb_copy_from_linear_data(skb, skb_put(frag_skb, flen),
947 flen);
948 } else {
949 /* append frame payload to the end of the fragment
950 * cache skb */
951 skb_copy_from_linear_data_offset(skb, hdrlen,
952 skb_put(frag_skb,
953 flen), flen);
954 }
955 dev_kfree_skb(skb);
956 skb = NULL;
957
958 if (fc & IEEE80211_FCTL_MOREFRAGS) {
959 /* more fragments expected - leave the skb in fragment
960 * cache for now; it will be delivered to upper layers
961 * after all fragments have been received */
962 goto rx_exit;
963 }
964
965 /* this was the last fragment and the frame will be
966 * delivered, so remove skb from fragment cache */
967 skb = frag_skb;
968 hdr = (struct ieee80211_hdr *) skb->data;
969 prism2_frag_cache_invalidate(local, hdr);
970 }
971
972 /* skb: hdr + (possible reassembled) full MSDU payload; possibly still
973 * encrypted/authenticated */
974
975 if (local->host_decrypt && (fc & IEEE80211_FCTL_PROTECTED) &&
976 hostap_rx_frame_decrypt_msdu(local, skb, keyidx, crypt))
977 goto rx_dropped;
978
979 hdr = (struct ieee80211_hdr *) skb->data;
980 if (crypt && !(fc & IEEE80211_FCTL_PROTECTED) && !local->open_wep) {
981 if (local->ieee_802_1x &&
982 hostap_is_eapol_frame(local, skb)) {
983 /* pass unencrypted EAPOL frames even if encryption is
984 * configured */
985 PDEBUG(DEBUG_EXTRA2, "%s: RX: IEEE 802.1X - passing "
986 "unencrypted EAPOL frame\n", local->dev->name);
987 } else {
988 printk(KERN_DEBUG "%s: encryption configured, but RX "
989 "frame not encrypted (SA=%pM)\n",
990 local->dev->name, hdr->addr2);
991 goto rx_dropped;
992 }
993 }
994
995 if (local->drop_unencrypted && !(fc & IEEE80211_FCTL_PROTECTED) &&
996 !hostap_is_eapol_frame(local, skb)) {
997 if (net_ratelimit()) {
998 printk(KERN_DEBUG "%s: dropped unencrypted RX data "
999 "frame from %pM (drop_unencrypted=1)\n",
1000 dev->name, hdr->addr2);
1001 }
1002 goto rx_dropped;
1003 }
1004
1005 /* skb: hdr + (possible reassembled) full plaintext payload */
1006
1007 payload = skb->data + hdrlen;
1008 ethertype = (payload[6] << 8) | payload[7];
1009
1010 /* If IEEE 802.1X is used, check whether the port is authorized to send
1011 * the received frame. */
1012 if (local->ieee_802_1x && local->iw_mode == IW_MODE_MASTER) {
1013 if (ethertype == ETH_P_PAE) {
1014 PDEBUG(DEBUG_EXTRA2, "%s: RX: IEEE 802.1X frame\n",
1015 dev->name);
1016 if (local->hostapd && local->apdev) {
1017 /* Send IEEE 802.1X frames to the user
1018 * space daemon for processing */
1019 prism2_rx_80211(local->apdev, skb, rx_stats,
1020 PRISM2_RX_MGMT);
1021 local->apdevstats.rx_packets++;
1022 local->apdevstats.rx_bytes += skb->len;
1023 goto rx_exit;
1024 }
1025 } else if (!frame_authorized) {
1026 printk(KERN_DEBUG "%s: dropped frame from "
1027 "unauthorized port (IEEE 802.1X): "
1028 "ethertype=0x%04x\n",
1029 dev->name, ethertype);
1030 goto rx_dropped;
1031 }
1032 }
1033
1034 /* convert hdr + possible LLC headers into Ethernet header */
1035 if (skb->len - hdrlen >= 8 &&
1036 ((memcmp(payload, rfc1042_header, 6) == 0 &&
1037 ethertype != ETH_P_AARP && ethertype != ETH_P_IPX) ||
1038 memcmp(payload, bridge_tunnel_header, 6) == 0)) {
1039 /* remove RFC1042 or Bridge-Tunnel encapsulation and
1040 * replace EtherType */
1041 skb_pull(skb, hdrlen + 6);
1042 memcpy(skb_push(skb, ETH_ALEN), src, ETH_ALEN);
1043 memcpy(skb_push(skb, ETH_ALEN), dst, ETH_ALEN);
1044 } else {
1045 __be16 len;
1046 /* Leave Ethernet header part of hdr and full payload */
1047 skb_pull(skb, hdrlen);
1048 len = htons(skb->len);
1049 memcpy(skb_push(skb, 2), &len, 2);
1050 memcpy(skb_push(skb, ETH_ALEN), src, ETH_ALEN);
1051 memcpy(skb_push(skb, ETH_ALEN), dst, ETH_ALEN);
1052 }
1053
1054 if (wds && ((fc & (IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS)) ==
1055 IEEE80211_FCTL_TODS) &&
1056 skb->len >= ETH_HLEN + ETH_ALEN) {
1057 /* Non-standard frame: get addr4 from its bogus location after
1058 * the payload */
1059 skb_copy_from_linear_data_offset(skb, skb->len - ETH_ALEN,
1060 skb->data + ETH_ALEN,
1061 ETH_ALEN);
1062 skb_trim(skb, skb->len - ETH_ALEN);
1063 }
1064
1065 dev->stats.rx_packets++;
1066 dev->stats.rx_bytes += skb->len;
1067
1068 if (local->iw_mode == IW_MODE_MASTER && !wds &&
1069 local->ap->bridge_packets) {
1070 if (dst[0] & 0x01) {
1071 /* copy multicast frame both to the higher layers and
1072 * to the wireless media */
1073 local->ap->bridged_multicast++;
1074 skb2 = skb_clone(skb, GFP_ATOMIC);
1075 if (skb2 == NULL)
1076 printk(KERN_DEBUG "%s: skb_clone failed for "
1077 "multicast frame\n", dev->name);
1078 } else if (hostap_is_sta_authorized(local->ap, dst)) {
1079 /* send frame directly to the associated STA using
1080 * wireless media and not passing to higher layers */
1081 local->ap->bridged_unicast++;
1082 skb2 = skb;
1083 skb = NULL;
1084 }
1085 }
1086
1087 if (skb2 != NULL) {
1088 /* send to wireless media */
1089 skb2->dev = dev;
1090 skb2->protocol = cpu_to_be16(ETH_P_802_3);
1091 skb_reset_mac_header(skb2);
1092 skb_reset_network_header(skb2);
1093 /* skb2->network_header += ETH_HLEN; */
1094 dev_queue_xmit(skb2);
1095 }
1096
1097 if (skb) {
1098 skb->protocol = eth_type_trans(skb, dev);
1099 memset(skb->cb, 0, sizeof(skb->cb));
1100 netif_rx(skb);
1101 }
1102
1103 rx_exit:
1104 if (sta)
1105 hostap_handle_sta_release(sta);
1106 return;
1107
1108 rx_dropped:
1109 dev_kfree_skb(skb);
1110
1111 dev->stats.rx_dropped++;
1112 goto rx_exit;
1113}
1114
1115
1116EXPORT_SYMBOL(hostap_80211_rx);
drivers/net/wireless/intersil/hostap/hostap_80211_tx.c+0−554
@@ -1,554 +0,0 @@
1// SPDX-License-Identifier: GPL-2.0
2#include <linux/slab.h>
3#include <linux/export.h>
4#include <linux/etherdevice.h>
5
6#include "hostap_80211.h"
7#include "hostap_common.h"
8#include "hostap_wlan.h"
9#include "hostap.h"
10#include "hostap_ap.h"
11
12/* See IEEE 802.1H for LLC/SNAP encapsulation/decapsulation */
13/* Ethernet-II snap header (RFC1042 for most EtherTypes) */
14static unsigned char rfc1042_header[] =
15{ 0xaa, 0xaa, 0x03, 0x00, 0x00, 0x00 };
16/* Bridge-Tunnel header (for EtherTypes ETH_P_AARP and ETH_P_IPX) */
17static unsigned char bridge_tunnel_header[] =
18{ 0xaa, 0xaa, 0x03, 0x00, 0x00, 0xf8 };
19/* No encapsulation header if EtherType < 0x600 (=length) */
20
21void hostap_dump_tx_80211(const char *name, struct sk_buff *skb)
22{
23 struct ieee80211_hdr *hdr;
24 u16 fc;
25
26 hdr = (struct ieee80211_hdr *) skb->data;
27
28 printk(KERN_DEBUG "%s: TX len=%d jiffies=%ld\n",
29 name, skb->len, jiffies);
30
31 if (skb->len < 2)
32 return;
33
34 fc = le16_to_cpu(hdr->frame_control);
35 printk(KERN_DEBUG " FC=0x%04x (type=%d:%d)%s%s",
36 fc, (fc & IEEE80211_FCTL_FTYPE) >> 2,
37 (fc & IEEE80211_FCTL_STYPE) >> 4,
38 fc & IEEE80211_FCTL_TODS ? " [ToDS]" : "",
39 fc & IEEE80211_FCTL_FROMDS ? " [FromDS]" : "");
40
41 if (skb->len < IEEE80211_DATA_HDR3_LEN) {
42 printk("\n");
43 return;
44 }
45
46 printk(" dur=0x%04x seq=0x%04x\n", le16_to_cpu(hdr->duration_id),
47 le16_to_cpu(hdr->seq_ctrl));
48
49 printk(KERN_DEBUG " A1=%pM", hdr->addr1);
50 printk(" A2=%pM", hdr->addr2);
51 printk(" A3=%pM", hdr->addr3);
52 if (skb->len >= 30)
53 printk(" A4=%pM", hdr->addr4);
54 printk("\n");
55}
56
57
58/* hard_start_xmit function for data interfaces (wlan#, wlan#wds#, wlan#sta)
59 * Convert Ethernet header into a suitable IEEE 802.11 header depending on
60 * device configuration. */
61netdev_tx_t hostap_data_start_xmit(struct sk_buff *skb,
62 struct net_device *dev)
63{
64 struct hostap_interface *iface;
65 local_info_t *local;
66 int need_headroom, need_tailroom = 0;
67 struct ieee80211_hdr hdr;
68 u16 fc, ethertype = 0;
69 enum {
70 WDS_NO = 0, WDS_OWN_FRAME, WDS_COMPLIANT_FRAME
71 } use_wds = WDS_NO;
72 u8 *encaps_data;
73 int hdr_len, encaps_len, skip_header_bytes;
74 int to_assoc_ap = 0;
75 struct hostap_skb_tx_data *meta;
76
77 iface = netdev_priv(dev);
78 local = iface->local;
79
80 if (skb->len < ETH_HLEN) {
81 printk(KERN_DEBUG "%s: hostap_data_start_xmit: short skb "
82 "(len=%d)\n", dev->name, skb->len);
83 kfree_skb(skb);
84 return NETDEV_TX_OK;
85 }
86
87 if (local->ddev != dev) {
88 use_wds = (local->iw_mode == IW_MODE_MASTER &&
89 !(local->wds_type & HOSTAP_WDS_STANDARD_FRAME)) ?
90 WDS_OWN_FRAME : WDS_COMPLIANT_FRAME;
91 if (dev == local->stadev) {
92 to_assoc_ap = 1;
93 use_wds = WDS_NO;
94 } else if (dev == local->apdev) {
95 printk(KERN_DEBUG "%s: prism2_tx: trying to use "
96 "AP device with Ethernet net dev\n", dev->name);
97 kfree_skb(skb);
98 return NETDEV_TX_OK;
99 }
100 } else {
101 if (local->iw_mode == IW_MODE_REPEAT) {
102 printk(KERN_DEBUG "%s: prism2_tx: trying to use "
103 "non-WDS link in Repeater mode\n", dev->name);
104 kfree_skb(skb);
105 return NETDEV_TX_OK;
106 } else if (local->iw_mode == IW_MODE_INFRA &&
107 (local->wds_type & HOSTAP_WDS_AP_CLIENT) &&
108 !ether_addr_equal(skb->data + ETH_ALEN, dev->dev_addr)) {
109 /* AP client mode: send frames with foreign src addr
110 * using 4-addr WDS frames */
111 use_wds = WDS_COMPLIANT_FRAME;
112 }
113 }
114
115 /* Incoming skb->data: dst_addr[6], src_addr[6], proto[2], payload
116 * ==>
117 * Prism2 TX frame with 802.11 header:
118 * txdesc (address order depending on used mode; includes dst_addr and
119 * src_addr), possible encapsulation (RFC1042/Bridge-Tunnel;
120 * proto[2], payload {, possible addr4[6]} */
121
122 ethertype = (skb->data[12] << 8) | skb->data[13];
123
124 memset(&hdr, 0, sizeof(hdr));
125
126 /* Length of data after IEEE 802.11 header */
127 encaps_data = NULL;
128 encaps_len = 0;
129 skip_header_bytes = ETH_HLEN;
130 if (ethertype == ETH_P_AARP || ethertype == ETH_P_IPX) {
131 encaps_data = bridge_tunnel_header;
132 encaps_len = sizeof(bridge_tunnel_header);
133 skip_header_bytes -= 2;
134 } else if (ethertype >= 0x600) {
135 encaps_data = rfc1042_header;
136 encaps_len = sizeof(rfc1042_header);
137 skip_header_bytes -= 2;
138 }
139
140 fc = IEEE80211_FTYPE_DATA | IEEE80211_STYPE_DATA;
141 hdr_len = IEEE80211_DATA_HDR3_LEN;
142
143 if (use_wds != WDS_NO) {
144 /* Note! Prism2 station firmware has problems with sending real
145 * 802.11 frames with four addresses; until these problems can
146 * be fixed or worked around, 4-addr frames needed for WDS are
147 * using incompatible format: FromDS flag is not set and the
148 * fourth address is added after the frame payload; it is
149 * assumed, that the receiving station knows how to handle this
150 * frame format */
151
152 if (use_wds == WDS_COMPLIANT_FRAME) {
153 fc |= IEEE80211_FCTL_FROMDS | IEEE80211_FCTL_TODS;
154 /* From&To DS: Addr1 = RA, Addr2 = TA, Addr3 = DA,
155 * Addr4 = SA */
156 skb_copy_from_linear_data_offset(skb, ETH_ALEN,
157 &hdr.addr4, ETH_ALEN);
158 hdr_len += ETH_ALEN;
159 } else {
160 /* bogus 4-addr format to workaround Prism2 station
161 * f/w bug */
162 fc |= IEEE80211_FCTL_TODS;
163 /* From DS: Addr1 = DA (used as RA),
164 * Addr2 = BSSID (used as TA), Addr3 = SA (used as DA),
165 */
166
167 /* SA from skb->data + ETH_ALEN will be added after
168 * frame payload; use hdr.addr4 as a temporary buffer
169 */
170 skb_copy_from_linear_data_offset(skb, ETH_ALEN,
171 &hdr.addr4, ETH_ALEN);
172 need_tailroom += ETH_ALEN;
173 }
174
175 /* send broadcast and multicast frames to broadcast RA, if
176 * configured; otherwise, use unicast RA of the WDS link */
177 if ((local->wds_type & HOSTAP_WDS_BROADCAST_RA) &&
178 is_multicast_ether_addr(skb->data))
179 eth_broadcast_addr(hdr.addr1);
180 else if (iface->type == HOSTAP_INTERFACE_WDS)
181 memcpy(&hdr.addr1, iface->u.wds.remote_addr,
182 ETH_ALEN);
183 else
184 memcpy(&hdr.addr1, local->bssid, ETH_ALEN);
185 memcpy(&hdr.addr2, dev->dev_addr, ETH_ALEN);
186 skb_copy_from_linear_data(skb, &hdr.addr3, ETH_ALEN);
187 } else if (local->iw_mode == IW_MODE_MASTER && !to_assoc_ap) {
188 fc |= IEEE80211_FCTL_FROMDS;
189 /* From DS: Addr1 = DA, Addr2 = BSSID, Addr3 = SA */
190 skb_copy_from_linear_data(skb, &hdr.addr1, ETH_ALEN);
191 memcpy(&hdr.addr2, dev->dev_addr, ETH_ALEN);
192 skb_copy_from_linear_data_offset(skb, ETH_ALEN, &hdr.addr3,
193 ETH_ALEN);
194 } else if (local->iw_mode == IW_MODE_INFRA || to_assoc_ap) {
195 fc |= IEEE80211_FCTL_TODS;
196 /* To DS: Addr1 = BSSID, Addr2 = SA, Addr3 = DA */
197 memcpy(&hdr.addr1, to_assoc_ap ?
198 local->assoc_ap_addr : local->bssid, ETH_ALEN);
199 skb_copy_from_linear_data_offset(skb, ETH_ALEN, &hdr.addr2,
200 ETH_ALEN);
201 skb_copy_from_linear_data(skb, &hdr.addr3, ETH_ALEN);
202 } else if (local->iw_mode == IW_MODE_ADHOC) {
203 /* not From/To DS: Addr1 = DA, Addr2 = SA, Addr3 = BSSID */
204 skb_copy_from_linear_data(skb, &hdr.addr1, ETH_ALEN);
205 skb_copy_from_linear_data_offset(skb, ETH_ALEN, &hdr.addr2,
206 ETH_ALEN);
207 memcpy(&hdr.addr3, local->bssid, ETH_ALEN);
208 }
209
210 hdr.frame_control = cpu_to_le16(fc);
211
212 skb_pull(skb, skip_header_bytes);
213 need_headroom = local->func->need_tx_headroom + hdr_len + encaps_len;
214 if (skb_tailroom(skb) < need_tailroom) {
215 skb = skb_unshare(skb, GFP_ATOMIC);
216 if (skb == NULL) {
217 iface->stats.tx_dropped++;
218 return NETDEV_TX_OK;
219 }
220 if (pskb_expand_head(skb, need_headroom, need_tailroom,
221 GFP_ATOMIC)) {
222 kfree_skb(skb);
223 iface->stats.tx_dropped++;
224 return NETDEV_TX_OK;
225 }
226 } else if (skb_headroom(skb) < need_headroom) {
227 struct sk_buff *tmp = skb;
228 skb = skb_realloc_headroom(skb, need_headroom);
229 kfree_skb(tmp);
230 if (skb == NULL) {
231 iface->stats.tx_dropped++;
232 return NETDEV_TX_OK;
233 }
234 } else {
235 skb = skb_unshare(skb, GFP_ATOMIC);
236 if (skb == NULL) {
237 iface->stats.tx_dropped++;
238 return NETDEV_TX_OK;
239 }
240 }
241
242 if (encaps_data)
243 memcpy(skb_push(skb, encaps_len), encaps_data, encaps_len);
244 memcpy(skb_push(skb, hdr_len), &hdr, hdr_len);
245 if (use_wds == WDS_OWN_FRAME) {
246 skb_put_data(skb, &hdr.addr4, ETH_ALEN);
247 }
248
249 iface->stats.tx_packets++;
250 iface->stats.tx_bytes += skb->len;
251
252 skb_reset_mac_header(skb);
253 meta = (struct hostap_skb_tx_data *) skb->cb;
254 memset(meta, 0, sizeof(*meta));
255 meta->magic = HOSTAP_SKB_TX_DATA_MAGIC;
256 if (use_wds)
257 meta->flags |= HOSTAP_TX_FLAGS_WDS;
258 meta->ethertype = ethertype;
259 meta->iface = iface;
260
261 /* Send IEEE 802.11 encapsulated frame using the master radio device */
262 skb->dev = local->dev;
263 dev_queue_xmit(skb);
264 return NETDEV_TX_OK;
265}
266
267
268/* hard_start_xmit function for hostapd wlan#ap interfaces */
269netdev_tx_t hostap_mgmt_start_xmit(struct sk_buff *skb,
270 struct net_device *dev)
271{
272 struct hostap_interface *iface;
273 local_info_t *local;
274 struct hostap_skb_tx_data *meta;
275 struct ieee80211_hdr *hdr;
276 u16 fc;
277
278 iface = netdev_priv(dev);
279 local = iface->local;
280
281 if (skb->len < 10) {
282 printk(KERN_DEBUG "%s: hostap_mgmt_start_xmit: short skb "
283 "(len=%d)\n", dev->name, skb->len);
284 kfree_skb(skb);
285 return NETDEV_TX_OK;
286 }
287
288 iface->stats.tx_packets++;
289 iface->stats.tx_bytes += skb->len;
290
291 meta = (struct hostap_skb_tx_data *) skb->cb;
292 memset(meta, 0, sizeof(*meta));
293 meta->magic = HOSTAP_SKB_TX_DATA_MAGIC;
294 meta->iface = iface;
295
296 if (skb->len >= IEEE80211_DATA_HDR3_LEN + sizeof(rfc1042_header) + 2) {
297 hdr = (struct ieee80211_hdr *) skb->data;
298 fc = le16_to_cpu(hdr->frame_control);
299 if (ieee80211_is_data(hdr->frame_control) &&
300 (fc & IEEE80211_FCTL_STYPE) == IEEE80211_STYPE_DATA) {
301 u8 *pos = &skb->data[IEEE80211_DATA_HDR3_LEN +
302 sizeof(rfc1042_header)];
303 meta->ethertype = (pos[0] << 8) | pos[1];
304 }
305 }
306
307 /* Send IEEE 802.11 encapsulated frame using the master radio device */
308 skb->dev = local->dev;
309 dev_queue_xmit(skb);
310 return NETDEV_TX_OK;
311}
312
313
314/* Called only from software IRQ */
315static struct sk_buff * hostap_tx_encrypt(struct sk_buff *skb,
316 struct lib80211_crypt_data *crypt)
317{
318 struct hostap_interface *iface;
319 local_info_t *local;
320 struct ieee80211_hdr *hdr;
321 int prefix_len, postfix_len, hdr_len, res;
322
323 iface = netdev_priv(skb->dev);
324 local = iface->local;
325
326 if (skb->len < IEEE80211_DATA_HDR3_LEN) {
327 kfree_skb(skb);
328 return NULL;
329 }
330
331 if (local->tkip_countermeasures &&
332 strcmp(crypt->ops->name, "TKIP") == 0) {
333 hdr = (struct ieee80211_hdr *) skb->data;
334 if (net_ratelimit()) {
335 printk(KERN_DEBUG "%s: TKIP countermeasures: dropped "
336 "TX packet to %pM\n",
337 local->dev->name, hdr->addr1);
338 }
339 kfree_skb(skb);
340 return NULL;
341 }
342
343 skb = skb_unshare(skb, GFP_ATOMIC);
344 if (skb == NULL)
345 return NULL;
346
347 prefix_len = crypt->ops->extra_mpdu_prefix_len +
348 crypt->ops->extra_msdu_prefix_len;
349 postfix_len = crypt->ops->extra_mpdu_postfix_len +
350 crypt->ops->extra_msdu_postfix_len;
351 if ((skb_headroom(skb) < prefix_len ||
352 skb_tailroom(skb) < postfix_len) &&
353 pskb_expand_head(skb, prefix_len, postfix_len, GFP_ATOMIC)) {
354 kfree_skb(skb);
355 return NULL;
356 }
357
358 hdr = (struct ieee80211_hdr *) skb->data;
359 hdr_len = hostap_80211_get_hdrlen(hdr->frame_control);
360
361 /* Host-based IEEE 802.11 fragmentation for TX is not yet supported, so
362 * call both MSDU and MPDU encryption functions from here. */
363 atomic_inc(&crypt->refcnt);
364 res = 0;
365 if (crypt->ops->encrypt_msdu)
366 res = crypt->ops->encrypt_msdu(skb, hdr_len, crypt->priv);
367 if (res == 0 && crypt->ops->encrypt_mpdu)
368 res = crypt->ops->encrypt_mpdu(skb, hdr_len, crypt->priv);
369 atomic_dec(&crypt->refcnt);
370 if (res < 0) {
371 kfree_skb(skb);
372 return NULL;
373 }
374
375 return skb;
376}
377
378
379/* hard_start_xmit function for master radio interface wifi#.
380 * AP processing (TX rate control, power save buffering, etc.).
381 * Use hardware TX function to send the frame. */
382netdev_tx_t hostap_master_start_xmit(struct sk_buff *skb,
383 struct net_device *dev)
384{
385 struct hostap_interface *iface;
386 local_info_t *local;
387 netdev_tx_t ret = NETDEV_TX_BUSY;
388 u16 fc;
389 struct hostap_tx_data tx;
390 ap_tx_ret tx_ret;
391 struct hostap_skb_tx_data *meta;
392 int no_encrypt = 0;
393 struct ieee80211_hdr *hdr;
394
395 iface = netdev_priv(dev);
396 local = iface->local;
397
398 tx.skb = skb;
399 tx.sta_ptr = NULL;
400
401 meta = (struct hostap_skb_tx_data *) skb->cb;
402 if (meta->magic != HOSTAP_SKB_TX_DATA_MAGIC) {
403 printk(KERN_DEBUG "%s: invalid skb->cb magic (0x%08x, "
404 "expected 0x%08x)\n",
405 dev->name, meta->magic, HOSTAP_SKB_TX_DATA_MAGIC);
406 ret = NETDEV_TX_OK;
407 iface->stats.tx_dropped++;
408 goto fail;
409 }
410
411 if (local->host_encrypt) {
412 /* Set crypt to default algorithm and key; will be replaced in
413 * AP code if STA has own alg/key */
414 tx.crypt = local->crypt_info.crypt[local->crypt_info.tx_keyidx];
415 tx.host_encrypt = 1;
416 } else {
417 tx.crypt = NULL;
418 tx.host_encrypt = 0;
419 }
420
421 if (skb->len < 24) {
422 printk(KERN_DEBUG "%s: hostap_master_start_xmit: short skb "
423 "(len=%d)\n", dev->name, skb->len);
424 ret = NETDEV_TX_OK;
425 iface->stats.tx_dropped++;
426 goto fail;
427 }
428
429 /* FIX (?):
430 * Wi-Fi 802.11b test plan suggests that AP should ignore power save
431 * bit in authentication and (re)association frames and assume tha
432 * STA remains awake for the response. */
433 tx_ret = hostap_handle_sta_tx(local, &tx);
434 skb = tx.skb;
435 meta = (struct hostap_skb_tx_data *) skb->cb;
436 hdr = (struct ieee80211_hdr *) skb->data;
437 fc = le16_to_cpu(hdr->frame_control);
438 switch (tx_ret) {
439 case AP_TX_CONTINUE:
440 break;
441 case AP_TX_CONTINUE_NOT_AUTHORIZED:
442 if (local->ieee_802_1x &&
443 ieee80211_is_data(hdr->frame_control) &&
444 meta->ethertype != ETH_P_PAE &&
445 !(meta->flags & HOSTAP_TX_FLAGS_WDS)) {
446 printk(KERN_DEBUG "%s: dropped frame to unauthorized "
447 "port (IEEE 802.1X): ethertype=0x%04x\n",
448 dev->name, meta->ethertype);
449 hostap_dump_tx_80211(dev->name, skb);
450
451 ret = NETDEV_TX_OK; /* drop packet */
452 iface->stats.tx_dropped++;
453 goto fail;
454 }
455 break;
456 case AP_TX_DROP:
457 ret = NETDEV_TX_OK; /* drop packet */
458 iface->stats.tx_dropped++;
459 goto fail;
460 case AP_TX_RETRY:
461 goto fail;
462 case AP_TX_BUFFERED:
463 /* do not free skb here, it will be freed when the
464 * buffered frame is sent/timed out */
465 ret = NETDEV_TX_OK;
466 goto tx_exit;
467 }
468
469 /* Request TX callback if protocol version is 2 in 802.11 header;
470 * this version 2 is a special case used between hostapd and kernel
471 * driver */
472 if (((fc & IEEE80211_FCTL_VERS) == BIT(1)) &&
473 local->ap && local->ap->tx_callback_idx && meta->tx_cb_idx == 0) {
474 meta->tx_cb_idx = local->ap->tx_callback_idx;
475
476 /* remove special version from the frame header */
477 fc &= ~IEEE80211_FCTL_VERS;
478 hdr->frame_control = cpu_to_le16(fc);
479 }
480
481 if (!ieee80211_is_data(hdr->frame_control)) {
482 no_encrypt = 1;
483 tx.crypt = NULL;
484 }
485
486 if (local->ieee_802_1x && meta->ethertype == ETH_P_PAE && tx.crypt &&
487 !(fc & IEEE80211_FCTL_PROTECTED)) {
488 no_encrypt = 1;
489 PDEBUG(DEBUG_EXTRA2, "%s: TX: IEEE 802.1X - passing "
490 "unencrypted EAPOL frame\n", dev->name);
491 tx.crypt = NULL; /* no encryption for IEEE 802.1X frames */
492 }
493
494 if (tx.crypt && (!tx.crypt->ops || !tx.crypt->ops->encrypt_mpdu))
495 tx.crypt = NULL;
496 else if ((tx.crypt ||
497 local->crypt_info.crypt[local->crypt_info.tx_keyidx]) &&
498 !no_encrypt) {
499 /* Add ISWEP flag both for firmware and host based encryption
500 */
501 fc |= IEEE80211_FCTL_PROTECTED;
502 hdr->frame_control = cpu_to_le16(fc);
503 } else if (local->drop_unencrypted &&
504 ieee80211_is_data(hdr->frame_control) &&
505 meta->ethertype != ETH_P_PAE) {
506 if (net_ratelimit()) {
507 printk(KERN_DEBUG "%s: dropped unencrypted TX data "
508 "frame (drop_unencrypted=1)\n", dev->name);
509 }
510 iface->stats.tx_dropped++;
511 ret = NETDEV_TX_OK;
512 goto fail;
513 }
514
515 if (tx.crypt) {
516 skb = hostap_tx_encrypt(skb, tx.crypt);
517 if (skb == NULL) {
518 printk(KERN_DEBUG "%s: TX - encryption failed\n",
519 dev->name);
520 ret = NETDEV_TX_OK;
521 goto fail;
522 }
523 meta = (struct hostap_skb_tx_data *) skb->cb;
524 if (meta->magic != HOSTAP_SKB_TX_DATA_MAGIC) {
525 printk(KERN_DEBUG "%s: invalid skb->cb magic (0x%08x, "
526 "expected 0x%08x) after hostap_tx_encrypt\n",
527 dev->name, meta->magic,
528 HOSTAP_SKB_TX_DATA_MAGIC);
529 ret = NETDEV_TX_OK;
530 iface->stats.tx_dropped++;
531 goto fail;
532 }
533 }
534
535 if (local->func->tx == NULL || local->func->tx(skb, dev)) {
536 ret = NETDEV_TX_OK;
537 iface->stats.tx_dropped++;
538 } else {
539 ret = NETDEV_TX_OK;
540 iface->stats.tx_packets++;
541 iface->stats.tx_bytes += skb->len;
542 }
543
544 fail:
545 if (ret == NETDEV_TX_OK && skb)
546 dev_kfree_skb(skb);
547 tx_exit:
548 if (tx.sta_ptr)
549 hostap_handle_sta_release(tx.sta_ptr);
550 return ret;
551}
552
553
554EXPORT_SYMBOL(hostap_master_start_xmit);
drivers/net/wireless/intersil/hostap/hostap_ap.c+0−3277
@@ -1,3277 +0,0 @@
1// SPDX-License-Identifier: GPL-2.0
2/*
3 * Intersil Prism2 driver with Host AP (software access point) support
4 * Copyright (c) 2001-2002, SSH Communications Security Corp and Jouni Malinen
5 * <j@w1.fi>
6 * Copyright (c) 2002-2005, Jouni Malinen <j@w1.fi>
7 *
8 * This file is to be included into hostap.c when S/W AP functionality is
9 * compiled.
10 *
11 * AP: FIX:
12 * - if unicast Class 2 (assoc,reassoc,disassoc) frame received from
13 * unauthenticated STA, send deauth. frame (8802.11: 5.5)
14 * - if unicast Class 3 (data with to/from DS,deauth,pspoll) frame received
15 * from authenticated, but unassoc STA, send disassoc frame (8802.11: 5.5)
16 * - if unicast Class 3 received from unauthenticated STA, send deauth. frame
17 * (8802.11: 5.5)
18 */
19
20#include <linux/proc_fs.h>
21#include <linux/seq_file.h>
22#include <linux/delay.h>
23#include <linux/random.h>
24#include <linux/if_arp.h>
25#include <linux/slab.h>
26#include <linux/export.h>
27#include <linux/moduleparam.h>
28#include <linux/etherdevice.h>
29
30#include "hostap_wlan.h"
31#include "hostap.h"
32#include "hostap_ap.h"
33
34static int other_ap_policy[MAX_PARM_DEVICES] = { AP_OTHER_AP_SKIP_ALL,
35 DEF_INTS };
36module_param_array(other_ap_policy, int, NULL, 0444);
37MODULE_PARM_DESC(other_ap_policy, "Other AP beacon monitoring policy (0-3)");
38
39static int ap_max_inactivity[MAX_PARM_DEVICES] = { AP_MAX_INACTIVITY_SEC,
40 DEF_INTS };
41module_param_array(ap_max_inactivity, int, NULL, 0444);
42MODULE_PARM_DESC(ap_max_inactivity, "AP timeout (in seconds) for station "
43 "inactivity");
44
45static int ap_bridge_packets[MAX_PARM_DEVICES] = { 1, DEF_INTS };
46module_param_array(ap_bridge_packets, int, NULL, 0444);
47MODULE_PARM_DESC(ap_bridge_packets, "Bridge packets directly between "
48 "stations");
49
50static int autom_ap_wds[MAX_PARM_DEVICES] = { 0, DEF_INTS };
51module_param_array(autom_ap_wds, int, NULL, 0444);
52MODULE_PARM_DESC(autom_ap_wds, "Add WDS connections to other APs "
53 "automatically");
54
55
56static struct sta_info* ap_get_sta(struct ap_data *ap, u8 *sta);
57static void hostap_event_expired_sta(struct net_device *dev,
58 struct sta_info *sta);
59static void handle_add_proc_queue(struct work_struct *work);
60
61#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
62static void handle_wds_oper_queue(struct work_struct *work);
63static void prism2_send_mgmt(struct net_device *dev,
64 u16 type_subtype, char *body,
65 int body_len, u8 *addr, u16 tx_cb_idx);
66#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
67
68
69#if !defined(PRISM2_NO_PROCFS_DEBUG) && defined(CONFIG_PROC_FS)
70static int ap_debug_proc_show(struct seq_file *m, void *v)
71{
72 struct ap_data *ap = pde_data(file_inode(m->file));
73
74 seq_printf(m, "BridgedUnicastFrames=%u\n", ap->bridged_unicast);
75 seq_printf(m, "BridgedMulticastFrames=%u\n", ap->bridged_multicast);
76 seq_printf(m, "max_inactivity=%u\n", ap->max_inactivity / HZ);
77 seq_printf(m, "bridge_packets=%u\n", ap->bridge_packets);
78 seq_printf(m, "nullfunc_ack=%u\n", ap->nullfunc_ack);
79 seq_printf(m, "autom_ap_wds=%u\n", ap->autom_ap_wds);
80 seq_printf(m, "auth_algs=%u\n", ap->local->auth_algs);
81 seq_printf(m, "tx_drop_nonassoc=%u\n", ap->tx_drop_nonassoc);
82 return 0;
83}
84#endif
85
86static void ap_sta_hash_add(struct ap_data *ap, struct sta_info *sta)
87{
88 sta->hnext = ap->sta_hash[STA_HASH(sta->addr)];
89 ap->sta_hash[STA_HASH(sta->addr)] = sta;
90}
91
92static void ap_sta_hash_del(struct ap_data *ap, struct sta_info *sta)
93{
94 struct sta_info *s;
95
96 s = ap->sta_hash[STA_HASH(sta->addr)];
97 if (s == NULL) return;
98 if (ether_addr_equal(s->addr, sta->addr)) {
99 ap->sta_hash[STA_HASH(sta->addr)] = s->hnext;
100 return;
101 }
102
103 while (s->hnext != NULL && !ether_addr_equal(s->hnext->addr, sta->addr))
104 s = s->hnext;
105 if (s->hnext != NULL)
106 s->hnext = s->hnext->hnext;
107 else
108 printk("AP: could not remove STA %pM from hash table\n",
109 sta->addr);
110}
111
112static void ap_free_sta(struct ap_data *ap, struct sta_info *sta)
113{
114 if (sta->ap && sta->local)
115 hostap_event_expired_sta(sta->local->dev, sta);
116
117 if (ap->proc != NULL) {
118 char name[20];
119 sprintf(name, "%pM", sta->addr);
120 remove_proc_entry(name, ap->proc);
121 }
122
123 if (sta->crypt) {
124 sta->crypt->ops->deinit(sta->crypt->priv);
125 kfree(sta->crypt);
126 sta->crypt = NULL;
127 }
128
129 skb_queue_purge(&sta->tx_buf);
130
131 ap->num_sta--;
132#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
133 if (sta->aid > 0)
134 ap->sta_aid[sta->aid - 1] = NULL;
135
136 if (!sta->ap)
137 kfree(sta->u.sta.challenge);
138 timer_shutdown_sync(&sta->timer);
139#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
140
141 kfree(sta);
142}
143
144
145static void hostap_set_tim(local_info_t *local, int aid, int set)
146{
147 if (local->func->set_tim)
148 local->func->set_tim(local->dev, aid, set);
149}
150
151
152static void hostap_event_new_sta(struct net_device *dev, struct sta_info *sta)
153{
154 union iwreq_data wrqu;
155 memset(&wrqu, 0, sizeof(wrqu));
156 memcpy(wrqu.addr.sa_data, sta->addr, ETH_ALEN);
157 wrqu.addr.sa_family = ARPHRD_ETHER;
158 wireless_send_event(dev, IWEVREGISTERED, &wrqu, NULL);
159}
160
161
162static void hostap_event_expired_sta(struct net_device *dev,
163 struct sta_info *sta)
164{
165 union iwreq_data wrqu;
166 memset(&wrqu, 0, sizeof(wrqu));
167 memcpy(wrqu.addr.sa_data, sta->addr, ETH_ALEN);
168 wrqu.addr.sa_family = ARPHRD_ETHER;
169 wireless_send_event(dev, IWEVEXPIRED, &wrqu, NULL);
170}
171
172
173#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
174
175static void ap_handle_timer(struct timer_list *t)
176{
177 struct sta_info *sta = from_timer(sta, t, timer);
178 local_info_t *local;
179 struct ap_data *ap;
180 unsigned long next_time = 0;
181 int was_assoc;
182
183 if (sta == NULL || sta->local == NULL || sta->local->ap == NULL) {
184 PDEBUG(DEBUG_AP, "ap_handle_timer() called with NULL data\n");
185 return;
186 }
187
188 local = sta->local;
189 ap = local->ap;
190 was_assoc = sta->flags & WLAN_STA_ASSOC;
191
192 if (atomic_read(&sta->users) != 0)
193 next_time = jiffies + HZ;
194 else if ((sta->flags & WLAN_STA_PERM) && !(sta->flags & WLAN_STA_AUTH))
195 next_time = jiffies + ap->max_inactivity;
196
197 if (time_before(jiffies, sta->last_rx + ap->max_inactivity)) {
198 /* station activity detected; reset timeout state */
199 sta->timeout_next = STA_NULLFUNC;
200 next_time = sta->last_rx + ap->max_inactivity;
201 } else if (sta->timeout_next == STA_DISASSOC &&
202 !(sta->flags & WLAN_STA_PENDING_POLL)) {
203 /* STA ACKed data nullfunc frame poll */
204 sta->timeout_next = STA_NULLFUNC;
205 next_time = jiffies + ap->max_inactivity;
206 }
207
208 if (next_time) {
209 sta->timer.expires = next_time;
210 add_timer(&sta->timer);
211 return;
212 }
213
214 if (sta->ap)
215 sta->timeout_next = STA_DEAUTH;
216
217 if (sta->timeout_next == STA_DEAUTH && !(sta->flags & WLAN_STA_PERM)) {
218 spin_lock(&ap->sta_table_lock);
219 ap_sta_hash_del(ap, sta);
220 list_del(&sta->list);
221 spin_unlock(&ap->sta_table_lock);
222 sta->flags &= ~(WLAN_STA_AUTH | WLAN_STA_ASSOC);
223 } else if (sta->timeout_next == STA_DISASSOC)
224 sta->flags &= ~WLAN_STA_ASSOC;
225
226 if (was_assoc && !(sta->flags & WLAN_STA_ASSOC) && !sta->ap)
227 hostap_event_expired_sta(local->dev, sta);
228
229 if (sta->timeout_next == STA_DEAUTH && sta->aid > 0 &&
230 !skb_queue_empty(&sta->tx_buf)) {
231 hostap_set_tim(local, sta->aid, 0);
232 sta->flags &= ~WLAN_STA_TIM;
233 }
234
235 if (sta->ap) {
236 if (ap->autom_ap_wds) {
237 PDEBUG(DEBUG_AP, "%s: removing automatic WDS "
238 "connection to AP %pM\n",
239 local->dev->name, sta->addr);
240 hostap_wds_link_oper(local, sta->addr, WDS_DEL);
241 }
242 } else if (sta->timeout_next == STA_NULLFUNC) {
243 /* send data frame to poll STA and check whether this frame
244 * is ACKed */
245 /* FIX: IEEE80211_STYPE_NULLFUNC would be more appropriate, but
246 * it is apparently not retried so TX Exc events are not
247 * received for it */
248 sta->flags |= WLAN_STA_PENDING_POLL;
249 prism2_send_mgmt(local->dev, IEEE80211_FTYPE_DATA |
250 IEEE80211_STYPE_DATA, NULL, 0,
251 sta->addr, ap->tx_callback_poll);
252 } else {
253 int deauth = sta->timeout_next == STA_DEAUTH;
254 __le16 resp;
255 PDEBUG(DEBUG_AP, "%s: sending %s info to STA %pM"
256 "(last=%lu, jiffies=%lu)\n",
257 local->dev->name,
258 deauth ? "deauthentication" : "disassociation",
259 sta->addr, sta->last_rx, jiffies);
260
261 resp = cpu_to_le16(deauth ? WLAN_REASON_PREV_AUTH_NOT_VALID :
262 WLAN_REASON_DISASSOC_DUE_TO_INACTIVITY);
263 prism2_send_mgmt(local->dev, IEEE80211_FTYPE_MGMT |
264 (deauth ? IEEE80211_STYPE_DEAUTH :
265 IEEE80211_STYPE_DISASSOC),
266 (char *) &resp, 2, sta->addr, 0);
267 }
268
269 if (sta->timeout_next == STA_DEAUTH) {
270 if (sta->flags & WLAN_STA_PERM) {
271 PDEBUG(DEBUG_AP, "%s: STA %pM"
272 " would have been removed, "
273 "but it has 'perm' flag\n",
274 local->dev->name, sta->addr);
275 } else
276 ap_free_sta(ap, sta);
277 return;
278 }
279
280 if (sta->timeout_next == STA_NULLFUNC) {
281 sta->timeout_next = STA_DISASSOC;
282 sta->timer.expires = jiffies + AP_DISASSOC_DELAY;
283 } else {
284 sta->timeout_next = STA_DEAUTH;
285 sta->timer.expires = jiffies + AP_DEAUTH_DELAY;
286 }
287
288 add_timer(&sta->timer);
289}
290
291
292void hostap_deauth_all_stas(struct net_device *dev, struct ap_data *ap,
293 int resend)
294{
295 u8 addr[ETH_ALEN];
296 __le16 resp;
297 int i;
298
299 PDEBUG(DEBUG_AP, "%s: Deauthenticate all stations\n", dev->name);
300 eth_broadcast_addr(addr);
301
302 resp = cpu_to_le16(WLAN_REASON_PREV_AUTH_NOT_VALID);
303
304 /* deauth message sent; try to resend it few times; the message is
305 * broadcast, so it may be delayed until next DTIM; there is not much
306 * else we can do at this point since the driver is going to be shut
307 * down */
308 for (i = 0; i < 5; i++) {
309 prism2_send_mgmt(dev, IEEE80211_FTYPE_MGMT |
310 IEEE80211_STYPE_DEAUTH,
311 (char *) &resp, 2, addr, 0);
312
313 if (!resend || ap->num_sta <= 0)
314 return;
315
316 mdelay(50);
317 }
318}
319
320
321static int ap_control_proc_show(struct seq_file *m, void *v)
322{
323 struct ap_data *ap = pde_data(file_inode(m->file));
324 char *policy_txt;
325 struct mac_entry *entry;
326
327 if (v == SEQ_START_TOKEN) {
328 switch (ap->mac_restrictions.policy) {
329 case MAC_POLICY_OPEN:
330 policy_txt = "open";
331 break;
332 case MAC_POLICY_ALLOW:
333 policy_txt = "allow";
334 break;
335 case MAC_POLICY_DENY:
336 policy_txt = "deny";
337 break;
338 default:
339 policy_txt = "unknown";
340 break;
341 }
342 seq_printf(m, "MAC policy: %s\n", policy_txt);
343 seq_printf(m, "MAC entries: %u\n", ap->mac_restrictions.entries);
344 seq_puts(m, "MAC list:\n");
345 return 0;
346 }
347
348 entry = v;
349 seq_printf(m, "%pM\n", entry->addr);
350 return 0;
351}
352
353static void *ap_control_proc_start(struct seq_file *m, loff_t *_pos)
354{
355 struct ap_data *ap = pde_data(file_inode(m->file));
356 spin_lock_bh(&ap->mac_restrictions.lock);
357 return seq_list_start_head(&ap->mac_restrictions.mac_list, *_pos);
358}
359
360static void *ap_control_proc_next(struct seq_file *m, void *v, loff_t *_pos)
361{
362 struct ap_data *ap = pde_data(file_inode(m->file));
363 return seq_list_next(v, &ap->mac_restrictions.mac_list, _pos);
364}
365
366static void ap_control_proc_stop(struct seq_file *m, void *v)
367{
368 struct ap_data *ap = pde_data(file_inode(m->file));
369 spin_unlock_bh(&ap->mac_restrictions.lock);
370}
371
372static const struct seq_operations ap_control_proc_seqops = {
373 .start = ap_control_proc_start,
374 .next = ap_control_proc_next,
375 .stop = ap_control_proc_stop,
376 .show = ap_control_proc_show,
377};
378
379int ap_control_add_mac(struct mac_restrictions *mac_restrictions, u8 *mac)
380{
381 struct mac_entry *entry;
382
383 entry = kmalloc(sizeof(struct mac_entry), GFP_KERNEL);
384 if (entry == NULL)
385 return -ENOMEM;
386
387 memcpy(entry->addr, mac, ETH_ALEN);
388
389 spin_lock_bh(&mac_restrictions->lock);
390 list_add_tail(&entry->list, &mac_restrictions->mac_list);
391 mac_restrictions->entries++;
392 spin_unlock_bh(&mac_restrictions->lock);
393
394 return 0;
395}
396
397
398int ap_control_del_mac(struct mac_restrictions *mac_restrictions, u8 *mac)
399{
400 struct list_head *ptr;
401 struct mac_entry *entry;
402
403 spin_lock_bh(&mac_restrictions->lock);
404 for (ptr = mac_restrictions->mac_list.next;
405 ptr != &mac_restrictions->mac_list; ptr = ptr->next) {
406 entry = list_entry(ptr, struct mac_entry, list);
407
408 if (ether_addr_equal(entry->addr, mac)) {
409 list_del(ptr);
410 kfree(entry);
411 mac_restrictions->entries--;
412 spin_unlock_bh(&mac_restrictions->lock);
413 return 0;
414 }
415 }
416 spin_unlock_bh(&mac_restrictions->lock);
417 return -1;
418}
419
420
421static int ap_control_mac_deny(struct mac_restrictions *mac_restrictions,
422 u8 *mac)
423{
424 struct mac_entry *entry;
425 int found = 0;
426
427 if (mac_restrictions->policy == MAC_POLICY_OPEN)
428 return 0;
429
430 spin_lock_bh(&mac_restrictions->lock);
431 list_for_each_entry(entry, &mac_restrictions->mac_list, list) {
432 if (ether_addr_equal(entry->addr, mac)) {
433 found = 1;
434 break;
435 }
436 }
437 spin_unlock_bh(&mac_restrictions->lock);
438
439 if (mac_restrictions->policy == MAC_POLICY_ALLOW)
440 return !found;
441 else
442 return found;
443}
444
445
446void ap_control_flush_macs(struct mac_restrictions *mac_restrictions)
447{
448 struct list_head *ptr, *n;
449 struct mac_entry *entry;
450
451 if (mac_restrictions->entries == 0)
452 return;
453
454 spin_lock_bh(&mac_restrictions->lock);
455 for (ptr = mac_restrictions->mac_list.next, n = ptr->next;
456 ptr != &mac_restrictions->mac_list;
457 ptr = n, n = ptr->next) {
458 entry = list_entry(ptr, struct mac_entry, list);
459 list_del(ptr);
460 kfree(entry);
461 }
462 mac_restrictions->entries = 0;
463 spin_unlock_bh(&mac_restrictions->lock);
464}
465
466
467int ap_control_kick_mac(struct ap_data *ap, struct net_device *dev, u8 *mac)
468{
469 struct sta_info *sta;
470 __le16 resp;
471
472 spin_lock_bh(&ap->sta_table_lock);
473 sta = ap_get_sta(ap, mac);
474 if (sta) {
475 ap_sta_hash_del(ap, sta);
476 list_del(&sta->list);
477 }
478 spin_unlock_bh(&ap->sta_table_lock);
479
480 if (!sta)
481 return -EINVAL;
482
483 resp = cpu_to_le16(WLAN_REASON_PREV_AUTH_NOT_VALID);
484 prism2_send_mgmt(dev, IEEE80211_FTYPE_MGMT | IEEE80211_STYPE_DEAUTH,
485 (char *) &resp, 2, sta->addr, 0);
486
487 if ((sta->flags & WLAN_STA_ASSOC) && !sta->ap)
488 hostap_event_expired_sta(dev, sta);
489
490 ap_free_sta(ap, sta);
491
492 return 0;
493}
494
495#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
496
497
498void ap_control_kickall(struct ap_data *ap)
499{
500 struct list_head *ptr, *n;
501 struct sta_info *sta;
502
503 spin_lock_bh(&ap->sta_table_lock);
504 for (ptr = ap->sta_list.next, n = ptr->next; ptr != &ap->sta_list;
505 ptr = n, n = ptr->next) {
506 sta = list_entry(ptr, struct sta_info, list);
507 ap_sta_hash_del(ap, sta);
508 list_del(&sta->list);
509 if ((sta->flags & WLAN_STA_ASSOC) && !sta->ap && sta->local)
510 hostap_event_expired_sta(sta->local->dev, sta);
511 ap_free_sta(ap, sta);
512 }
513 spin_unlock_bh(&ap->sta_table_lock);
514}
515
516
517#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
518
519static int prism2_ap_proc_show(struct seq_file *m, void *v)
520{
521 struct sta_info *sta = v;
522 int i;
523
524 if (v == SEQ_START_TOKEN) {
525 seq_printf(m, "# BSSID CHAN SIGNAL NOISE RATE SSID FLAGS\n");
526 return 0;
527 }
528
529 if (!sta->ap)
530 return 0;
531
532 seq_printf(m, "%pM %d %d %d %d '",
533 sta->addr,
534 sta->u.ap.channel, sta->last_rx_signal,
535 sta->last_rx_silence, sta->last_rx_rate);
536
537 for (i = 0; i < sta->u.ap.ssid_len; i++) {
538 if (sta->u.ap.ssid[i] >= 32 && sta->u.ap.ssid[i] < 127)
539 seq_putc(m, sta->u.ap.ssid[i]);
540 else
541 seq_printf(m, "<%02x>", sta->u.ap.ssid[i]);
542 }
543
544 seq_putc(m, '\'');
545 if (sta->capability & WLAN_CAPABILITY_ESS)
546 seq_puts(m, " [ESS]");
547 if (sta->capability & WLAN_CAPABILITY_IBSS)
548 seq_puts(m, " [IBSS]");
549 if (sta->capability & WLAN_CAPABILITY_PRIVACY)
550 seq_puts(m, " [WEP]");
551 seq_putc(m, '\n');
552 return 0;
553}
554
555static void *prism2_ap_proc_start(struct seq_file *m, loff_t *_pos)
556{
557 struct ap_data *ap = pde_data(file_inode(m->file));
558 spin_lock_bh(&ap->sta_table_lock);
559 return seq_list_start_head(&ap->sta_list, *_pos);
560}
561
562static void *prism2_ap_proc_next(struct seq_file *m, void *v, loff_t *_pos)
563{
564 struct ap_data *ap = pde_data(file_inode(m->file));
565 return seq_list_next(v, &ap->sta_list, _pos);
566}
567
568static void prism2_ap_proc_stop(struct seq_file *m, void *v)
569{
570 struct ap_data *ap = pde_data(file_inode(m->file));
571 spin_unlock_bh(&ap->sta_table_lock);
572}
573
574static const struct seq_operations prism2_ap_proc_seqops = {
575 .start = prism2_ap_proc_start,
576 .next = prism2_ap_proc_next,
577 .stop = prism2_ap_proc_stop,
578 .show = prism2_ap_proc_show,
579};
580#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
581
582
583void hostap_check_sta_fw_version(struct ap_data *ap, int sta_fw_ver)
584{
585 if (!ap)
586 return;
587
588 if (sta_fw_ver == PRISM2_FW_VER(0,8,0)) {
589 PDEBUG(DEBUG_AP, "Using data::nullfunc ACK workaround - "
590 "firmware upgrade recommended\n");
591 ap->nullfunc_ack = 1;
592 } else
593 ap->nullfunc_ack = 0;
594
595 if (sta_fw_ver == PRISM2_FW_VER(1,4,2)) {
596 printk(KERN_WARNING "%s: Warning: secondary station firmware "
597 "version 1.4.2 does not seem to work in Host AP mode\n",
598 ap->local->dev->name);
599 }
600}
601
602
603/* Called only as a tasklet (software IRQ) */
604static void hostap_ap_tx_cb(struct sk_buff *skb, int ok, void *data)
605{
606 struct ap_data *ap = data;
607 struct ieee80211_hdr *hdr;
608
609 if (!ap->local->hostapd || !ap->local->apdev) {
610 dev_kfree_skb(skb);
611 return;
612 }
613
614 /* Pass the TX callback frame to the hostapd; use 802.11 header version
615 * 1 to indicate failure (no ACK) and 2 success (frame ACKed) */
616
617 hdr = (struct ieee80211_hdr *) skb->data;
618 hdr->frame_control &= cpu_to_le16(~IEEE80211_FCTL_VERS);
619 hdr->frame_control |= cpu_to_le16(ok ? BIT(1) : BIT(0));
620
621 skb->dev = ap->local->apdev;
622 skb_pull(skb, hostap_80211_get_hdrlen(hdr->frame_control));
623 skb->pkt_type = PACKET_OTHERHOST;
624 skb->protocol = cpu_to_be16(ETH_P_802_2);
625 memset(skb->cb, 0, sizeof(skb->cb));
626 netif_rx(skb);
627}
628
629
630#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
631/* Called only as a tasklet (software IRQ) */
632static void hostap_ap_tx_cb_auth(struct sk_buff *skb, int ok, void *data)
633{
634 struct ap_data *ap = data;
635 struct net_device *dev = ap->local->dev;
636 struct ieee80211_hdr *hdr;
637 u16 auth_alg, auth_transaction, status;
638 __le16 *pos;
639 struct sta_info *sta = NULL;
640 char *txt = NULL;
641
642 if (ap->local->hostapd) {
643 dev_kfree_skb(skb);
644 return;
645 }
646
647 hdr = (struct ieee80211_hdr *) skb->data;
648 if (!ieee80211_is_auth(hdr->frame_control) ||
649 skb->len < IEEE80211_MGMT_HDR_LEN + 6) {
650 printk(KERN_DEBUG "%s: hostap_ap_tx_cb_auth received invalid "
651 "frame\n", dev->name);
652 dev_kfree_skb(skb);
653 return;
654 }
655
656 pos = (__le16 *) (skb->data + IEEE80211_MGMT_HDR_LEN);
657 auth_alg = le16_to_cpu(*pos++);
658 auth_transaction = le16_to_cpu(*pos++);
659 status = le16_to_cpu(*pos++);
660
661 if (!ok) {
662 txt = "frame was not ACKed";
663 goto done;
664 }
665
666 spin_lock(&ap->sta_table_lock);
667 sta = ap_get_sta(ap, hdr->addr1);
668 if (sta)
669 atomic_inc(&sta->users);
670 spin_unlock(&ap->sta_table_lock);
671
672 if (!sta) {
673 txt = "STA not found";
674 goto done;
675 }
676
677 if (status == WLAN_STATUS_SUCCESS &&
678 ((auth_alg == WLAN_AUTH_OPEN && auth_transaction == 2) ||
679 (auth_alg == WLAN_AUTH_SHARED_KEY && auth_transaction == 4))) {
680 txt = "STA authenticated";
681 sta->flags |= WLAN_STA_AUTH;
682 sta->last_auth = jiffies;
683 } else if (status != WLAN_STATUS_SUCCESS)
684 txt = "authentication failed";
685
686 done:
687 if (sta)
688 atomic_dec(&sta->users);
689 if (txt) {
690 PDEBUG(DEBUG_AP, "%s: %pM auth_cb - alg=%d "
691 "trans#=%d status=%d - %s\n",
692 dev->name, hdr->addr1,
693 auth_alg, auth_transaction, status, txt);
694 }
695 dev_kfree_skb(skb);
696}
697
698
699/* Called only as a tasklet (software IRQ) */
700static void hostap_ap_tx_cb_assoc(struct sk_buff *skb, int ok, void *data)
701{
702 struct ap_data *ap = data;
703 struct net_device *dev = ap->local->dev;
704 struct ieee80211_hdr *hdr;
705 u16 status;
706 __le16 *pos;
707 struct sta_info *sta = NULL;
708 char *txt = NULL;
709
710 if (ap->local->hostapd) {
711 dev_kfree_skb(skb);
712 return;
713 }
714
715 hdr = (struct ieee80211_hdr *) skb->data;
716 if ((!ieee80211_is_assoc_resp(hdr->frame_control) &&
717 !ieee80211_is_reassoc_resp(hdr->frame_control)) ||
718 skb->len < IEEE80211_MGMT_HDR_LEN + 4) {
719 printk(KERN_DEBUG "%s: hostap_ap_tx_cb_assoc received invalid "
720 "frame\n", dev->name);
721 dev_kfree_skb(skb);
722 return;
723 }
724
725 if (!ok) {
726 txt = "frame was not ACKed";
727 goto done;
728 }
729
730 spin_lock(&ap->sta_table_lock);
731 sta = ap_get_sta(ap, hdr->addr1);
732 if (sta)
733 atomic_inc(&sta->users);
734 spin_unlock(&ap->sta_table_lock);
735
736 if (!sta) {
737 txt = "STA not found";
738 goto done;
739 }
740
741 pos = (__le16 *) (skb->data + IEEE80211_MGMT_HDR_LEN);
742 pos++;
743 status = le16_to_cpu(*pos++);
744 if (status == WLAN_STATUS_SUCCESS) {
745 if (!(sta->flags & WLAN_STA_ASSOC))
746 hostap_event_new_sta(dev, sta);
747 txt = "STA associated";
748 sta->flags |= WLAN_STA_ASSOC;
749 sta->last_assoc = jiffies;
750 } else
751 txt = "association failed";
752
753 done:
754 if (sta)
755 atomic_dec(&sta->users);
756 if (txt) {
757 PDEBUG(DEBUG_AP, "%s: %pM assoc_cb - %s\n",
758 dev->name, hdr->addr1, txt);
759 }
760 dev_kfree_skb(skb);
761}
762
763/* Called only as a tasklet (software IRQ); TX callback for poll frames used
764 * in verifying whether the STA is still present. */
765static void hostap_ap_tx_cb_poll(struct sk_buff *skb, int ok, void *data)
766{
767 struct ap_data *ap = data;
768 struct ieee80211_hdr *hdr;
769 struct sta_info *sta;
770
771 if (skb->len < 24)
772 goto fail;
773 hdr = (struct ieee80211_hdr *) skb->data;
774 if (ok) {
775 spin_lock(&ap->sta_table_lock);
776 sta = ap_get_sta(ap, hdr->addr1);
777 if (sta)
778 sta->flags &= ~WLAN_STA_PENDING_POLL;
779 spin_unlock(&ap->sta_table_lock);
780 } else {
781 PDEBUG(DEBUG_AP,
782 "%s: STA %pM did not ACK activity poll frame\n",
783 ap->local->dev->name, hdr->addr1);
784 }
785
786 fail:
787 dev_kfree_skb(skb);
788}
789#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
790
791
792void hostap_init_data(local_info_t *local)
793{
794 struct ap_data *ap = local->ap;
795
796 if (ap == NULL) {
797 printk(KERN_WARNING "hostap_init_data: ap == NULL\n");
798 return;
799 }
800 memset(ap, 0, sizeof(struct ap_data));
801 ap->local = local;
802
803 ap->ap_policy = GET_INT_PARM(other_ap_policy, local->card_idx);
804 ap->bridge_packets = GET_INT_PARM(ap_bridge_packets, local->card_idx);
805 ap->max_inactivity =
806 GET_INT_PARM(ap_max_inactivity, local->card_idx) * HZ;
807 ap->autom_ap_wds = GET_INT_PARM(autom_ap_wds, local->card_idx);
808
809 spin_lock_init(&ap->sta_table_lock);
810 INIT_LIST_HEAD(&ap->sta_list);
811
812 /* Initialize task queue structure for AP management */
813 INIT_WORK(&local->ap->add_sta_proc_queue, handle_add_proc_queue);
814
815 ap->tx_callback_idx =
816 hostap_tx_callback_register(local, hostap_ap_tx_cb, ap);
817 if (ap->tx_callback_idx == 0)
818 printk(KERN_WARNING "%s: failed to register TX callback for "
819 "AP\n", local->dev->name);
820#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
821 INIT_WORK(&local->ap->wds_oper_queue, handle_wds_oper_queue);
822
823 ap->tx_callback_auth =
824 hostap_tx_callback_register(local, hostap_ap_tx_cb_auth, ap);
825 ap->tx_callback_assoc =
826 hostap_tx_callback_register(local, hostap_ap_tx_cb_assoc, ap);
827 ap->tx_callback_poll =
828 hostap_tx_callback_register(local, hostap_ap_tx_cb_poll, ap);
829 if (ap->tx_callback_auth == 0 || ap->tx_callback_assoc == 0 ||
830 ap->tx_callback_poll == 0)
831 printk(KERN_WARNING "%s: failed to register TX callback for "
832 "AP\n", local->dev->name);
833
834 spin_lock_init(&ap->mac_restrictions.lock);
835 INIT_LIST_HEAD(&ap->mac_restrictions.mac_list);
836#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
837
838 ap->initialized = 1;
839}
840
841
842void hostap_init_ap_proc(local_info_t *local)
843{
844 struct ap_data *ap = local->ap;
845
846 ap->proc = local->proc;
847 if (ap->proc == NULL)
848 return;
849
850#ifndef PRISM2_NO_PROCFS_DEBUG
851 proc_create_single_data("ap_debug", 0, ap->proc, ap_debug_proc_show, ap);
852#endif /* PRISM2_NO_PROCFS_DEBUG */
853
854#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
855 proc_create_seq_data("ap_control", 0, ap->proc, &ap_control_proc_seqops,
856 ap);
857 proc_create_seq_data("ap", 0, ap->proc, &prism2_ap_proc_seqops, ap);
858#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
859
860}
861
862
863void hostap_free_data(struct ap_data *ap)
864{
865 struct sta_info *n, *sta;
866
867 if (ap == NULL || !ap->initialized) {
868 printk(KERN_DEBUG "hostap_free_data: ap has not yet been "
869 "initialized - skip resource freeing\n");
870 return;
871 }
872
873 flush_work(&ap->add_sta_proc_queue);
874
875#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
876 flush_work(&ap->wds_oper_queue);
877 if (ap->crypt)
878 ap->crypt->deinit(ap->crypt_priv);
879 ap->crypt = ap->crypt_priv = NULL;
880#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
881
882 list_for_each_entry_safe(sta, n, &ap->sta_list, list) {
883 ap_sta_hash_del(ap, sta);
884 list_del(&sta->list);
885 if ((sta->flags & WLAN_STA_ASSOC) && !sta->ap && sta->local)
886 hostap_event_expired_sta(sta->local->dev, sta);
887 ap_free_sta(ap, sta);
888 }
889
890#ifndef PRISM2_NO_PROCFS_DEBUG
891 if (ap->proc != NULL) {
892 remove_proc_entry("ap_debug", ap->proc);
893 }
894#endif /* PRISM2_NO_PROCFS_DEBUG */
895
896#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
897 if (ap->proc != NULL) {
898 remove_proc_entry("ap", ap->proc);
899 remove_proc_entry("ap_control", ap->proc);
900 }
901 ap_control_flush_macs(&ap->mac_restrictions);
902#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
903
904 ap->initialized = 0;
905}
906
907
908/* caller should have mutex for AP STA list handling */
909static struct sta_info* ap_get_sta(struct ap_data *ap, u8 *sta)
910{
911 struct sta_info *s;
912
913 s = ap->sta_hash[STA_HASH(sta)];
914 while (s != NULL && !ether_addr_equal(s->addr, sta))
915 s = s->hnext;
916 return s;
917}
918
919
920#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
921
922/* Called from timer handler and from scheduled AP queue handlers */
923static void prism2_send_mgmt(struct net_device *dev,
924 u16 type_subtype, char *body,
925 int body_len, u8 *addr, u16 tx_cb_idx)
926{
927 struct hostap_interface *iface;
928 local_info_t *local;
929 struct ieee80211_hdr *hdr;
930 u16 fc;
931 struct sk_buff *skb;
932 struct hostap_skb_tx_data *meta;
933 int hdrlen;
934
935 iface = netdev_priv(dev);
936 local = iface->local;
937 dev = local->dev; /* always use master radio device */
938 iface = netdev_priv(dev);
939
940 if (!(dev->flags & IFF_UP)) {
941 PDEBUG(DEBUG_AP, "%s: prism2_send_mgmt - device is not UP - "
942 "cannot send frame\n", dev->name);
943 return;
944 }
945
946 skb = dev_alloc_skb(sizeof(*hdr) + body_len);
947 if (skb == NULL) {
948 PDEBUG(DEBUG_AP, "%s: prism2_send_mgmt failed to allocate "
949 "skb\n", dev->name);
950 return;
951 }
952
953 fc = type_subtype;
954 hdrlen = hostap_80211_get_hdrlen(cpu_to_le16(type_subtype));
955 hdr = skb_put_zero(skb, hdrlen);
956 if (body)
957 skb_put_data(skb, body, body_len);
958
959 /* FIX: ctrl::ack sending used special HFA384X_TX_CTRL_802_11
960 * tx_control instead of using local->tx_control */
961
962
963 memcpy(hdr->addr1, addr, ETH_ALEN); /* DA / RA */
964 if (ieee80211_is_data(hdr->frame_control)) {
965 fc |= IEEE80211_FCTL_FROMDS;
966 memcpy(hdr->addr2, dev->dev_addr, ETH_ALEN); /* BSSID */
967 memcpy(hdr->addr3, dev->dev_addr, ETH_ALEN); /* SA */
968 } else if (ieee80211_is_ctl(hdr->frame_control)) {
969 /* control:ACK does not have addr2 or addr3 */
970 eth_zero_addr(hdr->addr2);
971 eth_zero_addr(hdr->addr3);
972 } else {
973 memcpy(hdr->addr2, dev->dev_addr, ETH_ALEN); /* SA */
974 memcpy(hdr->addr3, dev->dev_addr, ETH_ALEN); /* BSSID */
975 }
976
977 hdr->frame_control = cpu_to_le16(fc);
978
979 meta = (struct hostap_skb_tx_data *) skb->cb;
980 memset(meta, 0, sizeof(*meta));
981 meta->magic = HOSTAP_SKB_TX_DATA_MAGIC;
982 meta->iface = iface;
983 meta->tx_cb_idx = tx_cb_idx;
984
985 skb->dev = dev;
986 skb_reset_mac_header(skb);
987 skb_reset_network_header(skb);
988 dev_queue_xmit(skb);
989}
990#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
991
992#ifdef CONFIG_PROC_FS
993static int prism2_sta_proc_show(struct seq_file *m, void *v)
994{
995 struct sta_info *sta = m->private;
996 int i;
997
998 /* FIX: possible race condition.. the STA data could have just expired,
999 * but proc entry was still here so that the read could have started;
1000 * some locking should be done here.. */
1001
1002 seq_printf(m,
1003 "%s=%pM\nusers=%d\naid=%d\n"
1004 "flags=0x%04x%s%s%s%s%s%s%s\n"
1005 "capability=0x%02x\nlisten_interval=%d\nsupported_rates=",
1006 sta->ap ? "AP" : "STA",
1007 sta->addr, atomic_read(&sta->users), sta->aid,
1008 sta->flags,
1009 sta->flags & WLAN_STA_AUTH ? " AUTH" : "",
1010 sta->flags & WLAN_STA_ASSOC ? " ASSOC" : "",
1011 sta->flags & WLAN_STA_PS ? " PS" : "",
1012 sta->flags & WLAN_STA_TIM ? " TIM" : "",
1013 sta->flags & WLAN_STA_PERM ? " PERM" : "",
1014 sta->flags & WLAN_STA_AUTHORIZED ? " AUTHORIZED" : "",
1015 sta->flags & WLAN_STA_PENDING_POLL ? " POLL" : "",
1016 sta->capability, sta->listen_interval);
1017 /* supported_rates: 500 kbit/s units with msb ignored */
1018 for (i = 0; i < sizeof(sta->supported_rates); i++)
1019 if (sta->supported_rates[i] != 0)
1020 seq_printf(m, "%d%sMbps ",
1021 (sta->supported_rates[i] & 0x7f) / 2,
1022 sta->supported_rates[i] & 1 ? ".5" : "");
1023 seq_printf(m,
1024 "\njiffies=%lu\nlast_auth=%lu\nlast_assoc=%lu\n"
1025 "last_rx=%lu\nlast_tx=%lu\nrx_packets=%lu\n"
1026 "tx_packets=%lu\n"
1027 "rx_bytes=%lu\ntx_bytes=%lu\nbuffer_count=%d\n"
1028 "last_rx: silence=%d dBm signal=%d dBm rate=%d%s Mbps\n"
1029 "tx_rate=%d\ntx[1M]=%d\ntx[2M]=%d\ntx[5.5M]=%d\n"
1030 "tx[11M]=%d\n"
1031 "rx[1M]=%d\nrx[2M]=%d\nrx[5.5M]=%d\nrx[11M]=%d\n",
1032 jiffies, sta->last_auth, sta->last_assoc, sta->last_rx,
1033 sta->last_tx,
1034 sta->rx_packets, sta->tx_packets, sta->rx_bytes,
1035 sta->tx_bytes, skb_queue_len(&sta->tx_buf),
1036 sta->last_rx_silence,
1037 sta->last_rx_signal, sta->last_rx_rate / 10,
1038 sta->last_rx_rate % 10 ? ".5" : "",
1039 sta->tx_rate, sta->tx_count[0], sta->tx_count[1],
1040 sta->tx_count[2], sta->tx_count[3], sta->rx_count[0],
1041 sta->rx_count[1], sta->rx_count[2], sta->rx_count[3]);
1042 if (sta->crypt && sta->crypt->ops && sta->crypt->ops->print_stats)
1043 sta->crypt->ops->print_stats(m, sta->crypt->priv);
1044#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
1045 if (sta->ap) {
1046 if (sta->u.ap.channel >= 0)
1047 seq_printf(m, "channel=%d\n", sta->u.ap.channel);
1048 seq_puts(m, "ssid=");
1049 for (i = 0; i < sta->u.ap.ssid_len; i++) {
1050 if (sta->u.ap.ssid[i] >= 32 && sta->u.ap.ssid[i] < 127)
1051 seq_putc(m, sta->u.ap.ssid[i]);
1052 else
1053 seq_printf(m, "<%02x>", sta->u.ap.ssid[i]);
1054 }
1055 seq_putc(m, '\n');
1056 }
1057#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
1058
1059 return 0;
1060}
1061#endif
1062
1063static void handle_add_proc_queue(struct work_struct *work)
1064{
1065 struct ap_data *ap = container_of(work, struct ap_data,
1066 add_sta_proc_queue);
1067 struct sta_info *sta;
1068 char name[20];
1069 struct add_sta_proc_data *entry, *prev;
1070
1071 entry = ap->add_sta_proc_entries;
1072 ap->add_sta_proc_entries = NULL;
1073
1074 while (entry) {
1075 spin_lock_bh(&ap->sta_table_lock);
1076 sta = ap_get_sta(ap, entry->addr);
1077 if (sta)
1078 atomic_inc(&sta->users);
1079 spin_unlock_bh(&ap->sta_table_lock);
1080
1081 if (sta) {
1082 sprintf(name, "%pM", sta->addr);
1083 sta->proc = proc_create_single_data(
1084 name, 0, ap->proc,
1085 prism2_sta_proc_show, sta);
1086
1087 atomic_dec(&sta->users);
1088 }
1089
1090 prev = entry;
1091 entry = entry->next;
1092 kfree(prev);
1093 }
1094}
1095
1096
1097static struct sta_info * ap_add_sta(struct ap_data *ap, u8 *addr)
1098{
1099 struct sta_info *sta;
1100
1101 sta = kzalloc(sizeof(struct sta_info), GFP_ATOMIC);
1102 if (sta == NULL) {
1103 PDEBUG(DEBUG_AP, "AP: kmalloc failed\n");
1104 return NULL;
1105 }
1106
1107 /* initialize STA info data */
1108 sta->local = ap->local;
1109 skb_queue_head_init(&sta->tx_buf);
1110 memcpy(sta->addr, addr, ETH_ALEN);
1111
1112 atomic_inc(&sta->users);
1113 spin_lock_bh(&ap->sta_table_lock);
1114 list_add(&sta->list, &ap->sta_list);
1115 ap->num_sta++;
1116 ap_sta_hash_add(ap, sta);
1117 spin_unlock_bh(&ap->sta_table_lock);
1118
1119 if (ap->proc) {
1120 struct add_sta_proc_data *entry;
1121 /* schedule a non-interrupt context process to add a procfs
1122 * entry for the STA since procfs code use GFP_KERNEL */
1123 entry = kmalloc(sizeof(*entry), GFP_ATOMIC);
1124 if (entry) {
1125 memcpy(entry->addr, sta->addr, ETH_ALEN);
1126 entry->next = ap->add_sta_proc_entries;
1127 ap->add_sta_proc_entries = entry;
1128 schedule_work(&ap->add_sta_proc_queue);
1129 } else
1130 printk(KERN_DEBUG "Failed to add STA proc data\n");
1131 }
1132
1133#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
1134 timer_setup(&sta->timer, ap_handle_timer, 0);
1135 sta->timer.expires = jiffies + ap->max_inactivity;
1136 if (!ap->local->hostapd)
1137 add_timer(&sta->timer);
1138#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
1139
1140 return sta;
1141}
1142
1143
1144static int ap_tx_rate_ok(int rateidx, struct sta_info *sta,
1145 local_info_t *local)
1146{
1147 if (rateidx > sta->tx_max_rate ||
1148 !(sta->tx_supp_rates & (1 << rateidx)))
1149 return 0;
1150
1151 if (local->tx_rate_control != 0 &&
1152 !(local->tx_rate_control & (1 << rateidx)))
1153 return 0;
1154
1155 return 1;
1156}
1157
1158
1159static void prism2_check_tx_rates(struct sta_info *sta)
1160{
1161 int i;
1162
1163 sta->tx_supp_rates = 0;
1164 for (i = 0; i < sizeof(sta->supported_rates); i++) {
1165 if ((sta->supported_rates[i] & 0x7f) == 2)
1166 sta->tx_supp_rates |= WLAN_RATE_1M;
1167 if ((sta->supported_rates[i] & 0x7f) == 4)
1168 sta->tx_supp_rates |= WLAN_RATE_2M;
1169 if ((sta->supported_rates[i] & 0x7f) == 11)
1170 sta->tx_supp_rates |= WLAN_RATE_5M5;
1171 if ((sta->supported_rates[i] & 0x7f) == 22)
1172 sta->tx_supp_rates |= WLAN_RATE_11M;
1173 }
1174 sta->tx_max_rate = sta->tx_rate = sta->tx_rate_idx = 0;
1175 if (sta->tx_supp_rates & WLAN_RATE_1M) {
1176 sta->tx_max_rate = 0;
1177 if (ap_tx_rate_ok(0, sta, sta->local)) {
1178 sta->tx_rate = 10;
1179 sta->tx_rate_idx = 0;
1180 }
1181 }
1182 if (sta->tx_supp_rates & WLAN_RATE_2M) {
1183 sta->tx_max_rate = 1;
1184 if (ap_tx_rate_ok(1, sta, sta->local)) {
1185 sta->tx_rate = 20;
1186 sta->tx_rate_idx = 1;
1187 }
1188 }
1189 if (sta->tx_supp_rates & WLAN_RATE_5M5) {
1190 sta->tx_max_rate = 2;
1191 if (ap_tx_rate_ok(2, sta, sta->local)) {
1192 sta->tx_rate = 55;
1193 sta->tx_rate_idx = 2;
1194 }
1195 }
1196 if (sta->tx_supp_rates & WLAN_RATE_11M) {
1197 sta->tx_max_rate = 3;
1198 if (ap_tx_rate_ok(3, sta, sta->local)) {
1199 sta->tx_rate = 110;
1200 sta->tx_rate_idx = 3;
1201 }
1202 }
1203}
1204
1205
1206#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
1207
1208static void ap_crypt_init(struct ap_data *ap)
1209{
1210 ap->crypt = lib80211_get_crypto_ops("WEP");
1211
1212 if (ap->crypt) {
1213 if (ap->crypt->init) {
1214 ap->crypt_priv = ap->crypt->init(0);
1215 if (ap->crypt_priv == NULL)
1216 ap->crypt = NULL;
1217 else {
1218 u8 key[WEP_KEY_LEN];
1219 get_random_bytes(key, WEP_KEY_LEN);
1220 ap->crypt->set_key(key, WEP_KEY_LEN, NULL,
1221 ap->crypt_priv);
1222 }
1223 }
1224 }
1225
1226 if (ap->crypt == NULL) {
1227 printk(KERN_WARNING "AP could not initialize WEP: load module "
1228 "lib80211_crypt_wep.ko\n");
1229 }
1230}
1231
1232
1233/* Generate challenge data for shared key authentication. IEEE 802.11 specifies
1234 * that WEP algorithm is used for generating challenge. This should be unique,
1235 * but otherwise there is not really need for randomness etc. Initialize WEP
1236 * with pseudo random key and then use increasing IV to get unique challenge
1237 * streams.
1238 *
1239 * Called only as a scheduled task for pending AP frames.
1240 */
1241static char * ap_auth_make_challenge(struct ap_data *ap)
1242{
1243 char *tmpbuf;
1244 struct sk_buff *skb;
1245
1246 if (ap->crypt == NULL) {
1247 ap_crypt_init(ap);
1248 if (ap->crypt == NULL)
1249 return NULL;
1250 }
1251
1252 tmpbuf = kmalloc(WLAN_AUTH_CHALLENGE_LEN, GFP_ATOMIC);
1253 if (tmpbuf == NULL) {
1254 PDEBUG(DEBUG_AP, "AP: kmalloc failed for challenge\n");
1255 return NULL;
1256 }
1257
1258 skb = dev_alloc_skb(WLAN_AUTH_CHALLENGE_LEN +
1259 ap->crypt->extra_mpdu_prefix_len +
1260 ap->crypt->extra_mpdu_postfix_len);
1261 if (skb == NULL) {
1262 kfree(tmpbuf);
1263 return NULL;
1264 }
1265
1266 skb_reserve(skb, ap->crypt->extra_mpdu_prefix_len);
1267 skb_put_zero(skb, WLAN_AUTH_CHALLENGE_LEN);
1268 if (ap->crypt->encrypt_mpdu(skb, 0, ap->crypt_priv)) {
1269 dev_kfree_skb(skb);
1270 kfree(tmpbuf);
1271 return NULL;
1272 }
1273
1274 skb_copy_from_linear_data_offset(skb, ap->crypt->extra_mpdu_prefix_len,
1275 tmpbuf, WLAN_AUTH_CHALLENGE_LEN);
1276 dev_kfree_skb(skb);
1277
1278 return tmpbuf;
1279}
1280
1281
1282/* Called only as a scheduled task for pending AP frames. */
1283static void handle_authen(local_info_t *local, struct sk_buff *skb,
1284 struct hostap_80211_rx_status *rx_stats)
1285{
1286 struct net_device *dev = local->dev;
1287 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data;
1288 size_t hdrlen;
1289 struct ap_data *ap = local->ap;
1290 char body[8 + WLAN_AUTH_CHALLENGE_LEN], *challenge = NULL;
1291 int len, olen;
1292 u16 auth_alg, auth_transaction, status_code;
1293 __le16 *pos;
1294 u16 resp = WLAN_STATUS_SUCCESS;
1295 struct sta_info *sta = NULL;
1296 struct lib80211_crypt_data *crypt;
1297 char *txt = "";
1298
1299 len = skb->len - IEEE80211_MGMT_HDR_LEN;
1300
1301 hdrlen = hostap_80211_get_hdrlen(hdr->frame_control);
1302
1303 if (len < 6) {
1304 PDEBUG(DEBUG_AP, "%s: handle_authen - too short payload "
1305 "(len=%d) from %pM\n", dev->name, len, hdr->addr2);
1306 return;
1307 }
1308
1309 spin_lock_bh(&local->ap->sta_table_lock);
1310 sta = ap_get_sta(local->ap, hdr->addr2);
1311 if (sta)
1312 atomic_inc(&sta->users);
1313 spin_unlock_bh(&local->ap->sta_table_lock);
1314
1315 if (sta && sta->crypt)
1316 crypt = sta->crypt;
1317 else {
1318 int idx = 0;
1319 if (skb->len >= hdrlen + 3)
1320 idx = skb->data[hdrlen + 3] >> 6;
1321 crypt = local->crypt_info.crypt[idx];
1322 }
1323
1324 pos = (__le16 *) (skb->data + IEEE80211_MGMT_HDR_LEN);
1325 auth_alg = __le16_to_cpu(*pos);
1326 pos++;
1327 auth_transaction = __le16_to_cpu(*pos);
1328 pos++;
1329 status_code = __le16_to_cpu(*pos);
1330 pos++;
1331
1332 if (ether_addr_equal(dev->dev_addr, hdr->addr2) ||
1333 ap_control_mac_deny(&ap->mac_restrictions, hdr->addr2)) {
1334 txt = "authentication denied";
1335 resp = WLAN_STATUS_UNSPECIFIED_FAILURE;
1336 goto fail;
1337 }
1338
1339 if (((local->auth_algs & PRISM2_AUTH_OPEN) &&
1340 auth_alg == WLAN_AUTH_OPEN) ||
1341 ((local->auth_algs & PRISM2_AUTH_SHARED_KEY) &&
1342 crypt && auth_alg == WLAN_AUTH_SHARED_KEY)) {
1343 } else {
1344 txt = "unsupported algorithm";
1345 resp = WLAN_STATUS_NOT_SUPPORTED_AUTH_ALG;
1346 goto fail;
1347 }
1348
1349 if (len >= 8) {
1350 u8 *u = (u8 *) pos;
1351 if (*u == WLAN_EID_CHALLENGE) {
1352 if (*(u + 1) != WLAN_AUTH_CHALLENGE_LEN) {
1353 txt = "invalid challenge len";
1354 resp = WLAN_STATUS_CHALLENGE_FAIL;
1355 goto fail;
1356 }
1357 if (len - 8 < WLAN_AUTH_CHALLENGE_LEN) {
1358 txt = "challenge underflow";
1359 resp = WLAN_STATUS_CHALLENGE_FAIL;
1360 goto fail;
1361 }
1362 challenge = (char *) (u + 2);
1363 }
1364 }
1365
1366 if (sta && sta->ap) {
1367 if (time_after(jiffies, sta->u.ap.last_beacon +
1368 (10 * sta->listen_interval * HZ) / 1024)) {
1369 PDEBUG(DEBUG_AP, "%s: no beacons received for a while,"
1370 " assuming AP %pM is now STA\n",
1371 dev->name, sta->addr);
1372 sta->ap = 0;
1373 sta->flags = 0;
1374 sta->u.sta.challenge = NULL;
1375 } else {
1376 txt = "AP trying to authenticate?";
1377 resp = WLAN_STATUS_UNSPECIFIED_FAILURE;
1378 goto fail;
1379 }
1380 }
1381
1382 if ((auth_alg == WLAN_AUTH_OPEN && auth_transaction == 1) ||
1383 (auth_alg == WLAN_AUTH_SHARED_KEY &&
1384 (auth_transaction == 1 ||
1385 (auth_transaction == 3 && sta != NULL &&
1386 sta->u.sta.challenge != NULL)))) {
1387 } else {
1388 txt = "unknown authentication transaction number";
1389 resp = WLAN_STATUS_UNKNOWN_AUTH_TRANSACTION;
1390 goto fail;
1391 }
1392
1393 if (sta == NULL) {
1394 txt = "new STA";
1395
1396 if (local->ap->num_sta >= MAX_STA_COUNT) {
1397 /* FIX: might try to remove some old STAs first? */
1398 txt = "no more room for new STAs";
1399 resp = WLAN_STATUS_UNSPECIFIED_FAILURE;
1400 goto fail;
1401 }
1402
1403 sta = ap_add_sta(local->ap, hdr->addr2);
1404 if (sta == NULL) {
1405 txt = "ap_add_sta failed";
1406 resp = WLAN_STATUS_UNSPECIFIED_FAILURE;
1407 goto fail;
1408 }
1409 }
1410
1411 switch (auth_alg) {
1412 case WLAN_AUTH_OPEN:
1413 txt = "authOK";
1414 /* IEEE 802.11 standard is not completely clear about
1415 * whether STA is considered authenticated after
1416 * authentication OK frame has been send or after it
1417 * has been ACKed. In order to reduce interoperability
1418 * issues, mark the STA authenticated before ACK. */
1419 sta->flags |= WLAN_STA_AUTH;
1420 break;
1421
1422 case WLAN_AUTH_SHARED_KEY:
1423 if (auth_transaction == 1) {
1424 if (sta->u.sta.challenge == NULL) {
1425 sta->u.sta.challenge =
1426 ap_auth_make_challenge(local->ap);
1427 if (sta->u.sta.challenge == NULL) {
1428 resp = WLAN_STATUS_UNSPECIFIED_FAILURE;
1429 goto fail;
1430 }
1431 }
1432 } else {
1433 if (sta->u.sta.challenge == NULL ||
1434 challenge == NULL ||
1435 memcmp(sta->u.sta.challenge, challenge,
1436 WLAN_AUTH_CHALLENGE_LEN) != 0 ||
1437 !ieee80211_has_protected(hdr->frame_control)) {
1438 txt = "challenge response incorrect";
1439 resp = WLAN_STATUS_CHALLENGE_FAIL;
1440 goto fail;
1441 }
1442
1443 txt = "challenge OK - authOK";
1444 /* IEEE 802.11 standard is not completely clear about
1445 * whether STA is considered authenticated after
1446 * authentication OK frame has been send or after it
1447 * has been ACKed. In order to reduce interoperability
1448 * issues, mark the STA authenticated before ACK. */
1449 sta->flags |= WLAN_STA_AUTH;
1450 kfree(sta->u.sta.challenge);
1451 sta->u.sta.challenge = NULL;
1452 }
1453 break;
1454 }
1455
1456 fail:
1457 pos = (__le16 *) body;
1458 *pos = cpu_to_le16(auth_alg);
1459 pos++;
1460 *pos = cpu_to_le16(auth_transaction + 1);
1461 pos++;
1462 *pos = cpu_to_le16(resp); /* status_code */
1463 pos++;
1464 olen = 6;
1465
1466 if (resp == WLAN_STATUS_SUCCESS && sta != NULL &&
1467 sta->u.sta.challenge != NULL &&
1468 auth_alg == WLAN_AUTH_SHARED_KEY && auth_transaction == 1) {
1469 u8 *tmp = (u8 *) pos;
1470 *tmp++ = WLAN_EID_CHALLENGE;
1471 *tmp++ = WLAN_AUTH_CHALLENGE_LEN;
1472 pos++;
1473 memcpy(pos, sta->u.sta.challenge, WLAN_AUTH_CHALLENGE_LEN);
1474 olen += 2 + WLAN_AUTH_CHALLENGE_LEN;
1475 }
1476
1477 prism2_send_mgmt(dev, IEEE80211_FTYPE_MGMT | IEEE80211_STYPE_AUTH,
1478 body, olen, hdr->addr2, ap->tx_callback_auth);
1479
1480 if (sta) {
1481 sta->last_rx = jiffies;
1482 atomic_dec(&sta->users);
1483 }
1484
1485 if (resp) {
1486 PDEBUG(DEBUG_AP, "%s: %pM auth (alg=%d "
1487 "trans#=%d stat=%d len=%d fc=%04x) ==> %d (%s)\n",
1488 dev->name, hdr->addr2,
1489 auth_alg, auth_transaction, status_code, len,
1490 le16_to_cpu(hdr->frame_control), resp, txt);
1491 }
1492}
1493
1494
1495/* Called only as a scheduled task for pending AP frames. */
1496static void handle_assoc(local_info_t *local, struct sk_buff *skb,
1497 struct hostap_80211_rx_status *rx_stats, int reassoc)
1498{
1499 struct net_device *dev = local->dev;
1500 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data;
1501 char body[12], *p, *lpos;
1502 int len, left;
1503 __le16 *pos;
1504 u16 resp = WLAN_STATUS_SUCCESS;
1505 struct sta_info *sta = NULL;
1506 int send_deauth = 0;
1507 char __always_unused *txt = "";
1508 u8 prev_ap[ETH_ALEN];
1509
1510 left = len = skb->len - IEEE80211_MGMT_HDR_LEN;
1511
1512 if (len < (reassoc ? 10 : 4)) {
1513 PDEBUG(DEBUG_AP, "%s: handle_assoc - too short payload "
1514 "(len=%d, reassoc=%d) from %pM\n",
1515 dev->name, len, reassoc, hdr->addr2);
1516 return;
1517 }
1518
1519 spin_lock_bh(&local->ap->sta_table_lock);
1520 sta = ap_get_sta(local->ap, hdr->addr2);
1521 if (sta == NULL || (sta->flags & WLAN_STA_AUTH) == 0) {
1522 spin_unlock_bh(&local->ap->sta_table_lock);
1523 txt = "trying to associate before authentication";
1524 send_deauth = 1;
1525 resp = WLAN_STATUS_UNSPECIFIED_FAILURE;
1526 sta = NULL; /* do not decrement sta->users */
1527 goto fail;
1528 }
1529 atomic_inc(&sta->users);
1530 spin_unlock_bh(&local->ap->sta_table_lock);
1531
1532 pos = (__le16 *) (skb->data + IEEE80211_MGMT_HDR_LEN);
1533 sta->capability = __le16_to_cpu(*pos);
1534 pos++; left -= 2;
1535 sta->listen_interval = __le16_to_cpu(*pos);
1536 pos++; left -= 2;
1537
1538 if (reassoc) {
1539 memcpy(prev_ap, pos, ETH_ALEN);
1540 pos++; pos++; pos++; left -= 6;
1541 } else
1542 eth_zero_addr(prev_ap);
1543
1544 if (left >= 2) {
1545 unsigned int ileft;
1546 unsigned char *u = (unsigned char *) pos;
1547
1548 if (*u == WLAN_EID_SSID) {
1549 u++; left--;
1550 ileft = *u;
1551 u++; left--;
1552
1553 if (ileft > left || ileft > MAX_SSID_LEN) {
1554 txt = "SSID overflow";
1555 resp = WLAN_STATUS_UNSPECIFIED_FAILURE;
1556 goto fail;
1557 }
1558
1559 if (ileft != strlen(local->essid) ||
1560 memcmp(local->essid, u, ileft) != 0) {
1561 txt = "not our SSID";
1562 resp = WLAN_STATUS_ASSOC_DENIED_UNSPEC;
1563 goto fail;
1564 }
1565
1566 u += ileft;
1567 left -= ileft;
1568 }
1569
1570 if (left >= 2 && *u == WLAN_EID_SUPP_RATES) {
1571 u++; left--;
1572 ileft = *u;
1573 u++; left--;
1574
1575 if (ileft > left || ileft == 0 ||
1576 ileft > WLAN_SUPP_RATES_MAX) {
1577 txt = "SUPP_RATES len error";
1578 resp = WLAN_STATUS_UNSPECIFIED_FAILURE;
1579 goto fail;
1580 }
1581
1582 memset(sta->supported_rates, 0,
1583 sizeof(sta->supported_rates));
1584 memcpy(sta->supported_rates, u, ileft);
1585 prism2_check_tx_rates(sta);
1586
1587 u += ileft;
1588 left -= ileft;
1589 }
1590
1591 if (left > 0) {
1592 PDEBUG(DEBUG_AP, "%s: assoc from %pM"
1593 " with extra data (%d bytes) [",
1594 dev->name, hdr->addr2, left);
1595 while (left > 0) {
1596 PDEBUG2(DEBUG_AP, "<%02x>", *u);
1597 u++; left--;
1598 }
1599 PDEBUG2(DEBUG_AP, "]\n");
1600 }
1601 } else {
1602 txt = "frame underflow";
1603 resp = WLAN_STATUS_UNSPECIFIED_FAILURE;
1604 goto fail;
1605 }
1606
1607 /* get a unique AID */
1608 if (sta->aid > 0)
1609 txt = "OK, old AID";
1610 else {
1611 spin_lock_bh(&local->ap->sta_table_lock);
1612 for (sta->aid = 1; sta->aid <= MAX_AID_TABLE_SIZE; sta->aid++)
1613 if (local->ap->sta_aid[sta->aid - 1] == NULL)
1614 break;
1615 if (sta->aid > MAX_AID_TABLE_SIZE) {
1616 sta->aid = 0;
1617 spin_unlock_bh(&local->ap->sta_table_lock);
1618 resp = WLAN_STATUS_AP_UNABLE_TO_HANDLE_NEW_STA;
1619 txt = "no room for more AIDs";
1620 } else {
1621 local->ap->sta_aid[sta->aid - 1] = sta;
1622 spin_unlock_bh(&local->ap->sta_table_lock);
1623 txt = "OK, new AID";
1624 }
1625 }
1626
1627 fail:
1628 pos = (__le16 *) body;
1629
1630 if (send_deauth) {
1631 *pos = cpu_to_le16(WLAN_REASON_STA_REQ_ASSOC_WITHOUT_AUTH);
1632 pos++;
1633 } else {
1634 /* FIX: CF-Pollable and CF-PollReq should be set to match the
1635 * values in beacons/probe responses */
1636 /* FIX: how about privacy and WEP? */
1637 /* capability */
1638 *pos = cpu_to_le16(WLAN_CAPABILITY_ESS);
1639 pos++;
1640
1641 /* status_code */
1642 *pos = cpu_to_le16(resp);
1643 pos++;
1644
1645 *pos = cpu_to_le16((sta && sta->aid > 0 ? sta->aid : 0) |
1646 BIT(14) | BIT(15)); /* AID */
1647 pos++;
1648
1649 /* Supported rates (Information element) */
1650 p = (char *) pos;
1651 *p++ = WLAN_EID_SUPP_RATES;
1652 lpos = p;
1653 *p++ = 0; /* len */
1654 if (local->tx_rate_control & WLAN_RATE_1M) {
1655 *p++ = local->basic_rates & WLAN_RATE_1M ? 0x82 : 0x02;
1656 (*lpos)++;
1657 }
1658 if (local->tx_rate_control & WLAN_RATE_2M) {
1659 *p++ = local->basic_rates & WLAN_RATE_2M ? 0x84 : 0x04;
1660 (*lpos)++;
1661 }
1662 if (local->tx_rate_control & WLAN_RATE_5M5) {
1663 *p++ = local->basic_rates & WLAN_RATE_5M5 ?
1664 0x8b : 0x0b;
1665 (*lpos)++;
1666 }
1667 if (local->tx_rate_control & WLAN_RATE_11M) {
1668 *p++ = local->basic_rates & WLAN_RATE_11M ?
1669 0x96 : 0x16;
1670 (*lpos)++;
1671 }
1672 pos = (__le16 *) p;
1673 }
1674
1675 prism2_send_mgmt(dev, IEEE80211_FTYPE_MGMT |
1676 (send_deauth ? IEEE80211_STYPE_DEAUTH :
1677 (reassoc ? IEEE80211_STYPE_REASSOC_RESP :
1678 IEEE80211_STYPE_ASSOC_RESP)),
1679 body, (u8 *) pos - (u8 *) body,
1680 hdr->addr2,
1681 send_deauth ? 0 : local->ap->tx_callback_assoc);
1682
1683 if (sta) {
1684 if (resp == WLAN_STATUS_SUCCESS) {
1685 sta->last_rx = jiffies;
1686 /* STA will be marked associated from TX callback, if
1687 * AssocResp is ACKed */
1688 }
1689 atomic_dec(&sta->users);
1690 }
1691
1692#if 0
1693 PDEBUG(DEBUG_AP, "%s: %pM %sassoc (len=%d "
1694 "prev_ap=%pM) => %d(%d) (%s)\n",
1695 dev->name,
1696 hdr->addr2,
1697 reassoc ? "re" : "", len,
1698 prev_ap,
1699 resp, send_deauth, txt);
1700#endif
1701}
1702
1703
1704/* Called only as a scheduled task for pending AP frames. */
1705static void handle_deauth(local_info_t *local, struct sk_buff *skb,
1706 struct hostap_80211_rx_status *rx_stats)
1707{
1708 struct net_device *dev = local->dev;
1709 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data;
1710 char *body = (char *) (skb->data + IEEE80211_MGMT_HDR_LEN);
1711 int len;
1712 u16 reason_code;
1713 __le16 *pos;
1714 struct sta_info *sta = NULL;
1715
1716 len = skb->len - IEEE80211_MGMT_HDR_LEN;
1717
1718 if (len < 2) {
1719 printk("handle_deauth - too short payload (len=%d)\n", len);
1720 return;
1721 }
1722
1723 pos = (__le16 *) body;
1724 reason_code = le16_to_cpu(*pos);
1725
1726 PDEBUG(DEBUG_AP, "%s: deauthentication: %pM len=%d, "
1727 "reason_code=%d\n", dev->name, hdr->addr2,
1728 len, reason_code);
1729
1730 spin_lock_bh(&local->ap->sta_table_lock);
1731 sta = ap_get_sta(local->ap, hdr->addr2);
1732 if (sta != NULL) {
1733 if ((sta->flags & WLAN_STA_ASSOC) && !sta->ap)
1734 hostap_event_expired_sta(local->dev, sta);
1735 sta->flags &= ~(WLAN_STA_AUTH | WLAN_STA_ASSOC);
1736 }
1737 spin_unlock_bh(&local->ap->sta_table_lock);
1738 if (sta == NULL) {
1739 printk("%s: deauthentication from %pM, "
1740 "reason_code=%d, but STA not authenticated\n", dev->name,
1741 hdr->addr2, reason_code);
1742 }
1743}
1744
1745
1746/* Called only as a scheduled task for pending AP frames. */
1747static void handle_disassoc(local_info_t *local, struct sk_buff *skb,
1748 struct hostap_80211_rx_status *rx_stats)
1749{
1750 struct net_device *dev = local->dev;
1751 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data;
1752 char *body = skb->data + IEEE80211_MGMT_HDR_LEN;
1753 int len;
1754 u16 reason_code;
1755 __le16 *pos;
1756 struct sta_info *sta = NULL;
1757
1758 len = skb->len - IEEE80211_MGMT_HDR_LEN;
1759
1760 if (len < 2) {
1761 printk("handle_disassoc - too short payload (len=%d)\n", len);
1762 return;
1763 }
1764
1765 pos = (__le16 *) body;
1766 reason_code = le16_to_cpu(*pos);
1767
1768 PDEBUG(DEBUG_AP, "%s: disassociation: %pM len=%d, "
1769 "reason_code=%d\n", dev->name, hdr->addr2,
1770 len, reason_code);
1771
1772 spin_lock_bh(&local->ap->sta_table_lock);
1773 sta = ap_get_sta(local->ap, hdr->addr2);
1774 if (sta != NULL) {
1775 if ((sta->flags & WLAN_STA_ASSOC) && !sta->ap)
1776 hostap_event_expired_sta(local->dev, sta);
1777 sta->flags &= ~WLAN_STA_ASSOC;
1778 }
1779 spin_unlock_bh(&local->ap->sta_table_lock);
1780 if (sta == NULL) {
1781 printk("%s: disassociation from %pM, "
1782 "reason_code=%d, but STA not authenticated\n",
1783 dev->name, hdr->addr2, reason_code);
1784 }
1785}
1786
1787
1788/* Called only as a scheduled task for pending AP frames. */
1789static void ap_handle_data_nullfunc(local_info_t *local,
1790 struct ieee80211_hdr *hdr)
1791{
1792 struct net_device *dev = local->dev;
1793
1794 /* some STA f/w's seem to require control::ACK frame for
1795 * data::nullfunc, but at least Prism2 station f/w version 0.8.0 does
1796 * not send this..
1797 * send control::ACK for the data::nullfunc */
1798
1799 printk(KERN_DEBUG "Sending control::ACK for data::nullfunc\n");
1800 prism2_send_mgmt(dev, IEEE80211_FTYPE_CTL | IEEE80211_STYPE_ACK,
1801 NULL, 0, hdr->addr2, 0);
1802}
1803
1804
1805/* Called only as a scheduled task for pending AP frames. */
1806static void ap_handle_dropped_data(local_info_t *local,
1807 struct ieee80211_hdr *hdr)
1808{
1809 struct net_device *dev = local->dev;
1810 struct sta_info *sta;
1811 __le16 reason;
1812
1813 spin_lock_bh(&local->ap->sta_table_lock);
1814 sta = ap_get_sta(local->ap, hdr->addr2);
1815 if (sta)
1816 atomic_inc(&sta->users);
1817 spin_unlock_bh(&local->ap->sta_table_lock);
1818
1819 if (sta != NULL && (sta->flags & WLAN_STA_ASSOC)) {
1820 PDEBUG(DEBUG_AP, "ap_handle_dropped_data: STA is now okay?\n");
1821 atomic_dec(&sta->users);
1822 return;
1823 }
1824
1825 reason = cpu_to_le16(WLAN_REASON_CLASS3_FRAME_FROM_NONASSOC_STA);
1826 prism2_send_mgmt(dev, IEEE80211_FTYPE_MGMT |
1827 ((sta == NULL || !(sta->flags & WLAN_STA_ASSOC)) ?
1828 IEEE80211_STYPE_DEAUTH : IEEE80211_STYPE_DISASSOC),
1829 (char *) &reason, sizeof(reason), hdr->addr2, 0);
1830
1831 if (sta)
1832 atomic_dec(&sta->users);
1833}
1834
1835#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
1836
1837
1838/* Called only as a scheduled task for pending AP frames. */
1839static void pspoll_send_buffered(local_info_t *local, struct sta_info *sta,
1840 struct sk_buff *skb)
1841{
1842 struct hostap_skb_tx_data *meta;
1843
1844 if (!(sta->flags & WLAN_STA_PS)) {
1845 /* Station has moved to non-PS mode, so send all buffered
1846 * frames using normal device queue. */
1847 dev_queue_xmit(skb);
1848 return;
1849 }
1850
1851 /* add a flag for hostap_handle_sta_tx() to know that this skb should
1852 * be passed through even though STA is using PS */
1853 meta = (struct hostap_skb_tx_data *) skb->cb;
1854 meta->flags |= HOSTAP_TX_FLAGS_BUFFERED_FRAME;
1855 if (!skb_queue_empty(&sta->tx_buf)) {
1856 /* indicate to STA that more frames follow */
1857 meta->flags |= HOSTAP_TX_FLAGS_ADD_MOREDATA;
1858 }
1859 dev_queue_xmit(skb);
1860}
1861
1862
1863/* Called only as a scheduled task for pending AP frames. */
1864static void handle_pspoll(local_info_t *local,
1865 struct ieee80211_hdr *hdr,
1866 struct hostap_80211_rx_status *rx_stats)
1867{
1868 struct net_device *dev = local->dev;
1869 struct sta_info *sta;
1870 u16 aid;
1871 struct sk_buff *skb;
1872
1873 PDEBUG(DEBUG_PS2, "handle_pspoll: BSSID=%pM, TA=%pM PWRMGT=%d\n",
1874 hdr->addr1, hdr->addr2, !!ieee80211_has_pm(hdr->frame_control));
1875
1876 if (!ether_addr_equal(hdr->addr1, dev->dev_addr)) {
1877 PDEBUG(DEBUG_AP,
1878 "handle_pspoll - addr1(BSSID)=%pM not own MAC\n",
1879 hdr->addr1);
1880 return;
1881 }
1882
1883 aid = le16_to_cpu(hdr->duration_id);
1884 if ((aid & (BIT(15) | BIT(14))) != (BIT(15) | BIT(14))) {
1885 PDEBUG(DEBUG_PS, " PSPOLL and AID[15:14] not set\n");
1886 return;
1887 }
1888 aid &= ~(BIT(15) | BIT(14));
1889 if (aid == 0 || aid > MAX_AID_TABLE_SIZE) {
1890 PDEBUG(DEBUG_PS, " invalid aid=%d\n", aid);
1891 return;
1892 }
1893 PDEBUG(DEBUG_PS2, " aid=%d\n", aid);
1894
1895 spin_lock_bh(&local->ap->sta_table_lock);
1896 sta = ap_get_sta(local->ap, hdr->addr2);
1897 if (sta)
1898 atomic_inc(&sta->users);
1899 spin_unlock_bh(&local->ap->sta_table_lock);
1900
1901 if (sta == NULL) {
1902 PDEBUG(DEBUG_PS, " STA not found\n");
1903 return;
1904 }
1905 if (sta->aid != aid) {
1906 PDEBUG(DEBUG_PS, " received aid=%i does not match with "
1907 "assoc.aid=%d\n", aid, sta->aid);
1908 return;
1909 }
1910
1911 /* FIX: todo:
1912 * - add timeout for buffering (clear aid in TIM vector if buffer timed
1913 * out (expiry time must be longer than ListenInterval for
1914 * the corresponding STA; "8802-11: 11.2.1.9 AP aging function"
1915 * - what to do, if buffered, pspolled, and sent frame is not ACKed by
1916 * sta; store buffer for later use and leave TIM aid bit set? use
1917 * TX event to check whether frame was ACKed?
1918 */
1919
1920 while ((skb = skb_dequeue(&sta->tx_buf)) != NULL) {
1921 /* send buffered frame .. */
1922 PDEBUG(DEBUG_PS2, "Sending buffered frame to STA after PS POLL"
1923 " (buffer_count=%d)\n", skb_queue_len(&sta->tx_buf));
1924
1925 pspoll_send_buffered(local, sta, skb);
1926
1927 if (sta->flags & WLAN_STA_PS) {
1928 /* send only one buffered packet per PS Poll */
1929 /* FIX: should ignore further PS Polls until the
1930 * buffered packet that was just sent is acknowledged
1931 * (Tx or TxExc event) */
1932 break;
1933 }
1934 }
1935
1936 if (skb_queue_empty(&sta->tx_buf)) {
1937 /* try to clear aid from TIM */
1938 if (!(sta->flags & WLAN_STA_TIM))
1939 PDEBUG(DEBUG_PS2, "Re-unsetting TIM for aid %d\n",
1940 aid);
1941 hostap_set_tim(local, aid, 0);
1942 sta->flags &= ~WLAN_STA_TIM;
1943 }
1944
1945 atomic_dec(&sta->users);
1946}
1947
1948
1949#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
1950
1951static void handle_wds_oper_queue(struct work_struct *work)
1952{
1953 struct ap_data *ap = container_of(work, struct ap_data,
1954 wds_oper_queue);
1955 local_info_t *local = ap->local;
1956 struct wds_oper_data *entry, *prev;
1957
1958 spin_lock_bh(&local->lock);
1959 entry = local->ap->wds_oper_entries;
1960 local->ap->wds_oper_entries = NULL;
1961 spin_unlock_bh(&local->lock);
1962
1963 while (entry) {
1964 PDEBUG(DEBUG_AP, "%s: %s automatic WDS connection "
1965 "to AP %pM\n",
1966 local->dev->name,
1967 entry->type == WDS_ADD ? "adding" : "removing",
1968 entry->addr);
1969 if (entry->type == WDS_ADD)
1970 prism2_wds_add(local, entry->addr, 0);
1971 else if (entry->type == WDS_DEL)
1972 prism2_wds_del(local, entry->addr, 0, 1);
1973
1974 prev = entry;
1975 entry = entry->next;
1976 kfree(prev);
1977 }
1978}
1979
1980
1981/* Called only as a scheduled task for pending AP frames. */
1982static void handle_beacon(local_info_t *local, struct sk_buff *skb,
1983 struct hostap_80211_rx_status *rx_stats)
1984{
1985 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data;
1986 char *body = skb->data + IEEE80211_MGMT_HDR_LEN;
1987 int len, left;
1988 u16 beacon_int, capability;
1989 __le16 *pos;
1990 char *ssid = NULL;
1991 unsigned char *supp_rates = NULL;
1992 int ssid_len = 0, supp_rates_len = 0;
1993 struct sta_info *sta = NULL;
1994 int new_sta = 0, channel = -1;
1995
1996 len = skb->len - IEEE80211_MGMT_HDR_LEN;
1997
1998 if (len < 8 + 2 + 2) {
1999 printk(KERN_DEBUG "handle_beacon - too short payload "
2000 "(len=%d)\n", len);
2001 return;
2002 }
2003
2004 pos = (__le16 *) body;
2005 left = len;
2006
2007 /* Timestamp (8 octets) */
2008 pos += 4; left -= 8;
2009 /* Beacon interval (2 octets) */
2010 beacon_int = le16_to_cpu(*pos);
2011 pos++; left -= 2;
2012 /* Capability information (2 octets) */
2013 capability = le16_to_cpu(*pos);
2014 pos++; left -= 2;
2015
2016 if (local->ap->ap_policy != AP_OTHER_AP_EVEN_IBSS &&
2017 capability & WLAN_CAPABILITY_IBSS)
2018 return;
2019
2020 if (left >= 2) {
2021 unsigned int ileft;
2022 unsigned char *u = (unsigned char *) pos;
2023
2024 if (*u == WLAN_EID_SSID) {
2025 u++; left--;
2026 ileft = *u;
2027 u++; left--;
2028
2029 if (ileft > left || ileft > MAX_SSID_LEN) {
2030 PDEBUG(DEBUG_AP, "SSID: overflow\n");
2031 return;
2032 }
2033
2034 if (local->ap->ap_policy == AP_OTHER_AP_SAME_SSID &&
2035 (ileft != strlen(local->essid) ||
2036 memcmp(local->essid, u, ileft) != 0)) {
2037 /* not our SSID */
2038 return;
2039 }
2040
2041 ssid = u;
2042 ssid_len = ileft;
2043
2044 u += ileft;
2045 left -= ileft;
2046 }
2047
2048 if (*u == WLAN_EID_SUPP_RATES) {
2049 u++; left--;
2050 ileft = *u;
2051 u++; left--;
2052
2053 if (ileft > left || ileft == 0 || ileft > 8) {
2054 PDEBUG(DEBUG_AP, " - SUPP_RATES len error\n");
2055 return;
2056 }
2057
2058 supp_rates = u;
2059 supp_rates_len = ileft;
2060
2061 u += ileft;
2062 left -= ileft;
2063 }
2064
2065 if (*u == WLAN_EID_DS_PARAMS) {
2066 u++; left--;
2067 ileft = *u;
2068 u++; left--;
2069
2070 if (ileft > left || ileft != 1) {
2071 PDEBUG(DEBUG_AP, " - DS_PARAMS len error\n");
2072 return;
2073 }
2074
2075 channel = *u;
2076
2077 u += ileft;
2078 left -= ileft;
2079 }
2080 }
2081
2082 spin_lock_bh(&local->ap->sta_table_lock);
2083 sta = ap_get_sta(local->ap, hdr->addr2);
2084 if (sta != NULL)
2085 atomic_inc(&sta->users);
2086 spin_unlock_bh(&local->ap->sta_table_lock);
2087
2088 if (sta == NULL) {
2089 /* add new AP */
2090 new_sta = 1;
2091 sta = ap_add_sta(local->ap, hdr->addr2);
2092 if (sta == NULL) {
2093 printk(KERN_INFO "prism2: kmalloc failed for AP "
2094 "data structure\n");
2095 return;
2096 }
2097 hostap_event_new_sta(local->dev, sta);
2098
2099 /* mark APs authentication and associated for pseudo ad-hoc
2100 * style communication */
2101 sta->flags = WLAN_STA_AUTH | WLAN_STA_ASSOC;
2102
2103 if (local->ap->autom_ap_wds) {
2104 hostap_wds_link_oper(local, sta->addr, WDS_ADD);
2105 }
2106 }
2107
2108 sta->ap = 1;
2109 if (ssid) {
2110 sta->u.ap.ssid_len = ssid_len;
2111 memcpy(sta->u.ap.ssid, ssid, ssid_len);
2112 sta->u.ap.ssid[ssid_len] = '\0';
2113 } else {
2114 sta->u.ap.ssid_len = 0;
2115 sta->u.ap.ssid[0] = '\0';
2116 }
2117 sta->u.ap.channel = channel;
2118 sta->rx_packets++;
2119 sta->rx_bytes += len;
2120 sta->u.ap.last_beacon = sta->last_rx = jiffies;
2121 sta->capability = capability;
2122 sta->listen_interval = beacon_int;
2123
2124 atomic_dec(&sta->users);
2125
2126 if (new_sta) {
2127 memset(sta->supported_rates, 0, sizeof(sta->supported_rates));
2128 memcpy(sta->supported_rates, supp_rates, supp_rates_len);
2129 prism2_check_tx_rates(sta);
2130 }
2131}
2132
2133#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
2134
2135
2136/* Called only as a tasklet. */
2137static void handle_ap_item(local_info_t *local, struct sk_buff *skb,
2138 struct hostap_80211_rx_status *rx_stats)
2139{
2140#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
2141 struct net_device *dev = local->dev;
2142#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
2143 u16 fc, type, stype;
2144 struct ieee80211_hdr *hdr;
2145
2146 /* FIX: should give skb->len to handler functions and check that the
2147 * buffer is long enough */
2148 hdr = (struct ieee80211_hdr *) skb->data;
2149 fc = le16_to_cpu(hdr->frame_control);
2150 type = fc & IEEE80211_FCTL_FTYPE;
2151 stype = fc & IEEE80211_FCTL_STYPE;
2152
2153#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
2154 if (!local->hostapd && type == IEEE80211_FTYPE_DATA) {
2155 PDEBUG(DEBUG_AP, "handle_ap_item - data frame\n");
2156
2157 if (!(fc & IEEE80211_FCTL_TODS) ||
2158 (fc & IEEE80211_FCTL_FROMDS)) {
2159 if (stype == IEEE80211_STYPE_NULLFUNC) {
2160 /* no ToDS nullfunc seems to be used to check
2161 * AP association; so send reject message to
2162 * speed up re-association */
2163 ap_handle_dropped_data(local, hdr);
2164 goto done;
2165 }
2166 PDEBUG(DEBUG_AP, " not ToDS frame (fc=0x%04x)\n",
2167 fc);
2168 goto done;
2169 }
2170
2171 if (!ether_addr_equal(hdr->addr1, dev->dev_addr)) {
2172 PDEBUG(DEBUG_AP, "handle_ap_item - addr1(BSSID)=%pM"
2173 " not own MAC\n", hdr->addr1);
2174 goto done;
2175 }
2176
2177 if (local->ap->nullfunc_ack &&
2178 stype == IEEE80211_STYPE_NULLFUNC)
2179 ap_handle_data_nullfunc(local, hdr);
2180 else
2181 ap_handle_dropped_data(local, hdr);
2182 goto done;
2183 }
2184
2185 if (type == IEEE80211_FTYPE_MGMT && stype == IEEE80211_STYPE_BEACON) {
2186 handle_beacon(local, skb, rx_stats);
2187 goto done;
2188 }
2189#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
2190
2191 if (type == IEEE80211_FTYPE_CTL && stype == IEEE80211_STYPE_PSPOLL) {
2192 handle_pspoll(local, hdr, rx_stats);
2193 goto done;
2194 }
2195
2196 if (local->hostapd) {
2197 PDEBUG(DEBUG_AP, "Unknown frame in AP queue: type=0x%02x "
2198 "subtype=0x%02x\n", type, stype);
2199 goto done;
2200 }
2201
2202#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
2203 if (type != IEEE80211_FTYPE_MGMT) {
2204 PDEBUG(DEBUG_AP, "handle_ap_item - not a management frame?\n");
2205 goto done;
2206 }
2207
2208 if (!ether_addr_equal(hdr->addr1, dev->dev_addr)) {
2209 PDEBUG(DEBUG_AP, "handle_ap_item - addr1(DA)=%pM"
2210 " not own MAC\n", hdr->addr1);
2211 goto done;
2212 }
2213
2214 if (!ether_addr_equal(hdr->addr3, dev->dev_addr)) {
2215 PDEBUG(DEBUG_AP, "handle_ap_item - addr3(BSSID)=%pM"
2216 " not own MAC\n", hdr->addr3);
2217 goto done;
2218 }
2219
2220 switch (stype) {
2221 case IEEE80211_STYPE_ASSOC_REQ:
2222 handle_assoc(local, skb, rx_stats, 0);
2223 break;
2224 case IEEE80211_STYPE_ASSOC_RESP:
2225 PDEBUG(DEBUG_AP, "==> ASSOC RESP (ignored)\n");
2226 break;
2227 case IEEE80211_STYPE_REASSOC_REQ:
2228 handle_assoc(local, skb, rx_stats, 1);
2229 break;
2230 case IEEE80211_STYPE_REASSOC_RESP:
2231 PDEBUG(DEBUG_AP, "==> REASSOC RESP (ignored)\n");
2232 break;
2233 case IEEE80211_STYPE_ATIM:
2234 PDEBUG(DEBUG_AP, "==> ATIM (ignored)\n");
2235 break;
2236 case IEEE80211_STYPE_DISASSOC:
2237 handle_disassoc(local, skb, rx_stats);
2238 break;
2239 case IEEE80211_STYPE_AUTH:
2240 handle_authen(local, skb, rx_stats);
2241 break;
2242 case IEEE80211_STYPE_DEAUTH:
2243 handle_deauth(local, skb, rx_stats);
2244 break;
2245 default:
2246 PDEBUG(DEBUG_AP, "Unknown mgmt frame subtype 0x%02x\n",
2247 stype >> 4);
2248 break;
2249 }
2250#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
2251
2252 done:
2253 dev_kfree_skb(skb);
2254}
2255
2256
2257/* Called only as a tasklet (software IRQ) */
2258void hostap_rx(struct net_device *dev, struct sk_buff *skb,
2259 struct hostap_80211_rx_status *rx_stats)
2260{
2261 struct hostap_interface *iface;
2262 local_info_t *local;
2263 struct ieee80211_hdr *hdr;
2264
2265 iface = netdev_priv(dev);
2266 local = iface->local;
2267
2268 if (skb->len < 16)
2269 goto drop;
2270
2271 dev->stats.rx_packets++;
2272
2273 hdr = (struct ieee80211_hdr *) skb->data;
2274
2275 if (local->ap->ap_policy == AP_OTHER_AP_SKIP_ALL &&
2276 ieee80211_is_beacon(hdr->frame_control))
2277 goto drop;
2278
2279 skb->protocol = cpu_to_be16(ETH_P_HOSTAP);
2280 handle_ap_item(local, skb, rx_stats);
2281 return;
2282
2283 drop:
2284 dev_kfree_skb(skb);
2285}
2286
2287
2288/* Called only as a tasklet (software IRQ) */
2289static void schedule_packet_send(local_info_t *local, struct sta_info *sta)
2290{
2291 struct sk_buff *skb;
2292 struct ieee80211_hdr *hdr;
2293 struct hostap_80211_rx_status rx_stats;
2294
2295 if (skb_queue_empty(&sta->tx_buf))
2296 return;
2297
2298 skb = dev_alloc_skb(16);
2299 if (skb == NULL) {
2300 printk(KERN_DEBUG "%s: schedule_packet_send: skb alloc "
2301 "failed\n", local->dev->name);
2302 return;
2303 }
2304
2305 hdr = skb_put(skb, 16);
2306
2307 /* Generate a fake pspoll frame to start packet delivery */
2308 hdr->frame_control = cpu_to_le16(
2309 IEEE80211_FTYPE_CTL | IEEE80211_STYPE_PSPOLL);
2310 memcpy(hdr->addr1, local->dev->dev_addr, ETH_ALEN);
2311 memcpy(hdr->addr2, sta->addr, ETH_ALEN);
2312 hdr->duration_id = cpu_to_le16(sta->aid | BIT(15) | BIT(14));
2313
2314 PDEBUG(DEBUG_PS2,
2315 "%s: Scheduling buffered packet delivery for STA %pM\n",
2316 local->dev->name, sta->addr);
2317
2318 skb->dev = local->dev;
2319
2320 memset(&rx_stats, 0, sizeof(rx_stats));
2321 hostap_rx(local->dev, skb, &rx_stats);
2322}
2323
2324
2325int prism2_ap_get_sta_qual(local_info_t *local, struct sockaddr addr[],
2326 struct iw_quality qual[], int buf_size,
2327 int aplist)
2328{
2329 struct ap_data *ap = local->ap;
2330 struct list_head *ptr;
2331 int count = 0;
2332
2333 spin_lock_bh(&ap->sta_table_lock);
2334
2335 for (ptr = ap->sta_list.next; ptr != NULL && ptr != &ap->sta_list;
2336 ptr = ptr->next) {
2337 struct sta_info *sta = (struct sta_info *) ptr;
2338
2339 if (aplist && !sta->ap)
2340 continue;
2341 addr[count].sa_family = ARPHRD_ETHER;
2342 memcpy(addr[count].sa_data, sta->addr, ETH_ALEN);
2343 if (sta->last_rx_silence == 0)
2344 qual[count].qual = sta->last_rx_signal < 27 ?
2345 0 : (sta->last_rx_signal - 27) * 92 / 127;
2346 else
2347 qual[count].qual = sta->last_rx_signal -
2348 sta->last_rx_silence - 35;
2349 qual[count].level = HFA384X_LEVEL_TO_dBm(sta->last_rx_signal);
2350 qual[count].noise = HFA384X_LEVEL_TO_dBm(sta->last_rx_silence);
2351 qual[count].updated = sta->last_rx_updated;
2352
2353 sta->last_rx_updated = IW_QUAL_DBM;
2354
2355 count++;
2356 if (count >= buf_size)
2357 break;
2358 }
2359 spin_unlock_bh(&ap->sta_table_lock);
2360
2361 return count;
2362}
2363
2364
2365/* Translate our list of Access Points & Stations to a card independent
2366 * format that the Wireless Tools will understand - Jean II */
2367int prism2_ap_translate_scan(struct net_device *dev,
2368 struct iw_request_info *info, char *buffer)
2369{
2370 struct hostap_interface *iface;
2371 local_info_t *local;
2372 struct ap_data *ap;
2373 struct list_head *ptr;
2374 struct iw_event iwe;
2375 char *current_ev = buffer;
2376 char *end_buf = buffer + IW_SCAN_MAX_DATA;
2377#if !defined(PRISM2_NO_KERNEL_IEEE80211_MGMT)
2378 char buf[64];
2379#endif
2380
2381 iface = netdev_priv(dev);
2382 local = iface->local;
2383 ap = local->ap;
2384
2385 spin_lock_bh(&ap->sta_table_lock);
2386
2387 for (ptr = ap->sta_list.next; ptr != NULL && ptr != &ap->sta_list;
2388 ptr = ptr->next) {
2389 struct sta_info *sta = (struct sta_info *) ptr;
2390
2391 /* First entry *MUST* be the AP MAC address */
2392 memset(&iwe, 0, sizeof(iwe));
2393 iwe.cmd = SIOCGIWAP;
2394 iwe.u.ap_addr.sa_family = ARPHRD_ETHER;
2395 memcpy(iwe.u.ap_addr.sa_data, sta->addr, ETH_ALEN);
2396 iwe.len = IW_EV_ADDR_LEN;
2397 current_ev = iwe_stream_add_event(info, current_ev, end_buf,
2398 &iwe, IW_EV_ADDR_LEN);
2399
2400 /* Use the mode to indicate if it's a station or
2401 * an Access Point */
2402 memset(&iwe, 0, sizeof(iwe));
2403 iwe.cmd = SIOCGIWMODE;
2404 if (sta->ap)
2405 iwe.u.mode = IW_MODE_MASTER;
2406 else
2407 iwe.u.mode = IW_MODE_INFRA;
2408 iwe.len = IW_EV_UINT_LEN;
2409 current_ev = iwe_stream_add_event(info, current_ev, end_buf,
2410 &iwe, IW_EV_UINT_LEN);
2411
2412 /* Some quality */
2413 memset(&iwe, 0, sizeof(iwe));
2414 iwe.cmd = IWEVQUAL;
2415 if (sta->last_rx_silence == 0)
2416 iwe.u.qual.qual = sta->last_rx_signal < 27 ?
2417 0 : (sta->last_rx_signal - 27) * 92 / 127;
2418 else
2419 iwe.u.qual.qual = sta->last_rx_signal -
2420 sta->last_rx_silence - 35;
2421 iwe.u.qual.level = HFA384X_LEVEL_TO_dBm(sta->last_rx_signal);
2422 iwe.u.qual.noise = HFA384X_LEVEL_TO_dBm(sta->last_rx_silence);
2423 iwe.u.qual.updated = sta->last_rx_updated;
2424 iwe.len = IW_EV_QUAL_LEN;
2425 current_ev = iwe_stream_add_event(info, current_ev, end_buf,
2426 &iwe, IW_EV_QUAL_LEN);
2427
2428#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
2429 if (sta->ap) {
2430 memset(&iwe, 0, sizeof(iwe));
2431 iwe.cmd = SIOCGIWESSID;
2432 iwe.u.data.length = sta->u.ap.ssid_len;
2433 iwe.u.data.flags = 1;
2434 current_ev = iwe_stream_add_point(info, current_ev,
2435 end_buf, &iwe,
2436 sta->u.ap.ssid);
2437
2438 memset(&iwe, 0, sizeof(iwe));
2439 iwe.cmd = SIOCGIWENCODE;
2440 if (sta->capability & WLAN_CAPABILITY_PRIVACY)
2441 iwe.u.data.flags =
2442 IW_ENCODE_ENABLED | IW_ENCODE_NOKEY;
2443 else
2444 iwe.u.data.flags = IW_ENCODE_DISABLED;
2445 current_ev = iwe_stream_add_point(info, current_ev,
2446 end_buf, &iwe,
2447 sta->u.ap.ssid);
2448
2449 if (sta->u.ap.channel > 0 &&
2450 sta->u.ap.channel <= FREQ_COUNT) {
2451 memset(&iwe, 0, sizeof(iwe));
2452 iwe.cmd = SIOCGIWFREQ;
2453 iwe.u.freq.m = freq_list[sta->u.ap.channel - 1]
2454 * 100000;
2455 iwe.u.freq.e = 1;
2456 current_ev = iwe_stream_add_event(
2457 info, current_ev, end_buf, &iwe,
2458 IW_EV_FREQ_LEN);
2459 }
2460
2461 memset(&iwe, 0, sizeof(iwe));
2462 iwe.cmd = IWEVCUSTOM;
2463 sprintf(buf, "beacon_interval=%d",
2464 sta->listen_interval);
2465 iwe.u.data.length = strlen(buf);
2466 current_ev = iwe_stream_add_point(info, current_ev,
2467 end_buf, &iwe, buf);
2468 }
2469#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
2470
2471 sta->last_rx_updated = IW_QUAL_DBM;
2472
2473 /* To be continued, we should make good use of IWEVCUSTOM */
2474 }
2475
2476 spin_unlock_bh(&ap->sta_table_lock);
2477
2478 return current_ev - buffer;
2479}
2480
2481
2482static int prism2_hostapd_add_sta(struct ap_data *ap,
2483 struct prism2_hostapd_param *param)
2484{
2485 struct sta_info *sta;
2486
2487 spin_lock_bh(&ap->sta_table_lock);
2488 sta = ap_get_sta(ap, param->sta_addr);
2489 if (sta)
2490 atomic_inc(&sta->users);
2491 spin_unlock_bh(&ap->sta_table_lock);
2492
2493 if (sta == NULL) {
2494 sta = ap_add_sta(ap, param->sta_addr);
2495 if (sta == NULL)
2496 return -1;
2497 }
2498
2499 if (!(sta->flags & WLAN_STA_ASSOC) && !sta->ap && sta->local)
2500 hostap_event_new_sta(sta->local->dev, sta);
2501
2502 sta->flags |= WLAN_STA_AUTH | WLAN_STA_ASSOC;
2503 sta->last_rx = jiffies;
2504 sta->aid = param->u.add_sta.aid;
2505 sta->capability = param->u.add_sta.capability;
2506 sta->tx_supp_rates = param->u.add_sta.tx_supp_rates;
2507 if (sta->tx_supp_rates & WLAN_RATE_1M)
2508 sta->supported_rates[0] = 2;
2509 if (sta->tx_supp_rates & WLAN_RATE_2M)
2510 sta->supported_rates[1] = 4;
2511 if (sta->tx_supp_rates & WLAN_RATE_5M5)
2512 sta->supported_rates[2] = 11;
2513 if (sta->tx_supp_rates & WLAN_RATE_11M)
2514 sta->supported_rates[3] = 22;
2515 prism2_check_tx_rates(sta);
2516 atomic_dec(&sta->users);
2517 return 0;
2518}
2519
2520
2521static int prism2_hostapd_remove_sta(struct ap_data *ap,
2522 struct prism2_hostapd_param *param)
2523{
2524 struct sta_info *sta;
2525
2526 spin_lock_bh(&ap->sta_table_lock);
2527 sta = ap_get_sta(ap, param->sta_addr);
2528 if (sta) {
2529 ap_sta_hash_del(ap, sta);
2530 list_del(&sta->list);
2531 }
2532 spin_unlock_bh(&ap->sta_table_lock);
2533
2534 if (!sta)
2535 return -ENOENT;
2536
2537 if ((sta->flags & WLAN_STA_ASSOC) && !sta->ap && sta->local)
2538 hostap_event_expired_sta(sta->local->dev, sta);
2539 ap_free_sta(ap, sta);
2540
2541 return 0;
2542}
2543
2544
2545static int prism2_hostapd_get_info_sta(struct ap_data *ap,
2546 struct prism2_hostapd_param *param)
2547{
2548 struct sta_info *sta;
2549
2550 spin_lock_bh(&ap->sta_table_lock);
2551 sta = ap_get_sta(ap, param->sta_addr);
2552 if (sta)
2553 atomic_inc(&sta->users);
2554 spin_unlock_bh(&ap->sta_table_lock);
2555
2556 if (!sta)
2557 return -ENOENT;
2558
2559 param->u.get_info_sta.inactive_sec = (jiffies - sta->last_rx) / HZ;
2560
2561 atomic_dec(&sta->users);
2562
2563 return 1;
2564}
2565
2566
2567static int prism2_hostapd_set_flags_sta(struct ap_data *ap,
2568 struct prism2_hostapd_param *param)
2569{
2570 struct sta_info *sta;
2571
2572 spin_lock_bh(&ap->sta_table_lock);
2573 sta = ap_get_sta(ap, param->sta_addr);
2574 if (sta) {
2575 sta->flags |= param->u.set_flags_sta.flags_or;
2576 sta->flags &= param->u.set_flags_sta.flags_and;
2577 }
2578 spin_unlock_bh(&ap->sta_table_lock);
2579
2580 if (!sta)
2581 return -ENOENT;
2582
2583 return 0;
2584}
2585
2586
2587static int prism2_hostapd_sta_clear_stats(struct ap_data *ap,
2588 struct prism2_hostapd_param *param)
2589{
2590 struct sta_info *sta;
2591 int rate;
2592
2593 spin_lock_bh(&ap->sta_table_lock);
2594 sta = ap_get_sta(ap, param->sta_addr);
2595 if (sta) {
2596 sta->rx_packets = sta->tx_packets = 0;
2597 sta->rx_bytes = sta->tx_bytes = 0;
2598 for (rate = 0; rate < WLAN_RATE_COUNT; rate++) {
2599 sta->tx_count[rate] = 0;
2600 sta->rx_count[rate] = 0;
2601 }
2602 }
2603 spin_unlock_bh(&ap->sta_table_lock);
2604
2605 if (!sta)
2606 return -ENOENT;
2607
2608 return 0;
2609}
2610
2611
2612int prism2_hostapd(struct ap_data *ap, struct prism2_hostapd_param *param)
2613{
2614 switch (param->cmd) {
2615 case PRISM2_HOSTAPD_FLUSH:
2616 ap_control_kickall(ap);
2617 return 0;
2618 case PRISM2_HOSTAPD_ADD_STA:
2619 return prism2_hostapd_add_sta(ap, param);
2620 case PRISM2_HOSTAPD_REMOVE_STA:
2621 return prism2_hostapd_remove_sta(ap, param);
2622 case PRISM2_HOSTAPD_GET_INFO_STA:
2623 return prism2_hostapd_get_info_sta(ap, param);
2624 case PRISM2_HOSTAPD_SET_FLAGS_STA:
2625 return prism2_hostapd_set_flags_sta(ap, param);
2626 case PRISM2_HOSTAPD_STA_CLEAR_STATS:
2627 return prism2_hostapd_sta_clear_stats(ap, param);
2628 default:
2629 printk(KERN_WARNING "prism2_hostapd: unknown cmd=%d\n",
2630 param->cmd);
2631 return -EOPNOTSUPP;
2632 }
2633}
2634
2635
2636/* Update station info for host-based TX rate control and return current
2637 * TX rate */
2638static int ap_update_sta_tx_rate(struct sta_info *sta, struct net_device *dev)
2639{
2640 int ret = sta->tx_rate;
2641 struct hostap_interface *iface;
2642 local_info_t *local;
2643
2644 iface = netdev_priv(dev);
2645 local = iface->local;
2646
2647 sta->tx_count[sta->tx_rate_idx]++;
2648 sta->tx_since_last_failure++;
2649 sta->tx_consecutive_exc = 0;
2650 if (sta->tx_since_last_failure >= WLAN_RATE_UPDATE_COUNT &&
2651 sta->tx_rate_idx < sta->tx_max_rate) {
2652 /* use next higher rate */
2653 int old_rate, new_rate;
2654 old_rate = new_rate = sta->tx_rate_idx;
2655 while (new_rate < sta->tx_max_rate) {
2656 new_rate++;
2657 if (ap_tx_rate_ok(new_rate, sta, local)) {
2658 sta->tx_rate_idx = new_rate;
2659 break;
2660 }
2661 }
2662 if (old_rate != sta->tx_rate_idx) {
2663 switch (sta->tx_rate_idx) {
2664 case 0: sta->tx_rate = 10; break;
2665 case 1: sta->tx_rate = 20; break;
2666 case 2: sta->tx_rate = 55; break;
2667 case 3: sta->tx_rate = 110; break;
2668 default: sta->tx_rate = 0; break;
2669 }
2670 PDEBUG(DEBUG_AP, "%s: STA %pM TX rate raised to %d\n",
2671 dev->name, sta->addr, sta->tx_rate);
2672 }
2673 sta->tx_since_last_failure = 0;
2674 }
2675
2676 return ret;
2677}
2678
2679
2680/* Called only from software IRQ. Called for each TX frame prior possible
2681 * encryption and transmit. */
2682ap_tx_ret hostap_handle_sta_tx(local_info_t *local, struct hostap_tx_data *tx)
2683{
2684 struct sta_info *sta = NULL;
2685 struct sk_buff *skb = tx->skb;
2686 int set_tim, ret;
2687 struct ieee80211_hdr *hdr;
2688 struct hostap_skb_tx_data *meta;
2689
2690 meta = (struct hostap_skb_tx_data *) skb->cb;
2691 ret = AP_TX_CONTINUE;
2692 if (local->ap == NULL || skb->len < 10 ||
2693 meta->iface->type == HOSTAP_INTERFACE_STA)
2694 goto out;
2695
2696 hdr = (struct ieee80211_hdr *) skb->data;
2697
2698 if (hdr->addr1[0] & 0x01) {
2699 /* broadcast/multicast frame - no AP related processing */
2700 if (local->ap->num_sta <= 0)
2701 ret = AP_TX_DROP;
2702 goto out;
2703 }
2704
2705 /* unicast packet - check whether destination STA is associated */
2706 spin_lock(&local->ap->sta_table_lock);
2707 sta = ap_get_sta(local->ap, hdr->addr1);
2708 if (sta)
2709 atomic_inc(&sta->users);
2710 spin_unlock(&local->ap->sta_table_lock);
2711
2712 if (local->iw_mode == IW_MODE_MASTER && sta == NULL &&
2713 !(meta->flags & HOSTAP_TX_FLAGS_WDS) &&
2714 meta->iface->type != HOSTAP_INTERFACE_MASTER &&
2715 meta->iface->type != HOSTAP_INTERFACE_AP) {
2716#if 0
2717 /* This can happen, e.g., when wlan0 is added to a bridge and
2718 * bridging code does not know which port is the correct target
2719 * for a unicast frame. In this case, the packet is send to all
2720 * ports of the bridge. Since this is a valid scenario, do not
2721 * print out any errors here. */
2722 if (net_ratelimit()) {
2723 printk(KERN_DEBUG "AP: drop packet to non-associated "
2724 "STA %pM\n", hdr->addr1);
2725 }
2726#endif
2727 local->ap->tx_drop_nonassoc++;
2728 ret = AP_TX_DROP;
2729 goto out;
2730 }
2731
2732 if (sta == NULL)
2733 goto out;
2734
2735 if (!(sta->flags & WLAN_STA_AUTHORIZED))
2736 ret = AP_TX_CONTINUE_NOT_AUTHORIZED;
2737
2738 /* Set tx_rate if using host-based TX rate control */
2739 if (!local->fw_tx_rate_control)
2740 local->ap->last_tx_rate = meta->rate =
2741 ap_update_sta_tx_rate(sta, local->dev);
2742
2743 if (local->iw_mode != IW_MODE_MASTER)
2744 goto out;
2745
2746 if (!(sta->flags & WLAN_STA_PS))
2747 goto out;
2748
2749 if (meta->flags & HOSTAP_TX_FLAGS_ADD_MOREDATA) {
2750 /* indicate to STA that more frames follow */
2751 hdr->frame_control |=
2752 cpu_to_le16(IEEE80211_FCTL_MOREDATA);
2753 }
2754
2755 if (meta->flags & HOSTAP_TX_FLAGS_BUFFERED_FRAME) {
2756 /* packet was already buffered and now send due to
2757 * PS poll, so do not rebuffer it */
2758 goto out;
2759 }
2760
2761 if (skb_queue_len(&sta->tx_buf) >= STA_MAX_TX_BUFFER) {
2762 PDEBUG(DEBUG_PS, "%s: No more space in STA (%pM)'s"
2763 "PS mode buffer\n",
2764 local->dev->name, sta->addr);
2765 /* Make sure that TIM is set for the station (it might not be
2766 * after AP wlan hw reset). */
2767 /* FIX: should fix hw reset to restore bits based on STA
2768 * buffer state.. */
2769 hostap_set_tim(local, sta->aid, 1);
2770 sta->flags |= WLAN_STA_TIM;
2771 ret = AP_TX_DROP;
2772 goto out;
2773 }
2774
2775 /* STA in PS mode, buffer frame for later delivery */
2776 set_tim = skb_queue_empty(&sta->tx_buf);
2777 skb_queue_tail(&sta->tx_buf, skb);
2778 /* FIX: could save RX time to skb and expire buffered frames after
2779 * some time if STA does not poll for them */
2780
2781 if (set_tim) {
2782 if (sta->flags & WLAN_STA_TIM)
2783 PDEBUG(DEBUG_PS2, "Re-setting TIM for aid %d\n",
2784 sta->aid);
2785 hostap_set_tim(local, sta->aid, 1);
2786 sta->flags |= WLAN_STA_TIM;
2787 }
2788
2789 ret = AP_TX_BUFFERED;
2790
2791 out:
2792 if (sta != NULL) {
2793 if (ret == AP_TX_CONTINUE ||
2794 ret == AP_TX_CONTINUE_NOT_AUTHORIZED) {
2795 sta->tx_packets++;
2796 sta->tx_bytes += skb->len;
2797 sta->last_tx = jiffies;
2798 }
2799
2800 if ((ret == AP_TX_CONTINUE ||
2801 ret == AP_TX_CONTINUE_NOT_AUTHORIZED) &&
2802 sta->crypt && tx->host_encrypt) {
2803 tx->crypt = sta->crypt;
2804 tx->sta_ptr = sta; /* hostap_handle_sta_release() will
2805 * be called to release sta info
2806 * later */
2807 } else
2808 atomic_dec(&sta->users);
2809 }
2810
2811 return ret;
2812}
2813
2814
2815void hostap_handle_sta_release(void *ptr)
2816{
2817 struct sta_info *sta = ptr;
2818 atomic_dec(&sta->users);
2819}
2820
2821
2822/* Called only as a tasklet (software IRQ) */
2823void hostap_handle_sta_tx_exc(local_info_t *local, struct sk_buff *skb)
2824{
2825 struct sta_info *sta;
2826 struct ieee80211_hdr *hdr;
2827 struct hostap_skb_tx_data *meta;
2828
2829 hdr = (struct ieee80211_hdr *) skb->data;
2830 meta = (struct hostap_skb_tx_data *) skb->cb;
2831
2832 spin_lock(&local->ap->sta_table_lock);
2833 sta = ap_get_sta(local->ap, hdr->addr1);
2834 if (!sta) {
2835 spin_unlock(&local->ap->sta_table_lock);
2836 PDEBUG(DEBUG_AP, "%s: Could not find STA %pM"
2837 " for this TX error (@%lu)\n",
2838 local->dev->name, hdr->addr1, jiffies);
2839 return;
2840 }
2841
2842 sta->tx_since_last_failure = 0;
2843 sta->tx_consecutive_exc++;
2844
2845 if (sta->tx_consecutive_exc >= WLAN_RATE_DECREASE_THRESHOLD &&
2846 sta->tx_rate_idx > 0 && meta->rate <= sta->tx_rate) {
2847 /* use next lower rate */
2848 int old, rate;
2849 old = rate = sta->tx_rate_idx;
2850 while (rate > 0) {
2851 rate--;
2852 if (ap_tx_rate_ok(rate, sta, local)) {
2853 sta->tx_rate_idx = rate;
2854 break;
2855 }
2856 }
2857 if (old != sta->tx_rate_idx) {
2858 switch (sta->tx_rate_idx) {
2859 case 0: sta->tx_rate = 10; break;
2860 case 1: sta->tx_rate = 20; break;
2861 case 2: sta->tx_rate = 55; break;
2862 case 3: sta->tx_rate = 110; break;
2863 default: sta->tx_rate = 0; break;
2864 }
2865 PDEBUG(DEBUG_AP,
2866 "%s: STA %pM TX rate lowered to %d\n",
2867 local->dev->name, sta->addr, sta->tx_rate);
2868 }
2869 sta->tx_consecutive_exc = 0;
2870 }
2871 spin_unlock(&local->ap->sta_table_lock);
2872}
2873
2874
2875static void hostap_update_sta_ps2(local_info_t *local, struct sta_info *sta,
2876 int pwrmgt, int type, int stype)
2877{
2878 if (pwrmgt && !(sta->flags & WLAN_STA_PS)) {
2879 sta->flags |= WLAN_STA_PS;
2880 PDEBUG(DEBUG_PS2, "STA %pM changed to use PS "
2881 "mode (type=0x%02X, stype=0x%02X)\n",
2882 sta->addr, type >> 2, stype >> 4);
2883 } else if (!pwrmgt && (sta->flags & WLAN_STA_PS)) {
2884 sta->flags &= ~WLAN_STA_PS;
2885 PDEBUG(DEBUG_PS2, "STA %pM changed to not use "
2886 "PS mode (type=0x%02X, stype=0x%02X)\n",
2887 sta->addr, type >> 2, stype >> 4);
2888 if (type != IEEE80211_FTYPE_CTL ||
2889 stype != IEEE80211_STYPE_PSPOLL)
2890 schedule_packet_send(local, sta);
2891 }
2892}
2893
2894
2895/* Called only as a tasklet (software IRQ). Called for each RX frame to update
2896 * STA power saving state. pwrmgt is a flag from 802.11 frame_control field. */
2897int hostap_update_sta_ps(local_info_t *local, struct ieee80211_hdr *hdr)
2898{
2899 struct sta_info *sta;
2900 u16 fc;
2901
2902 spin_lock(&local->ap->sta_table_lock);
2903 sta = ap_get_sta(local->ap, hdr->addr2);
2904 if (sta)
2905 atomic_inc(&sta->users);
2906 spin_unlock(&local->ap->sta_table_lock);
2907
2908 if (!sta)
2909 return -1;
2910
2911 fc = le16_to_cpu(hdr->frame_control);
2912 hostap_update_sta_ps2(local, sta, fc & IEEE80211_FCTL_PM,
2913 fc & IEEE80211_FCTL_FTYPE,
2914 fc & IEEE80211_FCTL_STYPE);
2915
2916 atomic_dec(&sta->users);
2917 return 0;
2918}
2919
2920
2921/* Called only as a tasklet (software IRQ). Called for each RX frame after
2922 * getting RX header and payload from hardware. */
2923ap_rx_ret hostap_handle_sta_rx(local_info_t *local, struct net_device *dev,
2924 struct sk_buff *skb,
2925 struct hostap_80211_rx_status *rx_stats,
2926 int wds)
2927{
2928 int ret;
2929 struct sta_info *sta;
2930 u16 fc, type, stype;
2931 struct ieee80211_hdr *hdr;
2932
2933 if (local->ap == NULL)
2934 return AP_RX_CONTINUE;
2935
2936 hdr = (struct ieee80211_hdr *) skb->data;
2937
2938 fc = le16_to_cpu(hdr->frame_control);
2939 type = fc & IEEE80211_FCTL_FTYPE;
2940 stype = fc & IEEE80211_FCTL_STYPE;
2941
2942 spin_lock(&local->ap->sta_table_lock);
2943 sta = ap_get_sta(local->ap, hdr->addr2);
2944 if (sta)
2945 atomic_inc(&sta->users);
2946 spin_unlock(&local->ap->sta_table_lock);
2947
2948 if (sta && !(sta->flags & WLAN_STA_AUTHORIZED))
2949 ret = AP_RX_CONTINUE_NOT_AUTHORIZED;
2950 else
2951 ret = AP_RX_CONTINUE;
2952
2953
2954 if (fc & IEEE80211_FCTL_TODS) {
2955 if (!wds && (sta == NULL || !(sta->flags & WLAN_STA_ASSOC))) {
2956 if (local->hostapd) {
2957 prism2_rx_80211(local->apdev, skb, rx_stats,
2958 PRISM2_RX_NON_ASSOC);
2959#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
2960 } else {
2961 printk(KERN_DEBUG "%s: dropped received packet"
2962 " from non-associated STA %pM"
2963 " (type=0x%02x, subtype=0x%02x)\n",
2964 dev->name, hdr->addr2,
2965 type >> 2, stype >> 4);
2966 hostap_rx(dev, skb, rx_stats);
2967#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
2968 }
2969 ret = AP_RX_EXIT;
2970 goto out;
2971 }
2972 } else if (fc & IEEE80211_FCTL_FROMDS) {
2973 if (!wds) {
2974 /* FromDS frame - not for us; probably
2975 * broadcast/multicast in another BSS - drop */
2976 if (ether_addr_equal(hdr->addr1, dev->dev_addr)) {
2977 printk(KERN_DEBUG "Odd.. FromDS packet "
2978 "received with own BSSID\n");
2979 hostap_dump_rx_80211(dev->name, skb, rx_stats);
2980 }
2981 ret = AP_RX_DROP;
2982 goto out;
2983 }
2984 } else if (stype == IEEE80211_STYPE_NULLFUNC && sta == NULL &&
2985 ether_addr_equal(hdr->addr1, dev->dev_addr)) {
2986
2987 if (local->hostapd) {
2988 prism2_rx_80211(local->apdev, skb, rx_stats,
2989 PRISM2_RX_NON_ASSOC);
2990#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
2991 } else {
2992 /* At least Lucent f/w seems to send data::nullfunc
2993 * frames with no ToDS flag when the current AP returns
2994 * after being unavailable for some time. Speed up
2995 * re-association by informing the station about it not
2996 * being associated. */
2997 printk(KERN_DEBUG "%s: rejected received nullfunc frame"
2998 " without ToDS from not associated STA %pM\n",
2999 dev->name, hdr->addr2);
3000 hostap_rx(dev, skb, rx_stats);
3001#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
3002 }
3003 ret = AP_RX_EXIT;
3004 goto out;
3005 } else if (stype == IEEE80211_STYPE_NULLFUNC) {
3006 /* At least Lucent cards seem to send periodic nullfunc
3007 * frames with ToDS. Let these through to update SQ
3008 * stats and PS state. Nullfunc frames do not contain
3009 * any data and they will be dropped below. */
3010 } else {
3011 /* If BSSID (Addr3) is foreign, this frame is a normal
3012 * broadcast frame from an IBSS network. Drop it silently.
3013 * If BSSID is own, report the dropping of this frame. */
3014 if (ether_addr_equal(hdr->addr3, dev->dev_addr)) {
3015 printk(KERN_DEBUG "%s: dropped received packet from %pM"
3016 " with no ToDS flag "
3017 "(type=0x%02x, subtype=0x%02x)\n", dev->name,
3018 hdr->addr2, type >> 2, stype >> 4);
3019 hostap_dump_rx_80211(dev->name, skb, rx_stats);
3020 }
3021 ret = AP_RX_DROP;
3022 goto out;
3023 }
3024
3025 if (sta) {
3026 hostap_update_sta_ps2(local, sta, fc & IEEE80211_FCTL_PM,
3027 type, stype);
3028
3029 sta->rx_packets++;
3030 sta->rx_bytes += skb->len;
3031 sta->last_rx = jiffies;
3032 }
3033
3034 if (local->ap->nullfunc_ack && stype == IEEE80211_STYPE_NULLFUNC &&
3035 fc & IEEE80211_FCTL_TODS) {
3036 if (local->hostapd) {
3037 prism2_rx_80211(local->apdev, skb, rx_stats,
3038 PRISM2_RX_NULLFUNC_ACK);
3039#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
3040 } else {
3041 /* some STA f/w's seem to require control::ACK frame
3042 * for data::nullfunc, but Prism2 f/w 0.8.0 (at least
3043 * from Compaq) does not send this.. Try to generate
3044 * ACK for these frames from the host driver to make
3045 * power saving work with, e.g., Lucent WaveLAN f/w */
3046 hostap_rx(dev, skb, rx_stats);
3047#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
3048 }
3049 ret = AP_RX_EXIT;
3050 goto out;
3051 }
3052
3053 out:
3054 if (sta)
3055 atomic_dec(&sta->users);
3056
3057 return ret;
3058}
3059
3060
3061/* Called only as a tasklet (software IRQ) */
3062int hostap_handle_sta_crypto(local_info_t *local,
3063 struct ieee80211_hdr *hdr,
3064 struct lib80211_crypt_data **crypt,
3065 void **sta_ptr)
3066{
3067 struct sta_info *sta;
3068
3069 spin_lock(&local->ap->sta_table_lock);
3070 sta = ap_get_sta(local->ap, hdr->addr2);
3071 if (sta)
3072 atomic_inc(&sta->users);
3073 spin_unlock(&local->ap->sta_table_lock);
3074
3075 if (!sta)
3076 return -1;
3077
3078 if (sta->crypt) {
3079 *crypt = sta->crypt;
3080 *sta_ptr = sta;
3081 /* hostap_handle_sta_release() will be called to release STA
3082 * info */
3083 } else
3084 atomic_dec(&sta->users);
3085
3086 return 0;
3087}
3088
3089
3090/* Called only as a tasklet (software IRQ) */
3091int hostap_is_sta_assoc(struct ap_data *ap, u8 *sta_addr)
3092{
3093 struct sta_info *sta;
3094 int ret = 0;
3095
3096 spin_lock(&ap->sta_table_lock);
3097 sta = ap_get_sta(ap, sta_addr);
3098 if (sta != NULL && (sta->flags & WLAN_STA_ASSOC) && !sta->ap)
3099 ret = 1;
3100 spin_unlock(&ap->sta_table_lock);
3101
3102 return ret;
3103}
3104
3105
3106/* Called only as a tasklet (software IRQ) */
3107int hostap_is_sta_authorized(struct ap_data *ap, u8 *sta_addr)
3108{
3109 struct sta_info *sta;
3110 int ret = 0;
3111
3112 spin_lock(&ap->sta_table_lock);
3113 sta = ap_get_sta(ap, sta_addr);
3114 if (sta != NULL && (sta->flags & WLAN_STA_ASSOC) && !sta->ap &&
3115 ((sta->flags & WLAN_STA_AUTHORIZED) ||
3116 ap->local->ieee_802_1x == 0))
3117 ret = 1;
3118 spin_unlock(&ap->sta_table_lock);
3119
3120 return ret;
3121}
3122
3123
3124/* Called only as a tasklet (software IRQ) */
3125int hostap_add_sta(struct ap_data *ap, u8 *sta_addr)
3126{
3127 struct sta_info *sta;
3128 int ret = 1;
3129
3130 if (!ap)
3131 return -1;
3132
3133 spin_lock(&ap->sta_table_lock);
3134 sta = ap_get_sta(ap, sta_addr);
3135 if (sta)
3136 ret = 0;
3137 spin_unlock(&ap->sta_table_lock);
3138
3139 if (ret == 1) {
3140 sta = ap_add_sta(ap, sta_addr);
3141 if (!sta)
3142 return -1;
3143 sta->flags = WLAN_STA_AUTH | WLAN_STA_ASSOC;
3144 sta->ap = 1;
3145 memset(sta->supported_rates, 0, sizeof(sta->supported_rates));
3146 /* No way of knowing which rates are supported since we did not
3147 * get supported rates element from beacon/assoc req. Assume
3148 * that remote end supports all 802.11b rates. */
3149 sta->supported_rates[0] = 0x82;
3150 sta->supported_rates[1] = 0x84;
3151 sta->supported_rates[2] = 0x0b;
3152 sta->supported_rates[3] = 0x16;
3153 sta->tx_supp_rates = WLAN_RATE_1M | WLAN_RATE_2M |
3154 WLAN_RATE_5M5 | WLAN_RATE_11M;
3155 sta->tx_rate = 110;
3156 sta->tx_max_rate = sta->tx_rate_idx = 3;
3157 }
3158
3159 return ret;
3160}
3161
3162
3163/* Called only as a tasklet (software IRQ) */
3164int hostap_update_rx_stats(struct ap_data *ap,
3165 struct ieee80211_hdr *hdr,
3166 struct hostap_80211_rx_status *rx_stats)
3167{
3168 struct sta_info *sta;
3169
3170 if (!ap)
3171 return -1;
3172
3173 spin_lock(&ap->sta_table_lock);
3174 sta = ap_get_sta(ap, hdr->addr2);
3175 if (sta) {
3176 sta->last_rx_silence = rx_stats->noise;
3177 sta->last_rx_signal = rx_stats->signal;
3178 sta->last_rx_rate = rx_stats->rate;
3179 sta->last_rx_updated = IW_QUAL_ALL_UPDATED | IW_QUAL_DBM;
3180 if (rx_stats->rate == 10)
3181 sta->rx_count[0]++;
3182 else if (rx_stats->rate == 20)
3183 sta->rx_count[1]++;
3184 else if (rx_stats->rate == 55)
3185 sta->rx_count[2]++;
3186 else if (rx_stats->rate == 110)
3187 sta->rx_count[3]++;
3188 }
3189 spin_unlock(&ap->sta_table_lock);
3190
3191 return sta ? 0 : -1;
3192}
3193
3194
3195void hostap_update_rates(local_info_t *local)
3196{
3197 struct sta_info *sta;
3198 struct ap_data *ap = local->ap;
3199
3200 if (!ap)
3201 return;
3202
3203 spin_lock_bh(&ap->sta_table_lock);
3204 list_for_each_entry(sta, &ap->sta_list, list) {
3205 prism2_check_tx_rates(sta);
3206 }
3207 spin_unlock_bh(&ap->sta_table_lock);
3208}
3209
3210
3211void * ap_crypt_get_ptrs(struct ap_data *ap, u8 *addr, int permanent,
3212 struct lib80211_crypt_data ***crypt)
3213{
3214 struct sta_info *sta;
3215
3216 spin_lock_bh(&ap->sta_table_lock);
3217 sta = ap_get_sta(ap, addr);
3218 if (sta)
3219 atomic_inc(&sta->users);
3220 spin_unlock_bh(&ap->sta_table_lock);
3221
3222 if (!sta && permanent)
3223 sta = ap_add_sta(ap, addr);
3224
3225 if (!sta)
3226 return NULL;
3227
3228 if (permanent)
3229 sta->flags |= WLAN_STA_PERM;
3230
3231 *crypt = &sta->crypt;
3232
3233 return sta;
3234}
3235
3236
3237void hostap_add_wds_links(local_info_t *local)
3238{
3239 struct ap_data *ap = local->ap;
3240 struct sta_info *sta;
3241
3242 spin_lock_bh(&ap->sta_table_lock);
3243 list_for_each_entry(sta, &ap->sta_list, list) {
3244 if (sta->ap)
3245 hostap_wds_link_oper(local, sta->addr, WDS_ADD);
3246 }
3247 spin_unlock_bh(&ap->sta_table_lock);
3248
3249 schedule_work(&local->ap->wds_oper_queue);
3250}
3251
3252
3253void hostap_wds_link_oper(local_info_t *local, u8 *addr, wds_oper_type type)
3254{
3255 struct wds_oper_data *entry;
3256
3257 entry = kmalloc(sizeof(*entry), GFP_ATOMIC);
3258 if (!entry)
3259 return;
3260 memcpy(entry->addr, addr, ETH_ALEN);
3261 entry->type = type;
3262 spin_lock_bh(&local->lock);
3263 entry->next = local->ap->wds_oper_entries;
3264 local->ap->wds_oper_entries = entry;
3265 spin_unlock_bh(&local->lock);
3266
3267 schedule_work(&local->ap->wds_oper_queue);
3268}
3269
3270
3271EXPORT_SYMBOL(hostap_init_data);
3272EXPORT_SYMBOL(hostap_init_ap_proc);
3273EXPORT_SYMBOL(hostap_free_data);
3274EXPORT_SYMBOL(hostap_check_sta_fw_version);
3275EXPORT_SYMBOL(hostap_handle_sta_tx_exc);
3276#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
3277#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
drivers/net/wireless/intersil/hostap/hostap_ap.h+0−264
@@ -1,264 +0,0 @@
1/* SPDX-License-Identifier: GPL-2.0 */
2#ifndef HOSTAP_AP_H
3#define HOSTAP_AP_H
4
5#include "hostap_80211.h"
6
7/* AP data structures for STAs */
8
9/* maximum number of frames to buffer per STA */
10#define STA_MAX_TX_BUFFER 32
11
12/* STA flags */
13#define WLAN_STA_AUTH BIT(0)
14#define WLAN_STA_ASSOC BIT(1)
15#define WLAN_STA_PS BIT(2)
16#define WLAN_STA_TIM BIT(3) /* TIM bit is on for PS stations */
17#define WLAN_STA_PERM BIT(4) /* permanent; do not remove entry on expiration */
18#define WLAN_STA_AUTHORIZED BIT(5) /* If 802.1X is used, this flag is
19 * controlling whether STA is authorized to
20 * send and receive non-IEEE 802.1X frames
21 */
22#define WLAN_STA_PENDING_POLL BIT(6) /* pending activity poll not ACKed */
23
24#define WLAN_RATE_1M BIT(0)
25#define WLAN_RATE_2M BIT(1)
26#define WLAN_RATE_5M5 BIT(2)
27#define WLAN_RATE_11M BIT(3)
28#define WLAN_RATE_COUNT 4
29
30/* Maximum size of Supported Rates info element. IEEE 802.11 has a limit of 8,
31 * but some pre-standard IEEE 802.11g products use longer elements. */
32#define WLAN_SUPP_RATES_MAX 32
33
34/* Try to increase TX rate after # successfully sent consecutive packets */
35#define WLAN_RATE_UPDATE_COUNT 50
36
37/* Decrease TX rate after # consecutive dropped packets */
38#define WLAN_RATE_DECREASE_THRESHOLD 2
39
40struct sta_info {
41 struct list_head list;
42 struct sta_info *hnext; /* next entry in hash table list */
43 atomic_t users; /* number of users (do not remove if > 0) */
44 struct proc_dir_entry *proc;
45
46 u8 addr[6];
47 u16 aid; /* STA's unique AID (1 .. 2007) or 0 if not yet assigned */
48 u32 flags;
49 u16 capability;
50 u16 listen_interval; /* or beacon_int for APs */
51 u8 supported_rates[WLAN_SUPP_RATES_MAX];
52
53 unsigned long last_auth;
54 unsigned long last_assoc;
55 unsigned long last_rx;
56 unsigned long last_tx;
57 unsigned long rx_packets, tx_packets;
58 unsigned long rx_bytes, tx_bytes;
59 struct sk_buff_head tx_buf;
60 /* FIX: timeout buffers with an expiry time somehow derived from
61 * listen_interval */
62
63 s8 last_rx_silence; /* Noise in dBm */
64 s8 last_rx_signal; /* Signal strength in dBm */
65 u8 last_rx_rate; /* TX rate in 0.1 Mbps */
66 u8 last_rx_updated; /* IWSPY's struct iw_quality::updated */
67
68 u8 tx_supp_rates; /* bit field of supported TX rates */
69 u8 tx_rate; /* current TX rate (in 0.1 Mbps) */
70 u8 tx_rate_idx; /* current TX rate (WLAN_RATE_*) */
71 u8 tx_max_rate; /* max TX rate (WLAN_RATE_*) */
72 u32 tx_count[WLAN_RATE_COUNT]; /* number of frames sent (per rate) */
73 u32 rx_count[WLAN_RATE_COUNT]; /* number of frames received (per rate)
74 */
75 u32 tx_since_last_failure;
76 u32 tx_consecutive_exc;
77
78 struct lib80211_crypt_data *crypt;
79
80 int ap; /* whether this station is an AP */
81
82 local_info_t *local;
83
84#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
85 union {
86 struct {
87 char *challenge; /* shared key authentication
88 * challenge */
89 } sta;
90 struct {
91 int ssid_len;
92 unsigned char ssid[MAX_SSID_LEN + 1]; /* AP's ssid */
93 int channel;
94 unsigned long last_beacon; /* last RX beacon time */
95 } ap;
96 } u;
97
98 struct timer_list timer;
99 enum { STA_NULLFUNC = 0, STA_DISASSOC, STA_DEAUTH } timeout_next;
100#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
101};
102
103
104#define MAX_STA_COUNT 1024
105
106/* Maximum number of AIDs to use for STAs; must be 2007 or lower
107 * (8802.11 limitation) */
108#define MAX_AID_TABLE_SIZE 128
109
110#define STA_HASH_SIZE 256
111#define STA_HASH(sta) (sta[5])
112
113
114/* Default value for maximum station inactivity. After AP_MAX_INACTIVITY_SEC
115 * has passed since last received frame from the station, a nullfunc data
116 * frame is sent to the station. If this frame is not acknowledged and no other
117 * frames have been received, the station will be disassociated after
118 * AP_DISASSOC_DELAY. Similarly, a the station will be deauthenticated after
119 * AP_DEAUTH_DELAY. AP_TIMEOUT_RESOLUTION is the resolution that is used with
120 * max inactivity timer. */
121#define AP_MAX_INACTIVITY_SEC (5 * 60)
122#define AP_DISASSOC_DELAY (HZ)
123#define AP_DEAUTH_DELAY (HZ)
124
125/* ap_policy: whether to accept frames to/from other APs/IBSS */
126typedef enum {
127 AP_OTHER_AP_SKIP_ALL = 0,
128 AP_OTHER_AP_SAME_SSID = 1,
129 AP_OTHER_AP_ALL = 2,
130 AP_OTHER_AP_EVEN_IBSS = 3
131} ap_policy_enum;
132
133#define PRISM2_AUTH_OPEN BIT(0)
134#define PRISM2_AUTH_SHARED_KEY BIT(1)
135
136
137/* MAC address-based restrictions */
138struct mac_entry {
139 struct list_head list;
140 u8 addr[6];
141};
142
143struct mac_restrictions {
144 enum { MAC_POLICY_OPEN = 0, MAC_POLICY_ALLOW, MAC_POLICY_DENY } policy;
145 unsigned int entries;
146 struct list_head mac_list;
147 spinlock_t lock;
148};
149
150
151struct add_sta_proc_data {
152 u8 addr[ETH_ALEN];
153 struct add_sta_proc_data *next;
154};
155
156
157typedef enum { WDS_ADD, WDS_DEL } wds_oper_type;
158struct wds_oper_data {
159 wds_oper_type type;
160 u8 addr[ETH_ALEN];
161 struct wds_oper_data *next;
162};
163
164
165struct ap_data {
166 int initialized; /* whether ap_data has been initialized */
167 local_info_t *local;
168 int bridge_packets; /* send packet to associated STAs directly to the
169 * wireless media instead of higher layers in the
170 * kernel */
171 unsigned int bridged_unicast; /* number of unicast frames bridged on
172 * wireless media */
173 unsigned int bridged_multicast; /* number of non-unicast frames
174 * bridged on wireless media */
175 unsigned int tx_drop_nonassoc; /* number of unicast TX packets dropped
176 * because they were to an address that
177 * was not associated */
178 int nullfunc_ack; /* use workaround for nullfunc frame ACKs */
179
180 spinlock_t sta_table_lock;
181 int num_sta; /* number of entries in sta_list */
182 struct list_head sta_list; /* STA info list head */
183 struct sta_info *sta_hash[STA_HASH_SIZE];
184
185 struct proc_dir_entry *proc;
186
187 ap_policy_enum ap_policy;
188 unsigned int max_inactivity;
189 int autom_ap_wds;
190
191 struct mac_restrictions mac_restrictions; /* MAC-based auth */
192 int last_tx_rate;
193
194 struct work_struct add_sta_proc_queue;
195 struct add_sta_proc_data *add_sta_proc_entries;
196
197 struct work_struct wds_oper_queue;
198 struct wds_oper_data *wds_oper_entries;
199
200 u16 tx_callback_idx;
201
202#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
203 /* pointers to STA info; based on allocated AID or NULL if AID free
204 * AID is in the range 1-2007, so sta_aid[0] corresponders to AID 1
205 * and so on
206 */
207 struct sta_info *sta_aid[MAX_AID_TABLE_SIZE];
208
209 u16 tx_callback_auth, tx_callback_assoc, tx_callback_poll;
210
211 /* WEP operations for generating challenges to be used with shared key
212 * authentication */
213 struct lib80211_crypto_ops *crypt;
214 void *crypt_priv;
215#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
216};
217
218
219void hostap_rx(struct net_device *dev, struct sk_buff *skb,
220 struct hostap_80211_rx_status *rx_stats);
221void hostap_init_data(local_info_t *local);
222void hostap_init_ap_proc(local_info_t *local);
223void hostap_free_data(struct ap_data *ap);
224void hostap_check_sta_fw_version(struct ap_data *ap, int sta_fw_ver);
225
226typedef enum {
227 AP_TX_CONTINUE, AP_TX_DROP, AP_TX_RETRY, AP_TX_BUFFERED,
228 AP_TX_CONTINUE_NOT_AUTHORIZED
229} ap_tx_ret;
230struct hostap_tx_data {
231 struct sk_buff *skb;
232 int host_encrypt;
233 struct lib80211_crypt_data *crypt;
234 void *sta_ptr;
235};
236ap_tx_ret hostap_handle_sta_tx(local_info_t *local, struct hostap_tx_data *tx);
237void hostap_handle_sta_release(void *ptr);
238void hostap_handle_sta_tx_exc(local_info_t *local, struct sk_buff *skb);
239int hostap_update_sta_ps(local_info_t *local, struct ieee80211_hdr *hdr);
240typedef enum {
241 AP_RX_CONTINUE, AP_RX_DROP, AP_RX_EXIT, AP_RX_CONTINUE_NOT_AUTHORIZED
242} ap_rx_ret;
243ap_rx_ret hostap_handle_sta_rx(local_info_t *local, struct net_device *dev,
244 struct sk_buff *skb,
245 struct hostap_80211_rx_status *rx_stats,
246 int wds);
247int hostap_handle_sta_crypto(local_info_t *local, struct ieee80211_hdr *hdr,
248 struct lib80211_crypt_data **crypt,
249 void **sta_ptr);
250int hostap_is_sta_assoc(struct ap_data *ap, u8 *sta_addr);
251int hostap_is_sta_authorized(struct ap_data *ap, u8 *sta_addr);
252int hostap_add_sta(struct ap_data *ap, u8 *sta_addr);
253int hostap_update_rx_stats(struct ap_data *ap, struct ieee80211_hdr *hdr,
254 struct hostap_80211_rx_status *rx_stats);
255void hostap_update_rates(local_info_t *local);
256void hostap_add_wds_links(local_info_t *local);
257void hostap_wds_link_oper(local_info_t *local, u8 *addr, wds_oper_type type);
258
259#ifndef PRISM2_NO_KERNEL_IEEE80211_MGMT
260void hostap_deauth_all_stas(struct net_device *dev, struct ap_data *ap,
261 int resend);
262#endif /* PRISM2_NO_KERNEL_IEEE80211_MGMT */
263
264#endif /* HOSTAP_AP_H */
drivers/net/wireless/intersil/hostap/hostap_common.h+0−420
@@ -1,420 +0,0 @@
1/* SPDX-License-Identifier: GPL-2.0 */
2#ifndef HOSTAP_COMMON_H
3#define HOSTAP_COMMON_H
4
5#include <linux/types.h>
6#include <linux/if_ether.h>
7
8/* IEEE 802.11 defines */
9
10/* HFA384X Configuration RIDs */
11#define HFA384X_RID_CNFPORTTYPE 0xFC00
12#define HFA384X_RID_CNFOWNMACADDR 0xFC01
13#define HFA384X_RID_CNFDESIREDSSID 0xFC02
14#define HFA384X_RID_CNFOWNCHANNEL 0xFC03
15#define HFA384X_RID_CNFOWNSSID 0xFC04
16#define HFA384X_RID_CNFOWNATIMWINDOW 0xFC05
17#define HFA384X_RID_CNFSYSTEMSCALE 0xFC06
18#define HFA384X_RID_CNFMAXDATALEN 0xFC07
19#define HFA384X_RID_CNFWDSADDRESS 0xFC08
20#define HFA384X_RID_CNFPMENABLED 0xFC09
21#define HFA384X_RID_CNFPMEPS 0xFC0A
22#define HFA384X_RID_CNFMULTICASTRECEIVE 0xFC0B
23#define HFA384X_RID_CNFMAXSLEEPDURATION 0xFC0C
24#define HFA384X_RID_CNFPMHOLDOVERDURATION 0xFC0D
25#define HFA384X_RID_CNFOWNNAME 0xFC0E
26#define HFA384X_RID_CNFOWNDTIMPERIOD 0xFC10
27#define HFA384X_RID_CNFWDSADDRESS1 0xFC11 /* AP f/w only */
28#define HFA384X_RID_CNFWDSADDRESS2 0xFC12 /* AP f/w only */
29#define HFA384X_RID_CNFWDSADDRESS3 0xFC13 /* AP f/w only */
30#define HFA384X_RID_CNFWDSADDRESS4 0xFC14 /* AP f/w only */
31#define HFA384X_RID_CNFWDSADDRESS5 0xFC15 /* AP f/w only */
32#define HFA384X_RID_CNFWDSADDRESS6 0xFC16 /* AP f/w only */
33#define HFA384X_RID_CNFMULTICASTPMBUFFERING 0xFC17 /* AP f/w only */
34#define HFA384X_RID_UNKNOWN1 0xFC20
35#define HFA384X_RID_UNKNOWN2 0xFC21
36#define HFA384X_RID_CNFWEPDEFAULTKEYID 0xFC23
37#define HFA384X_RID_CNFDEFAULTKEY0 0xFC24
38#define HFA384X_RID_CNFDEFAULTKEY1 0xFC25
39#define HFA384X_RID_CNFDEFAULTKEY2 0xFC26
40#define HFA384X_RID_CNFDEFAULTKEY3 0xFC27
41#define HFA384X_RID_CNFWEPFLAGS 0xFC28
42#define HFA384X_RID_CNFWEPKEYMAPPINGTABLE 0xFC29
43#define HFA384X_RID_CNFAUTHENTICATION 0xFC2A
44#define HFA384X_RID_CNFMAXASSOCSTA 0xFC2B /* AP f/w only */
45#define HFA384X_RID_CNFTXCONTROL 0xFC2C
46#define HFA384X_RID_CNFROAMINGMODE 0xFC2D
47#define HFA384X_RID_CNFHOSTAUTHENTICATION 0xFC2E /* AP f/w only */
48#define HFA384X_RID_CNFRCVCRCERROR 0xFC30
49#define HFA384X_RID_CNFMMLIFE 0xFC31
50#define HFA384X_RID_CNFALTRETRYCOUNT 0xFC32
51#define HFA384X_RID_CNFBEACONINT 0xFC33
52#define HFA384X_RID_CNFAPPCFINFO 0xFC34 /* AP f/w only */
53#define HFA384X_RID_CNFSTAPCFINFO 0xFC35
54#define HFA384X_RID_CNFPRIORITYQUSAGE 0xFC37
55#define HFA384X_RID_CNFTIMCTRL 0xFC40
56#define HFA384X_RID_UNKNOWN3 0xFC41 /* added in STA f/w 0.7.x */
57#define HFA384X_RID_CNFTHIRTY2TALLY 0xFC42 /* added in STA f/w 0.8.0 */
58#define HFA384X_RID_CNFENHSECURITY 0xFC43 /* AP f/w or STA f/w >= 1.6.3 */
59#define HFA384X_RID_CNFDBMADJUST 0xFC46 /* added in STA f/w 1.3.1 */
60#define HFA384X_RID_GENERICELEMENT 0xFC48 /* added in STA f/w 1.7.0;
61 * write only */
62#define HFA384X_RID_PROPAGATIONDELAY 0xFC49 /* added in STA f/w 1.7.6 */
63#define HFA384X_RID_GROUPADDRESSES 0xFC80
64#define HFA384X_RID_CREATEIBSS 0xFC81
65#define HFA384X_RID_FRAGMENTATIONTHRESHOLD 0xFC82
66#define HFA384X_RID_RTSTHRESHOLD 0xFC83
67#define HFA384X_RID_TXRATECONTROL 0xFC84
68#define HFA384X_RID_PROMISCUOUSMODE 0xFC85
69#define HFA384X_RID_FRAGMENTATIONTHRESHOLD0 0xFC90 /* AP f/w only */
70#define HFA384X_RID_FRAGMENTATIONTHRESHOLD1 0xFC91 /* AP f/w only */
71#define HFA384X_RID_FRAGMENTATIONTHRESHOLD2 0xFC92 /* AP f/w only */
72#define HFA384X_RID_FRAGMENTATIONTHRESHOLD3 0xFC93 /* AP f/w only */
73#define HFA384X_RID_FRAGMENTATIONTHRESHOLD4 0xFC94 /* AP f/w only */
74#define HFA384X_RID_FRAGMENTATIONTHRESHOLD5 0xFC95 /* AP f/w only */
75#define HFA384X_RID_FRAGMENTATIONTHRESHOLD6 0xFC96 /* AP f/w only */
76#define HFA384X_RID_RTSTHRESHOLD0 0xFC97 /* AP f/w only */
77#define HFA384X_RID_RTSTHRESHOLD1 0xFC98 /* AP f/w only */
78#define HFA384X_RID_RTSTHRESHOLD2 0xFC99 /* AP f/w only */
79#define HFA384X_RID_RTSTHRESHOLD3 0xFC9A /* AP f/w only */
80#define HFA384X_RID_RTSTHRESHOLD4 0xFC9B /* AP f/w only */
81#define HFA384X_RID_RTSTHRESHOLD5 0xFC9C /* AP f/w only */
82#define HFA384X_RID_RTSTHRESHOLD6 0xFC9D /* AP f/w only */
83#define HFA384X_RID_TXRATECONTROL0 0xFC9E /* AP f/w only */
84#define HFA384X_RID_TXRATECONTROL1 0xFC9F /* AP f/w only */
85#define HFA384X_RID_TXRATECONTROL2 0xFCA0 /* AP f/w only */
86#define HFA384X_RID_TXRATECONTROL3 0xFCA1 /* AP f/w only */
87#define HFA384X_RID_TXRATECONTROL4 0xFCA2 /* AP f/w only */
88#define HFA384X_RID_TXRATECONTROL5 0xFCA3 /* AP f/w only */
89#define HFA384X_RID_TXRATECONTROL6 0xFCA4 /* AP f/w only */
90#define HFA384X_RID_CNFSHORTPREAMBLE 0xFCB0
91#define HFA384X_RID_CNFEXCLUDELONGPREAMBLE 0xFCB1
92#define HFA384X_RID_CNFAUTHENTICATIONRSPTO 0xFCB2
93#define HFA384X_RID_CNFBASICRATES 0xFCB3
94#define HFA384X_RID_CNFSUPPORTEDRATES 0xFCB4
95#define HFA384X_RID_CNFFALLBACKCTRL 0xFCB5 /* added in STA f/w 1.3.1 */
96#define HFA384X_RID_WEPKEYDISABLE 0xFCB6 /* added in STA f/w 1.3.1 */
97#define HFA384X_RID_WEPKEYMAPINDEX 0xFCB7 /* ? */
98#define HFA384X_RID_BROADCASTKEYID 0xFCB8 /* ? */
99#define HFA384X_RID_ENTSECFLAGEYID 0xFCB9 /* ? */
100#define HFA384X_RID_CNFPASSIVESCANCTRL 0xFCBA /* added in STA f/w 1.5.0 */
101#define HFA384X_RID_SSNHANDLINGMODE 0xFCBB /* added in STA f/w 1.7.0 */
102#define HFA384X_RID_MDCCONTROL 0xFCBC /* added in STA f/w 1.7.0 */
103#define HFA384X_RID_MDCCOUNTRY 0xFCBD /* added in STA f/w 1.7.0 */
104#define HFA384X_RID_TXPOWERMAX 0xFCBE /* added in STA f/w 1.7.0 */
105#define HFA384X_RID_CNFLFOENABLED 0xFCBF /* added in STA f/w 1.6.3 */
106#define HFA384X_RID_CAPINFO 0xFCC0 /* added in STA f/w 1.7.0 */
107#define HFA384X_RID_LISTENINTERVAL 0xFCC1 /* added in STA f/w 1.7.0 */
108#define HFA384X_RID_SW_ANT_DIV 0xFCC2 /* added in STA f/w 1.7.0; Prism3 */
109#define HFA384X_RID_LED_CTRL 0xFCC4 /* added in STA f/w 1.7.6 */
110#define HFA384X_RID_HFODELAY 0xFCC5 /* added in STA f/w 1.7.6 */
111#define HFA384X_RID_DISALLOWEDBSSID 0xFCC6 /* added in STA f/w 1.8.0 */
112#define HFA384X_RID_TICKTIME 0xFCE0
113#define HFA384X_RID_SCANREQUEST 0xFCE1
114#define HFA384X_RID_JOINREQUEST 0xFCE2
115#define HFA384X_RID_AUTHENTICATESTATION 0xFCE3 /* AP f/w only */
116#define HFA384X_RID_CHANNELINFOREQUEST 0xFCE4 /* AP f/w only */
117#define HFA384X_RID_HOSTSCAN 0xFCE5 /* added in STA f/w 1.3.1 */
118
119/* HFA384X Information RIDs */
120#define HFA384X_RID_MAXLOADTIME 0xFD00
121#define HFA384X_RID_DOWNLOADBUFFER 0xFD01
122#define HFA384X_RID_PRIID 0xFD02
123#define HFA384X_RID_PRISUPRANGE 0xFD03
124#define HFA384X_RID_CFIACTRANGES 0xFD04
125#define HFA384X_RID_NICSERNUM 0xFD0A
126#define HFA384X_RID_NICID 0xFD0B
127#define HFA384X_RID_MFISUPRANGE 0xFD0C
128#define HFA384X_RID_CFISUPRANGE 0xFD0D
129#define HFA384X_RID_CHANNELLIST 0xFD10
130#define HFA384X_RID_REGULATORYDOMAINS 0xFD11
131#define HFA384X_RID_TEMPTYPE 0xFD12
132#define HFA384X_RID_CIS 0xFD13
133#define HFA384X_RID_STAID 0xFD20
134#define HFA384X_RID_STASUPRANGE 0xFD21
135#define HFA384X_RID_MFIACTRANGES 0xFD22
136#define HFA384X_RID_CFIACTRANGES2 0xFD23
137#define HFA384X_RID_PRODUCTNAME 0xFD24 /* added in STA f/w 1.3.1;
138 * only Prism2.5(?) */
139#define HFA384X_RID_PORTSTATUS 0xFD40
140#define HFA384X_RID_CURRENTSSID 0xFD41
141#define HFA384X_RID_CURRENTBSSID 0xFD42
142#define HFA384X_RID_COMMSQUALITY 0xFD43
143#define HFA384X_RID_CURRENTTXRATE 0xFD44
144#define HFA384X_RID_CURRENTBEACONINTERVAL 0xFD45
145#define HFA384X_RID_CURRENTSCALETHRESHOLDS 0xFD46
146#define HFA384X_RID_PROTOCOLRSPTIME 0xFD47
147#define HFA384X_RID_SHORTRETRYLIMIT 0xFD48
148#define HFA384X_RID_LONGRETRYLIMIT 0xFD49
149#define HFA384X_RID_MAXTRANSMITLIFETIME 0xFD4A
150#define HFA384X_RID_MAXRECEIVELIFETIME 0xFD4B
151#define HFA384X_RID_CFPOLLABLE 0xFD4C
152#define HFA384X_RID_AUTHENTICATIONALGORITHMS 0xFD4D
153#define HFA384X_RID_PRIVACYOPTIONIMPLEMENTED 0xFD4F
154#define HFA384X_RID_DBMCOMMSQUALITY 0xFD51 /* added in STA f/w 1.3.1 */
155#define HFA384X_RID_CURRENTTXRATE1 0xFD80 /* AP f/w only */
156#define HFA384X_RID_CURRENTTXRATE2 0xFD81 /* AP f/w only */
157#define HFA384X_RID_CURRENTTXRATE3 0xFD82 /* AP f/w only */
158#define HFA384X_RID_CURRENTTXRATE4 0xFD83 /* AP f/w only */
159#define HFA384X_RID_CURRENTTXRATE5 0xFD84 /* AP f/w only */
160#define HFA384X_RID_CURRENTTXRATE6 0xFD85 /* AP f/w only */
161#define HFA384X_RID_OWNMACADDR 0xFD86 /* AP f/w only */
162#define HFA384X_RID_SCANRESULTSTABLE 0xFD88 /* added in STA f/w 0.8.3 */
163#define HFA384X_RID_HOSTSCANRESULTS 0xFD89 /* added in STA f/w 1.3.1 */
164#define HFA384X_RID_AUTHENTICATIONUSED 0xFD8A /* added in STA f/w 1.3.4 */
165#define HFA384X_RID_CNFFAASWITCHCTRL 0xFD8B /* added in STA f/w 1.6.3 */
166#define HFA384X_RID_ASSOCIATIONFAILURE 0xFD8D /* added in STA f/w 1.8.0 */
167#define HFA384X_RID_PHYTYPE 0xFDC0
168#define HFA384X_RID_CURRENTCHANNEL 0xFDC1
169#define HFA384X_RID_CURRENTPOWERSTATE 0xFDC2
170#define HFA384X_RID_CCAMODE 0xFDC3
171#define HFA384X_RID_SUPPORTEDDATARATES 0xFDC6
172#define HFA384X_RID_LFO_VOLT_REG_TEST_RES 0xFDC7 /* added in STA f/w 1.7.1 */
173#define HFA384X_RID_BUILDSEQ 0xFFFE
174#define HFA384X_RID_FWID 0xFFFF
175
176
177struct hfa384x_comp_ident
178{
179 __le16 id;
180 __le16 variant;
181 __le16 major;
182 __le16 minor;
183} __packed;
184
185#define HFA384X_COMP_ID_PRI 0x15
186#define HFA384X_COMP_ID_STA 0x1f
187#define HFA384X_COMP_ID_FW_AP 0x14b
188
189struct hfa384x_sup_range
190{
191 __le16 role;
192 __le16 id;
193 __le16 variant;
194 __le16 bottom;
195 __le16 top;
196} __packed;
197
198
199struct hfa384x_build_id
200{
201 __le16 pri_seq;
202 __le16 sec_seq;
203} __packed;
204
205/* FD01 - Download Buffer */
206struct hfa384x_rid_download_buffer
207{
208 __le16 page;
209 __le16 offset;
210 __le16 length;
211} __packed;
212
213/* BSS connection quality (RID FD43 range, RID FD51 dBm-normalized) */
214struct hfa384x_comms_quality {
215 __le16 comm_qual; /* 0 .. 92 */
216 __le16 signal_level; /* 27 .. 154 */
217 __le16 noise_level; /* 27 .. 154 */
218} __packed;
219
220
221/* netdevice private ioctls (used, e.g., with iwpriv from user space) */
222
223/* New wireless extensions API - SET/GET convention (even ioctl numbers are
224 * root only)
225 */
226#define PRISM2_IOCTL_PRISM2_PARAM (SIOCIWFIRSTPRIV + 0)
227#define PRISM2_IOCTL_GET_PRISM2_PARAM (SIOCIWFIRSTPRIV + 1)
228#define PRISM2_IOCTL_WRITEMIF (SIOCIWFIRSTPRIV + 2)
229#define PRISM2_IOCTL_READMIF (SIOCIWFIRSTPRIV + 3)
230#define PRISM2_IOCTL_MONITOR (SIOCIWFIRSTPRIV + 4)
231#define PRISM2_IOCTL_RESET (SIOCIWFIRSTPRIV + 6)
232#define PRISM2_IOCTL_INQUIRE (SIOCIWFIRSTPRIV + 8)
233#define PRISM2_IOCTL_WDS_ADD (SIOCIWFIRSTPRIV + 10)
234#define PRISM2_IOCTL_WDS_DEL (SIOCIWFIRSTPRIV + 12)
235#define PRISM2_IOCTL_SET_RID_WORD (SIOCIWFIRSTPRIV + 14)
236#define PRISM2_IOCTL_MACCMD (SIOCIWFIRSTPRIV + 16)
237#define PRISM2_IOCTL_ADDMAC (SIOCIWFIRSTPRIV + 18)
238#define PRISM2_IOCTL_DELMAC (SIOCIWFIRSTPRIV + 20)
239#define PRISM2_IOCTL_KICKMAC (SIOCIWFIRSTPRIV + 22)
240
241/* following are not in SIOCGIWPRIV list; check permission in the driver code
242 */
243#define PRISM2_IOCTL_DOWNLOAD (SIOCDEVPRIVATE + 13)
244#define PRISM2_IOCTL_HOSTAPD (SIOCDEVPRIVATE + 14)
245
246
247/* PRISM2_IOCTL_PRISM2_PARAM ioctl() subtypes: */
248enum {
249 /* PRISM2_PARAM_PTYPE = 1, */ /* REMOVED 2003-10-22 */
250 PRISM2_PARAM_TXRATECTRL = 2,
251 PRISM2_PARAM_BEACON_INT = 3,
252 PRISM2_PARAM_PSEUDO_IBSS = 4,
253 PRISM2_PARAM_ALC = 5,
254 /* PRISM2_PARAM_TXPOWER = 6, */ /* REMOVED 2003-10-22 */
255 PRISM2_PARAM_DUMP = 7,
256 PRISM2_PARAM_OTHER_AP_POLICY = 8,
257 PRISM2_PARAM_AP_MAX_INACTIVITY = 9,
258 PRISM2_PARAM_AP_BRIDGE_PACKETS = 10,
259 PRISM2_PARAM_DTIM_PERIOD = 11,
260 PRISM2_PARAM_AP_NULLFUNC_ACK = 12,
261 PRISM2_PARAM_MAX_WDS = 13,
262 PRISM2_PARAM_AP_AUTOM_AP_WDS = 14,
263 PRISM2_PARAM_AP_AUTH_ALGS = 15,
264 PRISM2_PARAM_MONITOR_ALLOW_FCSERR = 16,
265 PRISM2_PARAM_HOST_ENCRYPT = 17,
266 PRISM2_PARAM_HOST_DECRYPT = 18,
267 /* PRISM2_PARAM_BUS_MASTER_THRESHOLD_RX = 19, REMOVED 2005-08-14 */
268 /* PRISM2_PARAM_BUS_MASTER_THRESHOLD_TX = 20, REMOVED 2005-08-14 */
269 PRISM2_PARAM_HOST_ROAMING = 21,
270 PRISM2_PARAM_BCRX_STA_KEY = 22,
271 PRISM2_PARAM_IEEE_802_1X = 23,
272 PRISM2_PARAM_ANTSEL_TX = 24,
273 PRISM2_PARAM_ANTSEL_RX = 25,
274 PRISM2_PARAM_MONITOR_TYPE = 26,
275 PRISM2_PARAM_WDS_TYPE = 27,
276 PRISM2_PARAM_HOSTSCAN = 28,
277 PRISM2_PARAM_AP_SCAN = 29,
278 PRISM2_PARAM_ENH_SEC = 30,
279 PRISM2_PARAM_IO_DEBUG = 31,
280 PRISM2_PARAM_BASIC_RATES = 32,
281 PRISM2_PARAM_OPER_RATES = 33,
282 PRISM2_PARAM_HOSTAPD = 34,
283 PRISM2_PARAM_HOSTAPD_STA = 35,
284 PRISM2_PARAM_WPA = 36,
285 PRISM2_PARAM_PRIVACY_INVOKED = 37,
286 PRISM2_PARAM_TKIP_COUNTERMEASURES = 38,
287 PRISM2_PARAM_DROP_UNENCRYPTED = 39,
288 PRISM2_PARAM_SCAN_CHANNEL_MASK = 40,
289};
290
291enum { HOSTAP_ANTSEL_DO_NOT_TOUCH = 0, HOSTAP_ANTSEL_DIVERSITY = 1,
292 HOSTAP_ANTSEL_LOW = 2, HOSTAP_ANTSEL_HIGH = 3 };
293
294
295/* PRISM2_IOCTL_MACCMD ioctl() subcommands: */
296enum { AP_MAC_CMD_POLICY_OPEN = 0, AP_MAC_CMD_POLICY_ALLOW = 1,
297 AP_MAC_CMD_POLICY_DENY = 2, AP_MAC_CMD_FLUSH = 3,
298 AP_MAC_CMD_KICKALL = 4 };
299
300
301/* PRISM2_IOCTL_DOWNLOAD ioctl() dl_cmd: */
302enum {
303 PRISM2_DOWNLOAD_VOLATILE = 1 /* RAM */,
304 /* Note! Old versions of prism2_srec have a fatal error in CRC-16
305 * calculation, which will corrupt all non-volatile downloads.
306 * PRISM2_DOWNLOAD_NON_VOLATILE used to be 2, but it is now 3 to
307 * prevent use of old versions of prism2_srec for non-volatile
308 * download. */
309 PRISM2_DOWNLOAD_NON_VOLATILE = 3 /* FLASH */,
310 PRISM2_DOWNLOAD_VOLATILE_GENESIS = 4 /* RAM in Genesis mode */,
311 /* Persistent versions of volatile download commands (keep firmware
312 * data in memory and automatically re-download after hw_reset */
313 PRISM2_DOWNLOAD_VOLATILE_PERSISTENT = 5,
314 PRISM2_DOWNLOAD_VOLATILE_GENESIS_PERSISTENT = 6,
315};
316
317struct prism2_download_param {
318 u32 dl_cmd;
319 u32 start_addr;
320 u32 num_areas;
321 struct prism2_download_area {
322 u32 addr; /* wlan card address */
323 u32 len;
324 void __user *ptr; /* pointer to data in user space */
325 } data[];
326};
327
328#define PRISM2_MAX_DOWNLOAD_AREA_LEN 131072
329#define PRISM2_MAX_DOWNLOAD_LEN 262144
330
331
332/* PRISM2_IOCTL_HOSTAPD ioctl() cmd: */
333enum {
334 PRISM2_HOSTAPD_FLUSH = 1,
335 PRISM2_HOSTAPD_ADD_STA = 2,
336 PRISM2_HOSTAPD_REMOVE_STA = 3,
337 PRISM2_HOSTAPD_GET_INFO_STA = 4,
338 /* REMOVED: PRISM2_HOSTAPD_RESET_TXEXC_STA = 5, */
339 PRISM2_SET_ENCRYPTION = 6,
340 PRISM2_GET_ENCRYPTION = 7,
341 PRISM2_HOSTAPD_SET_FLAGS_STA = 8,
342 PRISM2_HOSTAPD_GET_RID = 9,
343 PRISM2_HOSTAPD_SET_RID = 10,
344 PRISM2_HOSTAPD_SET_ASSOC_AP_ADDR = 11,
345 PRISM2_HOSTAPD_SET_GENERIC_ELEMENT = 12,
346 PRISM2_HOSTAPD_MLME = 13,
347 PRISM2_HOSTAPD_SCAN_REQ = 14,
348 PRISM2_HOSTAPD_STA_CLEAR_STATS = 15,
349};
350
351#define PRISM2_HOSTAPD_MAX_BUF_SIZE 1024
352#define PRISM2_HOSTAPD_RID_HDR_LEN \
353offsetof(struct prism2_hostapd_param, u.rid.data)
354#define PRISM2_HOSTAPD_GENERIC_ELEMENT_HDR_LEN \
355offsetof(struct prism2_hostapd_param, u.generic_elem.data)
356
357/* Maximum length for algorithm names (-1 for nul termination) used in ioctl()
358 */
359#define HOSTAP_CRYPT_ALG_NAME_LEN 16
360
361
362struct prism2_hostapd_param {
363 u32 cmd;
364 u8 sta_addr[ETH_ALEN];
365 union {
366 struct {
367 u16 aid;
368 u16 capability;
369 u8 tx_supp_rates;
370 } add_sta;
371 struct {
372 u32 inactive_sec;
373 } get_info_sta;
374 struct {
375 u8 alg[HOSTAP_CRYPT_ALG_NAME_LEN];
376 u32 flags;
377 u32 err;
378 u8 idx;
379 u8 seq[8]; /* sequence counter (set: RX, get: TX) */
380 u16 key_len;
381 u8 key[0];
382 } crypt;
383 struct {
384 u32 flags_and;
385 u32 flags_or;
386 } set_flags_sta;
387 struct {
388 u16 rid;
389 u16 len;
390 u8 data[0];
391 } rid;
392 struct {
393 u8 len;
394 u8 data[0];
395 } generic_elem;
396 struct {
397#define MLME_STA_DEAUTH 0
398#define MLME_STA_DISASSOC 1
399 u16 cmd;
400 u16 reason_code;
401 } mlme;
402 struct {
403 u8 ssid_len;
404 u8 ssid[32];
405 } scan_req;
406 } u;
407};
408
409#define HOSTAP_CRYPT_FLAG_SET_TX_KEY BIT(0)
410#define HOSTAP_CRYPT_FLAG_PERMANENT BIT(1)
411
412#define HOSTAP_CRYPT_ERR_UNKNOWN_ALG 2
413#define HOSTAP_CRYPT_ERR_UNKNOWN_ADDR 3
414#define HOSTAP_CRYPT_ERR_CRYPT_INIT_FAILED 4
415#define HOSTAP_CRYPT_ERR_KEY_SET_FAILED 5
416#define HOSTAP_CRYPT_ERR_TX_KEY_SET_FAILED 6
417#define HOSTAP_CRYPT_ERR_CARD_CONF_FAILED 7
418
419
420#endif /* HOSTAP_COMMON_H */
drivers/net/wireless/intersil/hostap/hostap_config.h+0−49
@@ -1,49 +0,0 @@
1/* SPDX-License-Identifier: GPL-2.0 */
2#ifndef HOSTAP_CONFIG_H
3#define HOSTAP_CONFIG_H
4
5/* In the previous versions of Host AP driver, support for user space version
6 * of IEEE 802.11 management (hostapd) used to be disabled in the default
7 * configuration. From now on, support for hostapd is always included and it is
8 * possible to disable kernel driver version of IEEE 802.11 management with a
9 * separate define, PRISM2_NO_KERNEL_IEEE80211_MGMT. */
10/* #define PRISM2_NO_KERNEL_IEEE80211_MGMT */
11
12/* Maximum number of events handler per one interrupt */
13#define PRISM2_MAX_INTERRUPT_EVENTS 20
14
15/* Include code for downloading firmware images into volatile RAM. */
16#define PRISM2_DOWNLOAD_SUPPORT
17
18/* Allow kernel configuration to enable download support. */
19#if !defined(PRISM2_DOWNLOAD_SUPPORT) && defined(CONFIG_HOSTAP_FIRMWARE)
20#define PRISM2_DOWNLOAD_SUPPORT
21#endif
22
23/* Allow kernel configuration to enable non-volatile download support. */
24#ifdef CONFIG_HOSTAP_FIRMWARE_NVRAM
25#define PRISM2_NON_VOLATILE_DOWNLOAD
26#endif
27
28/* Save low-level I/O for debugging. This should not be enabled in normal use.
29 */
30/* #define PRISM2_IO_DEBUG */
31
32/* Following defines can be used to remove unneeded parts of the driver, e.g.,
33 * to limit the size of the kernel module. Definitions can be added here in
34 * hostap_config.h or they can be added to make command with ccflags-y,
35 * e.g.,
36 * 'make pccard ccflags-y="-DPRISM2_NO_DEBUG -DPRISM2_NO_PROCFS_DEBUG"'
37 */
38
39/* Do not include debug messages into the driver */
40/* #define PRISM2_NO_DEBUG */
41
42/* Do not include /proc/net/prism2/wlan#/{registers,debug} */
43/* #define PRISM2_NO_PROCFS_DEBUG */
44
45/* Do not include station functionality (i.e., allow only Master (Host AP) mode
46 */
47/* #define PRISM2_NO_STATION_MODES */
48
49#endif /* HOSTAP_CONFIG_H */
drivers/net/wireless/intersil/hostap/hostap_cs.c+0−710
@@ -1,710 +0,0 @@
1// SPDX-License-Identifier: GPL-2.0-only
2#define PRISM2_PCCARD
3
4#include <linux/module.h>
5#include <linux/if.h>
6#include <linux/slab.h>
7#include <linux/wait.h>
8#include <linux/timer.h>
9#include <linux/skbuff.h>
10#include <linux/netdevice.h>
11#include <linux/workqueue.h>
12#include <linux/wireless.h>
13#include <net/iw_handler.h>
14
15#include <pcmcia/cistpl.h>
16#include <pcmcia/cisreg.h>
17#include <pcmcia/ds.h>
18
19#include <asm/io.h>
20
21#include "hostap_wlan.h"
22
23
24static char *dev_info = "hostap_cs";
25
26MODULE_AUTHOR("Jouni Malinen");
27MODULE_DESCRIPTION("Support for Intersil Prism2-based 802.11 wireless LAN "
28 "cards (PC Card).");
29MODULE_LICENSE("GPL");
30
31
32static int ignore_cis_vcc;
33module_param(ignore_cis_vcc, int, 0444);
34MODULE_PARM_DESC(ignore_cis_vcc, "Ignore broken CIS VCC entry");
35
36
37/* struct local_info::hw_priv */
38struct hostap_cs_priv {
39 struct pcmcia_device *link;
40 int sandisk_connectplus;
41};
42
43
44#ifdef PRISM2_IO_DEBUG
45
46static inline void hfa384x_outb_debug(struct net_device *dev, int a, u8 v)
47{
48 struct hostap_interface *iface;
49 local_info_t *local;
50 unsigned long flags;
51
52 iface = netdev_priv(dev);
53 local = iface->local;
54 spin_lock_irqsave(&local->lock, flags);
55 prism2_io_debug_add(dev, PRISM2_IO_DEBUG_CMD_OUTB, a, v);
56 outb(v, dev->base_addr + a);
57 spin_unlock_irqrestore(&local->lock, flags);
58}
59
60static inline u8 hfa384x_inb_debug(struct net_device *dev, int a)
61{
62 struct hostap_interface *iface;
63 local_info_t *local;
64 unsigned long flags;
65 u8 v;
66
67 iface = netdev_priv(dev);
68 local = iface->local;
69 spin_lock_irqsave(&local->lock, flags);
70 v = inb(dev->base_addr + a);
71 prism2_io_debug_add(dev, PRISM2_IO_DEBUG_CMD_INB, a, v);
72 spin_unlock_irqrestore(&local->lock, flags);
73 return v;
74}
75
76static inline void hfa384x_outw_debug(struct net_device *dev, int a, u16 v)
77{
78 struct hostap_interface *iface;
79 local_info_t *local;
80 unsigned long flags;
81
82 iface = netdev_priv(dev);
83 local = iface->local;
84 spin_lock_irqsave(&local->lock, flags);
85 prism2_io_debug_add(dev, PRISM2_IO_DEBUG_CMD_OUTW, a, v);
86 outw(v, dev->base_addr + a);
87 spin_unlock_irqrestore(&local->lock, flags);
88}
89
90static inline u16 hfa384x_inw_debug(struct net_device *dev, int a)
91{
92 struct hostap_interface *iface;
93 local_info_t *local;
94 unsigned long flags;
95 u16 v;
96
97 iface = netdev_priv(dev);
98 local = iface->local;
99 spin_lock_irqsave(&local->lock, flags);
100 v = inw(dev->base_addr + a);
101 prism2_io_debug_add(dev, PRISM2_IO_DEBUG_CMD_INW, a, v);
102 spin_unlock_irqrestore(&local->lock, flags);
103 return v;
104}
105
106static inline void hfa384x_outsw_debug(struct net_device *dev, int a,
107 u8 *buf, int wc)
108{
109 struct hostap_interface *iface;
110 local_info_t *local;
111 unsigned long flags;
112
113 iface = netdev_priv(dev);
114 local = iface->local;
115 spin_lock_irqsave(&local->lock, flags);
116 prism2_io_debug_add(dev, PRISM2_IO_DEBUG_CMD_OUTSW, a, wc);
117 outsw(dev->base_addr + a, buf, wc);
118 spin_unlock_irqrestore(&local->lock, flags);
119}
120
121static inline void hfa384x_insw_debug(struct net_device *dev, int a,
122 u8 *buf, int wc)
123{
124 struct hostap_interface *iface;
125 local_info_t *local;
126 unsigned long flags;
127
128 iface = netdev_priv(dev);
129 local = iface->local;
130 spin_lock_irqsave(&local->lock, flags);
131 prism2_io_debug_add(dev, PRISM2_IO_DEBUG_CMD_INSW, a, wc);
132 insw(dev->base_addr + a, buf, wc);
133 spin_unlock_irqrestore(&local->lock, flags);
134}
135
136#define HFA384X_OUTB(v,a) hfa384x_outb_debug(dev, (a), (v))
137#define HFA384X_INB(a) hfa384x_inb_debug(dev, (a))
138#define HFA384X_OUTW(v,a) hfa384x_outw_debug(dev, (a), (v))
139#define HFA384X_INW(a) hfa384x_inw_debug(dev, (a))
140#define HFA384X_OUTSW(a, buf, wc) hfa384x_outsw_debug(dev, (a), (buf), (wc))
141#define HFA384X_INSW(a, buf, wc) hfa384x_insw_debug(dev, (a), (buf), (wc))
142
143#else /* PRISM2_IO_DEBUG */
144
145#define HFA384X_OUTB(v,a) outb((v), dev->base_addr + (a))
146#define HFA384X_INB(a) inb(dev->base_addr + (a))
147#define HFA384X_OUTW(v,a) outw((v), dev->base_addr + (a))
148#define HFA384X_INW(a) inw(dev->base_addr + (a))
149#define HFA384X_INSW(a, buf, wc) insw(dev->base_addr + (a), buf, wc)
150#define HFA384X_OUTSW(a, buf, wc) outsw(dev->base_addr + (a), buf, wc)
151
152#endif /* PRISM2_IO_DEBUG */
153
154
155static int hfa384x_from_bap(struct net_device *dev, u16 bap, void *buf,
156 int len)
157{
158 u16 d_off;
159 u16 *pos;
160
161 d_off = (bap == 1) ? HFA384X_DATA1_OFF : HFA384X_DATA0_OFF;
162 pos = (u16 *) buf;
163
164 if (len / 2)
165 HFA384X_INSW(d_off, buf, len / 2);
166 pos += len / 2;
167
168 if (len & 1)
169 *((char *) pos) = HFA384X_INB(d_off);
170
171 return 0;
172}
173
174
175static int hfa384x_to_bap(struct net_device *dev, u16 bap, void *buf, int len)
176{
177 u16 d_off;
178 u16 *pos;
179
180 d_off = (bap == 1) ? HFA384X_DATA1_OFF : HFA384X_DATA0_OFF;
181 pos = (u16 *) buf;
182
183 if (len / 2)
184 HFA384X_OUTSW(d_off, buf, len / 2);
185 pos += len / 2;
186
187 if (len & 1)
188 HFA384X_OUTB(*((char *) pos), d_off);
189
190 return 0;
191}
192
193
194/* FIX: This might change at some point.. */
195#include "hostap_hw.c"
196
197
198
199static void prism2_detach(struct pcmcia_device *p_dev);
200static void prism2_release(u_long arg);
201static int prism2_config(struct pcmcia_device *link);
202
203
204static int prism2_pccard_card_present(local_info_t *local)
205{
206 struct hostap_cs_priv *hw_priv = local->hw_priv;
207 if (hw_priv != NULL && hw_priv->link != NULL && pcmcia_dev_present(hw_priv->link))
208 return 1;
209 return 0;
210}
211
212
213/*
214 * SanDisk CompactFlash WLAN Flashcard - Product Manual v1.0
215 * Document No. 20-10-00058, January 2004
216 * http://www.sandisk.com/pdf/industrial/ProdManualCFWLANv1.0.pdf
217 */
218#define SANDISK_WLAN_ACTIVATION_OFF 0x40
219#define SANDISK_HCR_OFF 0x42
220
221
222static void sandisk_set_iobase(local_info_t *local)
223{
224 int res;
225 struct hostap_cs_priv *hw_priv = local->hw_priv;
226
227 res = pcmcia_write_config_byte(hw_priv->link, 0x10,
228 hw_priv->link->resource[0]->start & 0x00ff);
229 if (res != 0) {
230 printk(KERN_DEBUG "Prism3 SanDisk - failed to set I/O base 0 -"
231 " res=%d\n", res);
232 }
233 udelay(10);
234
235 res = pcmcia_write_config_byte(hw_priv->link, 0x12,
236 (hw_priv->link->resource[0]->start >> 8) & 0x00ff);
237 if (res != 0) {
238 printk(KERN_DEBUG "Prism3 SanDisk - failed to set I/O base 1 -"
239 " res=%d\n", res);
240 }
241}
242
243
244static void sandisk_write_hcr(local_info_t *local, int hcr)
245{
246 struct net_device *dev = local->dev;
247 int i;
248
249 HFA384X_OUTB(0x80, SANDISK_WLAN_ACTIVATION_OFF);
250 udelay(50);
251 for (i = 0; i < 10; i++) {
252 HFA384X_OUTB(hcr, SANDISK_HCR_OFF);
253 }
254 udelay(55);
255 HFA384X_OUTB(0x45, SANDISK_WLAN_ACTIVATION_OFF);
256}
257
258
259static int sandisk_enable_wireless(struct net_device *dev)
260{
261 int res, ret = 0;
262 struct hostap_interface *iface = netdev_priv(dev);
263 local_info_t *local = iface->local;
264 struct hostap_cs_priv *hw_priv = local->hw_priv;
265
266 if (resource_size(hw_priv->link->resource[0]) < 0x42) {
267 /* Not enough ports to be SanDisk multi-function card */
268 ret = -ENODEV;
269 goto done;
270 }
271
272 if (hw_priv->link->manf_id != 0xd601 || hw_priv->link->card_id != 0x0101) {
273 /* No SanDisk manfid found */
274 ret = -ENODEV;
275 goto done;
276 }
277
278 if (hw_priv->link->socket->functions < 2) {
279 /* No multi-function links found */
280 ret = -ENODEV;
281 goto done;
282 }
283
284 printk(KERN_DEBUG "%s: Multi-function SanDisk ConnectPlus detected"
285 " - using vendor-specific initialization\n", dev->name);
286 hw_priv->sandisk_connectplus = 1;
287
288 res = pcmcia_write_config_byte(hw_priv->link, CISREG_COR,
289 COR_SOFT_RESET);
290 if (res != 0) {
291 printk(KERN_DEBUG "%s: SanDisk - COR sreset failed (%d)\n",
292 dev->name, res);
293 goto done;
294 }
295 mdelay(5);
296
297 /*
298 * Do not enable interrupts here to avoid some bogus events. Interrupts
299 * will be enabled during the first cor_sreset call.
300 */
301 res = pcmcia_write_config_byte(hw_priv->link, CISREG_COR,
302 (COR_LEVEL_REQ | 0x8 | COR_ADDR_DECODE |
303 COR_FUNC_ENA));
304 if (res != 0) {
305 printk(KERN_DEBUG "%s: SanDisk - COR sreset failed (%d)\n",
306 dev->name, res);
307 goto done;
308 }
309 mdelay(5);
310
311 sandisk_set_iobase(local);
312
313 HFA384X_OUTB(0xc5, SANDISK_WLAN_ACTIVATION_OFF);
314 udelay(10);
315 HFA384X_OUTB(0x4b, SANDISK_WLAN_ACTIVATION_OFF);
316 udelay(10);
317
318done:
319 return ret;
320}
321
322
323static void prism2_pccard_cor_sreset(local_info_t *local)
324{
325 int res;
326 u8 val;
327 struct hostap_cs_priv *hw_priv = local->hw_priv;
328
329 if (!prism2_pccard_card_present(local))
330 return;
331
332 res = pcmcia_read_config_byte(hw_priv->link, CISREG_COR, &val);
333 if (res != 0) {
334 printk(KERN_DEBUG "prism2_pccard_cor_sreset failed 1 (%d)\n",
335 res);
336 return;
337 }
338 printk(KERN_DEBUG "prism2_pccard_cor_sreset: original COR %02x\n",
339 val);
340
341 val |= COR_SOFT_RESET;
342 res = pcmcia_write_config_byte(hw_priv->link, CISREG_COR, val);
343 if (res != 0) {
344 printk(KERN_DEBUG "prism2_pccard_cor_sreset failed 2 (%d)\n",
345 res);
346 return;
347 }
348
349 mdelay(hw_priv->sandisk_connectplus ? 5 : 2);
350
351 val &= ~COR_SOFT_RESET;
352 if (hw_priv->sandisk_connectplus)
353 val |= COR_IREQ_ENA;
354 res = pcmcia_write_config_byte(hw_priv->link, CISREG_COR, val);
355 if (res != 0) {
356 printk(KERN_DEBUG "prism2_pccard_cor_sreset failed 3 (%d)\n",
357 res);
358 return;
359 }
360
361 mdelay(hw_priv->sandisk_connectplus ? 5 : 2);
362
363 if (hw_priv->sandisk_connectplus)
364 sandisk_set_iobase(local);
365}
366
367
368static void prism2_pccard_genesis_reset(local_info_t *local, int hcr)
369{
370 int res;
371 u8 old_cor;
372 struct hostap_cs_priv *hw_priv = local->hw_priv;
373
374 if (!prism2_pccard_card_present(local))
375 return;
376
377 if (hw_priv->sandisk_connectplus) {
378 sandisk_write_hcr(local, hcr);
379 return;
380 }
381
382 res = pcmcia_read_config_byte(hw_priv->link, CISREG_COR, &old_cor);
383 if (res != 0) {
384 printk(KERN_DEBUG "%s failed 1 (%d)\n", __func__, res);
385 return;
386 }
387 printk(KERN_DEBUG "%s: original COR %02x\n", __func__, old_cor);
388
389 res = pcmcia_write_config_byte(hw_priv->link, CISREG_COR,
390 old_cor | COR_SOFT_RESET);
391 if (res != 0) {
392 printk(KERN_DEBUG "%s failed 2 (%d)\n", __func__, res);
393 return;
394 }
395
396 mdelay(10);
397
398 /* Setup Genesis mode */
399 res = pcmcia_write_config_byte(hw_priv->link, CISREG_CCSR, hcr);
400 if (res != 0) {
401 printk(KERN_DEBUG "%s failed 3 (%d)\n", __func__, res);
402 return;
403 }
404 mdelay(10);
405
406 res = pcmcia_write_config_byte(hw_priv->link, CISREG_COR,
407 old_cor & ~COR_SOFT_RESET);
408 if (res != 0) {
409 printk(KERN_DEBUG "%s failed 4 (%d)\n", __func__, res);
410 return;
411 }
412
413 mdelay(10);
414}
415
416
417static struct prism2_helper_functions prism2_pccard_funcs =
418{
419 .card_present = prism2_pccard_card_present,
420 .cor_sreset = prism2_pccard_cor_sreset,
421 .genesis_reset = prism2_pccard_genesis_reset,
422 .hw_type = HOSTAP_HW_PCCARD,
423};
424
425
426/* allocate local data and register with CardServices
427 * initialize dev_link structure, but do not configure the card yet */
428static int hostap_cs_probe(struct pcmcia_device *p_dev)
429{
430 int ret;
431
432 PDEBUG(DEBUG_HW, "%s: setting Vcc=33 (constant)\n", dev_info);
433
434 ret = prism2_config(p_dev);
435 if (ret) {
436 PDEBUG(DEBUG_EXTRA, "prism2_config() failed\n");
437 }
438
439 return ret;
440}
441
442
443static void prism2_detach(struct pcmcia_device *link)
444{
445 PDEBUG(DEBUG_FLOW, "prism2_detach\n");
446
447 prism2_release((u_long)link);
448
449 /* release net devices */
450 if (link->priv) {
451 struct hostap_cs_priv *hw_priv;
452 struct net_device *dev;
453 struct hostap_interface *iface;
454 dev = link->priv;
455 iface = netdev_priv(dev);
456 hw_priv = iface->local->hw_priv;
457 prism2_free_local_data(dev);
458 kfree(hw_priv);
459 }
460}
461
462
463static int prism2_config_check(struct pcmcia_device *p_dev, void *priv_data)
464{
465 if (p_dev->config_index == 0)
466 return -EINVAL;
467
468 return pcmcia_request_io(p_dev);
469}
470
471static int prism2_config(struct pcmcia_device *link)
472{
473 struct net_device *dev;
474 struct hostap_interface *iface;
475 local_info_t *local;
476 int ret;
477 struct hostap_cs_priv *hw_priv;
478 unsigned long flags;
479
480 PDEBUG(DEBUG_FLOW, "prism2_config()\n");
481
482 hw_priv = kzalloc(sizeof(*hw_priv), GFP_KERNEL);
483 if (hw_priv == NULL) {
484 ret = -ENOMEM;
485 goto failed;
486 }
487
488 /* Look for an appropriate configuration table entry in the CIS */
489 link->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_AUDIO |
490 CONF_AUTO_CHECK_VCC | CONF_AUTO_SET_IO | CONF_ENABLE_IRQ;
491 if (ignore_cis_vcc)
492 link->config_flags &= ~CONF_AUTO_CHECK_VCC;
493 ret = pcmcia_loop_config(link, prism2_config_check, NULL);
494 if (ret) {
495 if (!ignore_cis_vcc)
496 printk(KERN_ERR "GetNextTuple(): No matching "
497 "CIS configuration. Maybe you need the "
498 "ignore_cis_vcc=1 parameter.\n");
499 goto failed;
500 }
501
502 /* Need to allocate net_device before requesting IRQ handler */
503 dev = prism2_init_local_data(&prism2_pccard_funcs, 0,
504 &link->dev);
505 if (!dev) {
506 ret = -ENOMEM;
507 goto failed;
508 }
509 link->priv = dev;
510
511 iface = netdev_priv(dev);
512 local = iface->local;
513 local->hw_priv = hw_priv;
514 hw_priv->link = link;
515
516 /*
517 * We enable IRQ here, but IRQ handler will not proceed
518 * until dev->base_addr is set below. This protect us from
519 * receive interrupts when driver is not initialized.
520 */
521 ret = pcmcia_request_irq(link, prism2_interrupt);
522 if (ret)
523 goto failed;
524
525 ret = pcmcia_enable_device(link);
526 if (ret)
527 goto failed;
528
529 spin_lock_irqsave(&local->irq_init_lock, flags);
530 dev->irq = link->irq;
531 dev->base_addr = link->resource[0]->start;
532 spin_unlock_irqrestore(&local->irq_init_lock, flags);
533
534 local->shutdown = 0;
535
536 sandisk_enable_wireless(dev);
537
538 ret = prism2_hw_config(dev, 1);
539 if (!ret)
540 ret = hostap_hw_ready(dev);
541
542 return ret;
543
544 failed:
545 kfree(hw_priv);
546 prism2_release((u_long)link);
547 return ret;
548}
549
550
551static void prism2_release(u_long arg)
552{
553 struct pcmcia_device *link = (struct pcmcia_device *)arg;
554
555 PDEBUG(DEBUG_FLOW, "prism2_release\n");
556
557 if (link->priv) {
558 struct net_device *dev = link->priv;
559 struct hostap_interface *iface;
560
561 iface = netdev_priv(dev);
562 prism2_hw_shutdown(dev, 0);
563 iface->local->shutdown = 1;
564 }
565
566 pcmcia_disable_device(link);
567 PDEBUG(DEBUG_FLOW, "release - done\n");
568}
569
570static int hostap_cs_suspend(struct pcmcia_device *link)
571{
572 struct net_device *dev = (struct net_device *) link->priv;
573 int dev_open = 0;
574 struct hostap_interface *iface = NULL;
575
576 if (!dev)
577 return -ENODEV;
578
579 iface = netdev_priv(dev);
580
581 PDEBUG(DEBUG_EXTRA, "%s: CS_EVENT_PM_SUSPEND\n", dev_info);
582 if (iface && iface->local)
583 dev_open = iface->local->num_dev_open > 0;
584 if (dev_open) {
585 netif_stop_queue(dev);
586 netif_device_detach(dev);
587 }
588 prism2_suspend(dev);
589
590 return 0;
591}
592
593static int hostap_cs_resume(struct pcmcia_device *link)
594{
595 struct net_device *dev = (struct net_device *) link->priv;
596 int dev_open = 0;
597 struct hostap_interface *iface = NULL;
598
599 if (!dev)
600 return -ENODEV;
601
602 iface = netdev_priv(dev);
603
604 PDEBUG(DEBUG_EXTRA, "%s: CS_EVENT_PM_RESUME\n", dev_info);
605
606 if (iface && iface->local)
607 dev_open = iface->local->num_dev_open > 0;
608
609 prism2_hw_shutdown(dev, 1);
610 prism2_hw_config(dev, dev_open ? 0 : 1);
611 if (dev_open) {
612 netif_device_attach(dev);
613 netif_start_queue(dev);
614 }
615
616 return 0;
617}
618
619static const struct pcmcia_device_id hostap_cs_ids[] = {
620 PCMCIA_DEVICE_MANF_CARD(0x000b, 0x7100),
621 PCMCIA_DEVICE_MANF_CARD(0x000b, 0x7300),
622 PCMCIA_DEVICE_MANF_CARD(0x0101, 0x0777),
623 PCMCIA_DEVICE_MANF_CARD(0x0126, 0x8000),
624 PCMCIA_DEVICE_MANF_CARD(0x0138, 0x0002),
625 PCMCIA_DEVICE_MANF_CARD(0x01bf, 0x3301),
626 PCMCIA_DEVICE_MANF_CARD(0x0250, 0x0002),
627 PCMCIA_DEVICE_MANF_CARD(0x026f, 0x030b),
628 PCMCIA_DEVICE_MANF_CARD(0x0274, 0x1612),
629 PCMCIA_DEVICE_MANF_CARD(0x0274, 0x1613),
630 PCMCIA_DEVICE_MANF_CARD(0x028a, 0x0002),
631 PCMCIA_DEVICE_MANF_CARD(0x02aa, 0x0002),
632 PCMCIA_DEVICE_MANF_CARD(0x02d2, 0x0001),
633 PCMCIA_DEVICE_MANF_CARD(0x50c2, 0x0001),
634 PCMCIA_DEVICE_MANF_CARD(0x50c2, 0x7300),
635/* PCMCIA_DEVICE_MANF_CARD(0xc00f, 0x0000), conflict with pcnet_cs */
636 PCMCIA_DEVICE_MANF_CARD(0xc250, 0x0002),
637 PCMCIA_DEVICE_MANF_CARD(0xd601, 0x0002),
638 PCMCIA_DEVICE_MANF_CARD(0xd601, 0x0005),
639 PCMCIA_DEVICE_MANF_CARD(0xd601, 0x0010),
640 PCMCIA_DEVICE_MANF_CARD(0x0126, 0x0002),
641 PCMCIA_DEVICE_MANF_CARD_PROD_ID1(0xd601, 0x0005, "ADLINK 345 CF",
642 0x2d858104),
643 PCMCIA_DEVICE_MANF_CARD_PROD_ID1(0x0156, 0x0002, "INTERSIL",
644 0x74c5e40d),
645 PCMCIA_DEVICE_MANF_CARD_PROD_ID1(0x0156, 0x0002, "Intersil",
646 0x4b801a17),
647 PCMCIA_DEVICE_MANF_CARD_PROD_ID3(0x0156, 0x0002, "Version 01.02",
648 0x4b74baa0),
649 PCMCIA_MFC_DEVICE_PROD_ID12(0, "SanDisk", "ConnectPlus",
650 0x7a954bd9, 0x74be00c6),
651 PCMCIA_DEVICE_PROD_ID123(
652 "Addtron", "AWP-100 Wireless PCMCIA", "Version 01.02",
653 0xe6ec52ce, 0x08649af2, 0x4b74baa0),
654 PCMCIA_DEVICE_PROD_ID123(
655 "Canon", "Wireless LAN CF Card K30225", "Version 01.00",
656 0x96ef6fe2, 0x263fcbab, 0xa57adb8c),
657 PCMCIA_DEVICE_PROD_ID123(
658 "D", "Link DWL-650 11Mbps WLAN Card", "Version 01.02",
659 0x71b18589, 0xb6f1b0ab, 0x4b74baa0),
660 PCMCIA_DEVICE_PROD_ID123(
661 "Instant Wireless ", " Network PC CARD", "Version 01.02",
662 0x11d901af, 0x6e9bd926, 0x4b74baa0),
663 PCMCIA_DEVICE_PROD_ID123(
664 "SMC", "SMC2632W", "Version 01.02",
665 0xc4f8b18b, 0x474a1f2a, 0x4b74baa0),
666 PCMCIA_DEVICE_PROD_ID12("BUFFALO", "WLI-CF-S11G",
667 0x2decece3, 0x82067c18),
668 PCMCIA_DEVICE_PROD_ID12("Compaq", "WL200_11Mbps_Wireless_PCI_Card",
669 0x54f7c49c, 0x15a75e5b),
670 PCMCIA_DEVICE_PROD_ID12("INTERSIL", "HFA384x/IEEE",
671 0x74c5e40d, 0xdb472a18),
672 PCMCIA_DEVICE_PROD_ID12("Linksys", "Wireless CompactFlash Card",
673 0x0733cc81, 0x0c52f395),
674 PCMCIA_DEVICE_PROD_ID12(
675 "ZoomAir 11Mbps High", "Rate wireless Networking",
676 0x273fe3db, 0x32a1eaee),
677 PCMCIA_DEVICE_PROD_ID12("NETGEAR MA401 Wireless PC", "Card",
678 0xa37434e9, 0x9762e8f1),
679 PCMCIA_DEVICE_PROD_ID123(
680 "Pretec", "CompactWLAN Card 802.11b", "2.5",
681 0x1cadd3e5, 0xe697636c, 0x7a5bfcf1),
682 PCMCIA_DEVICE_PROD_ID123(
683 "U.S. Robotics", "IEEE 802.11b PC-CARD", "Version 01.02",
684 0xc7b8df9d, 0x1700d087, 0x4b74baa0),
685 PCMCIA_DEVICE_PROD_ID123(
686 "Allied Telesyn", "AT-WCL452 Wireless PCMCIA Radio",
687 "Ver. 1.00",
688 0x5cd01705, 0x4271660f, 0x9d08ee12),
689 PCMCIA_DEVICE_PROD_ID123(
690 "Wireless LAN" , "11Mbps PC Card", "Version 01.02",
691 0x4b8870ff, 0x70e946d1, 0x4b74baa0),
692 PCMCIA_DEVICE_PROD_ID3("HFA3863", 0x355cb092),
693 PCMCIA_DEVICE_PROD_ID3("ISL37100P", 0x630d52b2),
694 PCMCIA_DEVICE_PROD_ID3("ISL37101P-10", 0xdd97a26b),
695 PCMCIA_DEVICE_PROD_ID3("ISL37300P", 0xc9049a39),
696 PCMCIA_DEVICE_NULL
697};
698MODULE_DEVICE_TABLE(pcmcia, hostap_cs_ids);
699
700
701static struct pcmcia_driver hostap_driver = {
702 .name = "hostap_cs",
703 .probe = hostap_cs_probe,
704 .remove = prism2_detach,
705 .owner = THIS_MODULE,
706 .id_table = hostap_cs_ids,
707 .suspend = hostap_cs_suspend,
708 .resume = hostap_cs_resume,
709};
710module_pcmcia_driver(hostap_driver);
drivers/net/wireless/intersil/hostap/hostap_download.c+0−810
@@ -1,810 +0,0 @@
1// SPDX-License-Identifier: GPL-2.0
2static int prism2_enable_aux_port(struct net_device *dev, int enable)
3{
4 u16 val, reg;
5 int i, tries;
6 unsigned long flags;
7 struct hostap_interface *iface;
8 local_info_t *local;
9
10 iface = netdev_priv(dev);
11 local = iface->local;
12
13 if (local->no_pri) {
14 if (enable) {
15 PDEBUG(DEBUG_EXTRA2, "%s: no PRI f/w - assuming Aux "
16 "port is already enabled\n", dev->name);
17 }
18 return 0;
19 }
20
21 spin_lock_irqsave(&local->cmdlock, flags);
22
23 /* wait until busy bit is clear */
24 tries = HFA384X_CMD_BUSY_TIMEOUT;
25 while (HFA384X_INW(HFA384X_CMD_OFF) & HFA384X_CMD_BUSY && tries > 0) {
26 tries--;
27 udelay(1);
28 }
29 if (tries == 0) {
30 reg = HFA384X_INW(HFA384X_CMD_OFF);
31 spin_unlock_irqrestore(&local->cmdlock, flags);
32 printk("%s: prism2_enable_aux_port - timeout - reg=0x%04x\n",
33 dev->name, reg);
34 return -ETIMEDOUT;
35 }
36
37 val = HFA384X_INW(HFA384X_CONTROL_OFF);
38
39 if (enable) {
40 HFA384X_OUTW(HFA384X_AUX_MAGIC0, HFA384X_PARAM0_OFF);
41 HFA384X_OUTW(HFA384X_AUX_MAGIC1, HFA384X_PARAM1_OFF);
42 HFA384X_OUTW(HFA384X_AUX_MAGIC2, HFA384X_PARAM2_OFF);
43
44 if ((val & HFA384X_AUX_PORT_MASK) != HFA384X_AUX_PORT_DISABLED)
45 printk("prism2_enable_aux_port: was not disabled!?\n");
46 val &= ~HFA384X_AUX_PORT_MASK;
47 val |= HFA384X_AUX_PORT_ENABLE;
48 } else {
49 HFA384X_OUTW(0, HFA384X_PARAM0_OFF);
50 HFA384X_OUTW(0, HFA384X_PARAM1_OFF);
51 HFA384X_OUTW(0, HFA384X_PARAM2_OFF);
52
53 if ((val & HFA384X_AUX_PORT_MASK) != HFA384X_AUX_PORT_ENABLED)
54 printk("prism2_enable_aux_port: was not enabled!?\n");
55 val &= ~HFA384X_AUX_PORT_MASK;
56 val |= HFA384X_AUX_PORT_DISABLE;
57 }
58 HFA384X_OUTW(val, HFA384X_CONTROL_OFF);
59
60 udelay(5);
61
62 i = 10000;
63 while (i > 0) {
64 val = HFA384X_INW(HFA384X_CONTROL_OFF);
65 val &= HFA384X_AUX_PORT_MASK;
66
67 if ((enable && val == HFA384X_AUX_PORT_ENABLED) ||
68 (!enable && val == HFA384X_AUX_PORT_DISABLED))
69 break;
70
71 udelay(10);
72 i--;
73 }
74
75 spin_unlock_irqrestore(&local->cmdlock, flags);
76
77 if (i == 0) {
78 printk("prism2_enable_aux_port(%d) timed out\n",
79 enable);
80 return -ETIMEDOUT;
81 }
82
83 return 0;
84}
85
86
87static int hfa384x_from_aux(struct net_device *dev, unsigned int addr, int len,
88 void *buf)
89{
90 u16 page, offset;
91 if (addr & 1 || len & 1)
92 return -1;
93
94 page = addr >> 7;
95 offset = addr & 0x7f;
96
97 HFA384X_OUTW(page, HFA384X_AUXPAGE_OFF);
98 HFA384X_OUTW(offset, HFA384X_AUXOFFSET_OFF);
99
100 udelay(5);
101
102#ifdef PRISM2_PCI
103 {
104 __le16 *pos = (__le16 *) buf;
105 while (len > 0) {
106 *pos++ = HFA384X_INW_DATA(HFA384X_AUXDATA_OFF);
107 len -= 2;
108 }
109 }
110#else /* PRISM2_PCI */
111 HFA384X_INSW(HFA384X_AUXDATA_OFF, buf, len / 2);
112#endif /* PRISM2_PCI */
113
114 return 0;
115}
116
117
118static int hfa384x_to_aux(struct net_device *dev, unsigned int addr, int len,
119 void *buf)
120{
121 u16 page, offset;
122 if (addr & 1 || len & 1)
123 return -1;
124
125 page = addr >> 7;
126 offset = addr & 0x7f;
127
128 HFA384X_OUTW(page, HFA384X_AUXPAGE_OFF);
129 HFA384X_OUTW(offset, HFA384X_AUXOFFSET_OFF);
130
131 udelay(5);
132
133#ifdef PRISM2_PCI
134 {
135 __le16 *pos = (__le16 *) buf;
136 while (len > 0) {
137 HFA384X_OUTW_DATA(*pos++, HFA384X_AUXDATA_OFF);
138 len -= 2;
139 }
140 }
141#else /* PRISM2_PCI */
142 HFA384X_OUTSW(HFA384X_AUXDATA_OFF, buf, len / 2);
143#endif /* PRISM2_PCI */
144
145 return 0;
146}
147
148
149static int prism2_pda_ok(u8 *buf)
150{
151 __le16 *pda = (__le16 *) buf;
152 int pos;
153 u16 len, pdr;
154
155 if (buf[0] == 0xff && buf[1] == 0x00 && buf[2] == 0xff &&
156 buf[3] == 0x00)
157 return 0;
158
159 pos = 0;
160 while (pos + 1 < PRISM2_PDA_SIZE / 2) {
161 len = le16_to_cpu(pda[pos]);
162 pdr = le16_to_cpu(pda[pos + 1]);
163 if (len == 0 || pos + len > PRISM2_PDA_SIZE / 2)
164 return 0;
165
166 if (pdr == 0x0000 && len == 2) {
167 /* PDA end found */
168 return 1;
169 }
170
171 pos += len + 1;
172 }
173
174 return 0;
175}
176
177
178#define prism2_download_aux_dump_npages 65536
179
180struct prism2_download_aux_dump {
181 local_info_t *local;
182 u16 page[0x80];
183};
184
185static int prism2_download_aux_dump_proc_show(struct seq_file *m, void *v)
186{
187 struct prism2_download_aux_dump *ctx = m->private;
188
189 hfa384x_from_aux(ctx->local->dev, (unsigned long)v - 1, 0x80, ctx->page);
190 seq_write(m, ctx->page, 0x80);
191 return 0;
192}
193
194static void *prism2_download_aux_dump_proc_start(struct seq_file *m, loff_t *_pos)
195{
196 struct prism2_download_aux_dump *ctx = m->private;
197 prism2_enable_aux_port(ctx->local->dev, 1);
198 if (*_pos >= prism2_download_aux_dump_npages)
199 return NULL;
200 return (void *)((unsigned long)*_pos + 1);
201}
202
203static void *prism2_download_aux_dump_proc_next(struct seq_file *m, void *v, loff_t *_pos)
204{
205 ++*_pos;
206 if (*_pos >= prism2_download_aux_dump_npages)
207 return NULL;
208 return (void *)((unsigned long)*_pos + 1);
209}
210
211static void prism2_download_aux_dump_proc_stop(struct seq_file *m, void *v)
212{
213 struct prism2_download_aux_dump *ctx = m->private;
214 prism2_enable_aux_port(ctx->local->dev, 0);
215}
216
217static const struct seq_operations prism2_download_aux_dump_proc_seqops = {
218 .start = prism2_download_aux_dump_proc_start,
219 .next = prism2_download_aux_dump_proc_next,
220 .stop = prism2_download_aux_dump_proc_stop,
221 .show = prism2_download_aux_dump_proc_show,
222};
223
224static int prism2_download_aux_dump_proc_open(struct inode *inode, struct file *file)
225{
226 int ret = seq_open_private(file, &prism2_download_aux_dump_proc_seqops,
227 sizeof(struct prism2_download_aux_dump));
228 if (ret == 0) {
229 struct seq_file *m = file->private_data;
230 m->private = pde_data(inode);
231 }
232 return ret;
233}
234
235static const struct proc_ops prism2_download_aux_dump_proc_ops = {
236 .proc_open = prism2_download_aux_dump_proc_open,
237 .proc_read = seq_read,
238 .proc_lseek = seq_lseek,
239 .proc_release = seq_release_private,
240};
241
242
243static u8 * prism2_read_pda(struct net_device *dev)
244{
245 u8 *buf;
246 int res, i, found = 0;
247#define NUM_PDA_ADDRS 4
248 unsigned int pda_addr[NUM_PDA_ADDRS] = {
249 0x7f0000 /* others than HFA3841 */,
250 0x3f0000 /* HFA3841 */,
251 0x390000 /* apparently used in older cards */,
252 0x7f0002 /* Intel PRO/Wireless 2011B (PCI) */,
253 };
254
255 buf = kmalloc(PRISM2_PDA_SIZE, GFP_KERNEL);
256 if (buf == NULL)
257 return NULL;
258
259 /* Note: wlan card should be in initial state (just after init cmd)
260 * and no other operations should be performed concurrently. */
261
262 prism2_enable_aux_port(dev, 1);
263
264 for (i = 0; i < NUM_PDA_ADDRS; i++) {
265 PDEBUG(DEBUG_EXTRA2, "%s: trying to read PDA from 0x%08x",
266 dev->name, pda_addr[i]);
267 res = hfa384x_from_aux(dev, pda_addr[i], PRISM2_PDA_SIZE, buf);
268 if (res)
269 continue;
270 if (res == 0 && prism2_pda_ok(buf)) {
271 PDEBUG2(DEBUG_EXTRA2, ": OK\n");
272 found = 1;
273 break;
274 } else {
275 PDEBUG2(DEBUG_EXTRA2, ": failed\n");
276 }
277 }
278
279 prism2_enable_aux_port(dev, 0);
280
281 if (!found) {
282 printk(KERN_DEBUG "%s: valid PDA not found\n", dev->name);
283 kfree(buf);
284 buf = NULL;
285 }
286
287 return buf;
288}
289
290
291static int prism2_download_volatile(local_info_t *local,
292 struct prism2_download_data *param)
293{
294 struct net_device *dev = local->dev;
295 int ret = 0, i;
296 u16 param0, param1;
297
298 if (local->hw_downloading) {
299 printk(KERN_WARNING "%s: Already downloading - aborting new "
300 "request\n", dev->name);
301 return -1;
302 }
303
304 local->hw_downloading = 1;
305 if (local->pri_only) {
306 hfa384x_disable_interrupts(dev);
307 } else {
308 prism2_hw_shutdown(dev, 0);
309
310 if (prism2_hw_init(dev, 0)) {
311 printk(KERN_WARNING "%s: Could not initialize card for"
312 " download\n", dev->name);
313 ret = -1;
314 goto out;
315 }
316 }
317
318 if (prism2_enable_aux_port(dev, 1)) {
319 printk(KERN_WARNING "%s: Could not enable AUX port\n",
320 dev->name);
321 ret = -1;
322 goto out;
323 }
324
325 param0 = param->start_addr & 0xffff;
326 param1 = param->start_addr >> 16;
327
328 HFA384X_OUTW(0, HFA384X_PARAM2_OFF);
329 HFA384X_OUTW(param1, HFA384X_PARAM1_OFF);
330 if (hfa384x_cmd_wait(dev, HFA384X_CMDCODE_DOWNLOAD |
331 (HFA384X_PROGMODE_ENABLE_VOLATILE << 8),
332 param0)) {
333 printk(KERN_WARNING "%s: Download command execution failed\n",
334 dev->name);
335 ret = -1;
336 goto out;
337 }
338
339 for (i = 0; i < param->num_areas; i++) {
340 PDEBUG(DEBUG_EXTRA2, "%s: Writing %d bytes at 0x%08x\n",
341 dev->name, param->data[i].len, param->data[i].addr);
342 if (hfa384x_to_aux(dev, param->data[i].addr,
343 param->data[i].len, param->data[i].data)) {
344 printk(KERN_WARNING "%s: RAM download at 0x%08x "
345 "(len=%d) failed\n", dev->name,
346 param->data[i].addr, param->data[i].len);
347 ret = -1;
348 goto out;
349 }
350 }
351
352 HFA384X_OUTW(param1, HFA384X_PARAM1_OFF);
353 HFA384X_OUTW(0, HFA384X_PARAM2_OFF);
354 if (hfa384x_cmd_no_wait(dev, HFA384X_CMDCODE_DOWNLOAD |
355 (HFA384X_PROGMODE_DISABLE << 8), param0)) {
356 printk(KERN_WARNING "%s: Download command execution failed\n",
357 dev->name);
358 ret = -1;
359 goto out;
360 }
361 /* ProgMode disable causes the hardware to restart itself from the
362 * given starting address. Give hw some time and ACK command just in
363 * case restart did not happen. */
364 mdelay(5);
365 HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_EVACK_OFF);
366
367 if (prism2_enable_aux_port(dev, 0)) {
368 printk(KERN_DEBUG "%s: Disabling AUX port failed\n",
369 dev->name);
370 /* continue anyway.. restart should have taken care of this */
371 }
372
373 mdelay(5);
374 local->hw_downloading = 0;
375 if (prism2_hw_config(dev, 2)) {
376 printk(KERN_WARNING "%s: Card configuration after RAM "
377 "download failed\n", dev->name);
378 ret = -1;
379 goto out;
380 }
381
382 out:
383 local->hw_downloading = 0;
384 return ret;
385}
386
387
388static int prism2_enable_genesis(local_info_t *local, int hcr)
389{
390 struct net_device *dev = local->dev;
391 u8 initseq[4] = { 0x00, 0xe1, 0xa1, 0xff };
392 u8 readbuf[4];
393
394 printk(KERN_DEBUG "%s: test Genesis mode with HCR 0x%02x\n",
395 dev->name, hcr);
396 local->func->cor_sreset(local);
397 hfa384x_to_aux(dev, 0x7e0038, sizeof(initseq), initseq);
398 local->func->genesis_reset(local, hcr);
399
400 /* Readback test */
401 hfa384x_from_aux(dev, 0x7e0038, sizeof(readbuf), readbuf);
402 hfa384x_to_aux(dev, 0x7e0038, sizeof(initseq), initseq);
403 hfa384x_from_aux(dev, 0x7e0038, sizeof(readbuf), readbuf);
404
405 if (memcmp(initseq, readbuf, sizeof(initseq)) == 0) {
406 printk(KERN_DEBUG "Readback test succeeded, HCR 0x%02x\n",
407 hcr);
408 return 0;
409 } else {
410 printk(KERN_DEBUG "Readback test failed, HCR 0x%02x write %4ph read %4ph\n",
411 hcr, initseq, readbuf);
412 return 1;
413 }
414}
415
416
417static int prism2_get_ram_size(local_info_t *local)
418{
419 int ret;
420
421 /* Try to enable genesis mode; 0x1F for x8 SRAM or 0x0F for x16 SRAM */
422 if (prism2_enable_genesis(local, 0x1f) == 0)
423 ret = 8;
424 else if (prism2_enable_genesis(local, 0x0f) == 0)
425 ret = 16;
426 else
427 ret = -1;
428
429 /* Disable genesis mode */
430 local->func->genesis_reset(local, ret == 16 ? 0x07 : 0x17);
431
432 return ret;
433}
434
435
436static int prism2_download_genesis(local_info_t *local,
437 struct prism2_download_data *param)
438{
439 struct net_device *dev = local->dev;
440 int ram16 = 0, i;
441 int ret = 0;
442
443 if (local->hw_downloading) {
444 printk(KERN_WARNING "%s: Already downloading - aborting new "
445 "request\n", dev->name);
446 return -EBUSY;
447 }
448
449 if (!local->func->genesis_reset || !local->func->cor_sreset) {
450 printk(KERN_INFO "%s: Genesis mode downloading not supported "
451 "with this hwmodel\n", dev->name);
452 return -EOPNOTSUPP;
453 }
454
455 local->hw_downloading = 1;
456
457 if (prism2_enable_aux_port(dev, 1)) {
458 printk(KERN_DEBUG "%s: failed to enable AUX port\n",
459 dev->name);
460 ret = -EIO;
461 goto out;
462 }
463
464 if (local->sram_type == -1) {
465 /* 0x1F for x8 SRAM or 0x0F for x16 SRAM */
466 if (prism2_enable_genesis(local, 0x1f) == 0) {
467 ram16 = 0;
468 PDEBUG(DEBUG_EXTRA2, "%s: Genesis mode OK using x8 "
469 "SRAM\n", dev->name);
470 } else if (prism2_enable_genesis(local, 0x0f) == 0) {
471 ram16 = 1;
472 PDEBUG(DEBUG_EXTRA2, "%s: Genesis mode OK using x16 "
473 "SRAM\n", dev->name);
474 } else {
475 printk(KERN_DEBUG "%s: Could not initiate genesis "
476 "mode\n", dev->name);
477 ret = -EIO;
478 goto out;
479 }
480 } else {
481 if (prism2_enable_genesis(local, local->sram_type == 8 ?
482 0x1f : 0x0f)) {
483 printk(KERN_DEBUG "%s: Failed to set Genesis "
484 "mode (sram_type=%d)\n", dev->name,
485 local->sram_type);
486 ret = -EIO;
487 goto out;
488 }
489 ram16 = local->sram_type != 8;
490 }
491
492 for (i = 0; i < param->num_areas; i++) {
493 PDEBUG(DEBUG_EXTRA2, "%s: Writing %d bytes at 0x%08x\n",
494 dev->name, param->data[i].len, param->data[i].addr);
495 if (hfa384x_to_aux(dev, param->data[i].addr,
496 param->data[i].len, param->data[i].data)) {
497 printk(KERN_WARNING "%s: RAM download at 0x%08x "
498 "(len=%d) failed\n", dev->name,
499 param->data[i].addr, param->data[i].len);
500 ret = -EIO;
501 goto out;
502 }
503 }
504
505 PDEBUG(DEBUG_EXTRA2, "Disable genesis mode\n");
506 local->func->genesis_reset(local, ram16 ? 0x07 : 0x17);
507 if (prism2_enable_aux_port(dev, 0)) {
508 printk(KERN_DEBUG "%s: Failed to disable AUX port\n",
509 dev->name);
510 }
511
512 mdelay(5);
513 local->hw_downloading = 0;
514
515 PDEBUG(DEBUG_EXTRA2, "Trying to initialize card\n");
516 /*
517 * Make sure the INIT command does not generate a command completion
518 * event by disabling interrupts.
519 */
520 hfa384x_disable_interrupts(dev);
521 if (prism2_hw_init(dev, 1)) {
522 printk(KERN_DEBUG "%s: Initialization after genesis mode "
523 "download failed\n", dev->name);
524 ret = -EIO;
525 goto out;
526 }
527
528 PDEBUG(DEBUG_EXTRA2, "Card initialized - running PRI only\n");
529 if (prism2_hw_init2(dev, 1)) {
530 printk(KERN_DEBUG "%s: Initialization(2) after genesis mode "
531 "download failed\n", dev->name);
532 ret = -EIO;
533 goto out;
534 }
535
536 out:
537 local->hw_downloading = 0;
538 return ret;
539}
540
541
542#ifdef PRISM2_NON_VOLATILE_DOWNLOAD
543/* Note! Non-volatile downloading functionality has not yet been tested
544 * thoroughly and it may corrupt flash image and effectively kill the card that
545 * is being updated. You have been warned. */
546
547static inline int prism2_download_block(struct net_device *dev,
548 u32 addr, u8 *data,
549 u32 bufaddr, int rest_len)
550{
551 u16 param0, param1;
552 int block_len;
553
554 block_len = rest_len < 4096 ? rest_len : 4096;
555
556 param0 = addr & 0xffff;
557 param1 = addr >> 16;
558
559 HFA384X_OUTW(block_len, HFA384X_PARAM2_OFF);
560 HFA384X_OUTW(param1, HFA384X_PARAM1_OFF);
561
562 if (hfa384x_cmd_wait(dev, HFA384X_CMDCODE_DOWNLOAD |
563 (HFA384X_PROGMODE_ENABLE_NON_VOLATILE << 8),
564 param0)) {
565 printk(KERN_WARNING "%s: Flash download command execution "
566 "failed\n", dev->name);
567 return -1;
568 }
569
570 if (hfa384x_to_aux(dev, bufaddr, block_len, data)) {
571 printk(KERN_WARNING "%s: flash download at 0x%08x "
572 "(len=%d) failed\n", dev->name, addr, block_len);
573 return -1;
574 }
575
576 HFA384X_OUTW(0, HFA384X_PARAM2_OFF);
577 HFA384X_OUTW(0, HFA384X_PARAM1_OFF);
578 if (hfa384x_cmd_wait(dev, HFA384X_CMDCODE_DOWNLOAD |
579 (HFA384X_PROGMODE_PROGRAM_NON_VOLATILE << 8),
580 0)) {
581 printk(KERN_WARNING "%s: Flash write command execution "
582 "failed\n", dev->name);
583 return -1;
584 }
585
586 return block_len;
587}
588
589
590static int prism2_download_nonvolatile(local_info_t *local,
591 struct prism2_download_data *dl)
592{
593 struct net_device *dev = local->dev;
594 int ret = 0, i;
595 struct {
596 __le16 page;
597 __le16 offset;
598 __le16 len;
599 } dlbuffer;
600 u32 bufaddr;
601
602 if (local->hw_downloading) {
603 printk(KERN_WARNING "%s: Already downloading - aborting new "
604 "request\n", dev->name);
605 return -1;
606 }
607
608 ret = local->func->get_rid(dev, HFA384X_RID_DOWNLOADBUFFER,
609 &dlbuffer, 6, 0);
610
611 if (ret < 0) {
612 printk(KERN_WARNING "%s: Could not read download buffer "
613 "parameters\n", dev->name);
614 goto out;
615 }
616
617 printk(KERN_DEBUG "Download buffer: %d bytes at 0x%04x:0x%04x\n",
618 le16_to_cpu(dlbuffer.len),
619 le16_to_cpu(dlbuffer.page),
620 le16_to_cpu(dlbuffer.offset));
621
622 bufaddr = (le16_to_cpu(dlbuffer.page) << 7) + le16_to_cpu(dlbuffer.offset);
623
624 local->hw_downloading = 1;
625
626 if (!local->pri_only) {
627 prism2_hw_shutdown(dev, 0);
628
629 if (prism2_hw_init(dev, 0)) {
630 printk(KERN_WARNING "%s: Could not initialize card for"
631 " download\n", dev->name);
632 ret = -1;
633 goto out;
634 }
635 }
636
637 hfa384x_disable_interrupts(dev);
638
639 if (prism2_enable_aux_port(dev, 1)) {
640 printk(KERN_WARNING "%s: Could not enable AUX port\n",
641 dev->name);
642 ret = -1;
643 goto out;
644 }
645
646 printk(KERN_DEBUG "%s: starting flash download\n", dev->name);
647 for (i = 0; i < dl->num_areas; i++) {
648 int rest_len = dl->data[i].len;
649 int data_off = 0;
650
651 while (rest_len > 0) {
652 int block_len;
653
654 block_len = prism2_download_block(
655 dev, dl->data[i].addr + data_off,
656 dl->data[i].data + data_off, bufaddr,
657 rest_len);
658
659 if (block_len < 0) {
660 ret = -1;
661 goto out;
662 }
663
664 rest_len -= block_len;
665 data_off += block_len;
666 }
667 }
668
669 HFA384X_OUTW(0, HFA384X_PARAM1_OFF);
670 HFA384X_OUTW(0, HFA384X_PARAM2_OFF);
671 if (hfa384x_cmd_wait(dev, HFA384X_CMDCODE_DOWNLOAD |
672 (HFA384X_PROGMODE_DISABLE << 8), 0)) {
673 printk(KERN_WARNING "%s: Download command execution failed\n",
674 dev->name);
675 ret = -1;
676 goto out;
677 }
678
679 if (prism2_enable_aux_port(dev, 0)) {
680 printk(KERN_DEBUG "%s: Disabling AUX port failed\n",
681 dev->name);
682 /* continue anyway.. restart should have taken care of this */
683 }
684
685 mdelay(5);
686
687 local->func->hw_reset(dev);
688 local->hw_downloading = 0;
689 if (prism2_hw_config(dev, 2)) {
690 printk(KERN_WARNING "%s: Card configuration after flash "
691 "download failed\n", dev->name);
692 ret = -1;
693 } else {
694 printk(KERN_INFO "%s: Card initialized successfully after "
695 "flash download\n", dev->name);
696 }
697
698 out:
699 local->hw_downloading = 0;
700 return ret;
701}
702#endif /* PRISM2_NON_VOLATILE_DOWNLOAD */
703
704
705static void prism2_download_free_data(struct prism2_download_data *dl)
706{
707 int i;
708
709 if (dl == NULL)
710 return;
711
712 for (i = 0; i < dl->num_areas; i++)
713 kfree(dl->data[i].data);
714 kfree(dl);
715}
716
717
718static int prism2_download(local_info_t *local,
719 struct prism2_download_param *param)
720{
721 int ret = 0;
722 int i;
723 u32 total_len = 0;
724 struct prism2_download_data *dl = NULL;
725
726 printk(KERN_DEBUG "prism2_download: dl_cmd=%d start_addr=0x%08x "
727 "num_areas=%d\n",
728 param->dl_cmd, param->start_addr, param->num_areas);
729
730 if (param->num_areas > 100) {
731 ret = -EINVAL;
732 goto out;
733 }
734
735 dl = kzalloc(struct_size(dl, data, param->num_areas), GFP_KERNEL);
736 if (dl == NULL) {
737 ret = -ENOMEM;
738 goto out;
739 }
740 dl->dl_cmd = param->dl_cmd;
741 dl->start_addr = param->start_addr;
742 dl->num_areas = param->num_areas;
743 for (i = 0; i < param->num_areas; i++) {
744 PDEBUG(DEBUG_EXTRA2,
745 " area %d: addr=0x%08x len=%d ptr=0x%p\n",
746 i, param->data[i].addr, param->data[i].len,
747 param->data[i].ptr);
748
749 dl->data[i].addr = param->data[i].addr;
750 dl->data[i].len = param->data[i].len;
751
752 total_len += param->data[i].len;
753 if (param->data[i].len > PRISM2_MAX_DOWNLOAD_AREA_LEN ||
754 total_len > PRISM2_MAX_DOWNLOAD_LEN) {
755 ret = -E2BIG;
756 goto out;
757 }
758
759 dl->data[i].data = kmalloc(dl->data[i].len, GFP_KERNEL);
760 if (dl->data[i].data == NULL) {
761 ret = -ENOMEM;
762 goto out;
763 }
764
765 if (copy_from_user(dl->data[i].data, param->data[i].ptr,
766 param->data[i].len)) {
767 ret = -EFAULT;
768 goto out;
769 }
770 }
771
772 switch (param->dl_cmd) {
773 case PRISM2_DOWNLOAD_VOLATILE:
774 case PRISM2_DOWNLOAD_VOLATILE_PERSISTENT:
775 ret = prism2_download_volatile(local, dl);
776 break;
777 case PRISM2_DOWNLOAD_VOLATILE_GENESIS:
778 case PRISM2_DOWNLOAD_VOLATILE_GENESIS_PERSISTENT:
779 ret = prism2_download_genesis(local, dl);
780 break;
781 case PRISM2_DOWNLOAD_NON_VOLATILE:
782#ifdef PRISM2_NON_VOLATILE_DOWNLOAD
783 ret = prism2_download_nonvolatile(local, dl);
784#else /* PRISM2_NON_VOLATILE_DOWNLOAD */
785 printk(KERN_INFO "%s: non-volatile downloading not enabled\n",
786 local->dev->name);
787 ret = -EOPNOTSUPP;
788#endif /* PRISM2_NON_VOLATILE_DOWNLOAD */
789 break;
790 default:
791 printk(KERN_DEBUG "%s: unsupported download command %d\n",
792 local->dev->name, param->dl_cmd);
793 ret = -EINVAL;
794 break;
795 }
796
797 out:
798 if (ret == 0 && dl &&
799 param->dl_cmd == PRISM2_DOWNLOAD_VOLATILE_GENESIS_PERSISTENT) {
800 prism2_download_free_data(local->dl_pri);
801 local->dl_pri = dl;
802 } else if (ret == 0 && dl &&
803 param->dl_cmd == PRISM2_DOWNLOAD_VOLATILE_PERSISTENT) {
804 prism2_download_free_data(local->dl_sec);
805 local->dl_sec = dl;
806 } else
807 prism2_download_free_data(dl);
808
809 return ret;
810}
drivers/net/wireless/intersil/hostap/hostap_hw.c+0−3387
@@ -1,3387 +0,0 @@
1// SPDX-License-Identifier: GPL-2.0-only
2/*
3 * Host AP (software wireless LAN access point) driver for
4 * Intersil Prism2/2.5/3.
5 *
6 * Copyright (c) 2001-2002, SSH Communications Security Corp and Jouni Malinen
7 * <j@w1.fi>
8 * Copyright (c) 2002-2005, Jouni Malinen <j@w1.fi>
9 *
10 * FIX:
11 * - there is currently no way of associating TX packets to correct wds device
12 * when TX Exc/OK event occurs, so all tx_packets and some
13 * tx_errors/tx_dropped are added to the main netdevice; using sw_support
14 * field in txdesc might be used to fix this (using Alloc event to increment
15 * tx_packets would need some further info in txfid table)
16 *
17 * Buffer Access Path (BAP) usage:
18 * Prism2 cards have two separate BAPs for accessing the card memory. These
19 * should allow concurrent access to two different frames and the driver
20 * previously used BAP0 for sending data and BAP1 for receiving data.
21 * However, there seems to be number of issues with concurrent access and at
22 * least one know hardware bug in using BAP0 and BAP1 concurrently with PCI
23 * Prism2.5. Therefore, the driver now only uses BAP0 for moving data between
24 * host and card memories. BAP0 accesses are protected with local->baplock
25 * (spin_lock_bh) to prevent concurrent use.
26 */
27
28
29
30#include <asm/delay.h>
31#include <linux/uaccess.h>
32
33#include <linux/slab.h>
34#include <linux/netdevice.h>
35#include <linux/etherdevice.h>
36#include <linux/proc_fs.h>
37#include <linux/seq_file.h>
38#include <linux/if_arp.h>
39#include <linux/delay.h>
40#include <linux/random.h>
41#include <linux/wait.h>
42#include <linux/sched/signal.h>
43#include <linux/rtnetlink.h>
44#include <linux/wireless.h>
45#include <net/iw_handler.h>
46#include <net/lib80211.h>
47#include <asm/irq.h>
48
49#include "hostap_80211.h"
50#include "hostap.h"
51#include "hostap_ap.h"
52
53
54/* #define final_version */
55
56static int mtu = 1500;
57module_param(mtu, int, 0444);
58MODULE_PARM_DESC(mtu, "Maximum transfer unit");
59
60static int channel[MAX_PARM_DEVICES] = { 3, DEF_INTS };
61module_param_array(channel, int, NULL, 0444);
62MODULE_PARM_DESC(channel, "Initial channel");
63
64static char essid[33] = "test";
65module_param_string(essid, essid, sizeof(essid), 0444);
66MODULE_PARM_DESC(essid, "Host AP's ESSID");
67
68static int iw_mode[MAX_PARM_DEVICES] = { IW_MODE_MASTER, DEF_INTS };
69module_param_array(iw_mode, int, NULL, 0444);
70MODULE_PARM_DESC(iw_mode, "Initial operation mode");
71
72static int beacon_int[MAX_PARM_DEVICES] = { 100, DEF_INTS };
73module_param_array(beacon_int, int, NULL, 0444);
74MODULE_PARM_DESC(beacon_int, "Beacon interval (1 = 1024 usec)");
75
76static int dtim_period[MAX_PARM_DEVICES] = { 1, DEF_INTS };
77module_param_array(dtim_period, int, NULL, 0444);
78MODULE_PARM_DESC(dtim_period, "DTIM period");
79
80static char dev_template[16] = "wlan%d";
81module_param_string(dev_template, dev_template, sizeof(dev_template), 0444);
82MODULE_PARM_DESC(dev_template, "Prefix for network device name (default: "
83 "wlan%d)");
84
85#ifdef final_version
86#define EXTRA_EVENTS_WTERR 0
87#else
88/* check WTERR events (Wait Time-out) in development versions */
89#define EXTRA_EVENTS_WTERR HFA384X_EV_WTERR
90#endif
91
92/* Events that will be using BAP0 */
93#define HFA384X_BAP0_EVENTS \
94 (HFA384X_EV_TXEXC | HFA384X_EV_RX | HFA384X_EV_INFO | HFA384X_EV_TX)
95
96/* event mask, i.e., events that will result in an interrupt */
97#define HFA384X_EVENT_MASK \
98 (HFA384X_BAP0_EVENTS | HFA384X_EV_ALLOC | HFA384X_EV_INFDROP | \
99 HFA384X_EV_CMD | HFA384X_EV_TICK | \
100 EXTRA_EVENTS_WTERR)
101
102/* Default TX control flags: use 802.11 headers and request interrupt for
103 * failed transmits. Frames that request ACK callback, will add
104 * _TX_OK flag and _ALT_RTRY flag may be used to select different retry policy.
105 */
106#define HFA384X_TX_CTRL_FLAGS \
107 (HFA384X_TX_CTRL_802_11 | HFA384X_TX_CTRL_TX_EX)
108
109
110/* ca. 1 usec */
111#define HFA384X_CMD_BUSY_TIMEOUT 5000
112#define HFA384X_BAP_BUSY_TIMEOUT 50000
113
114/* ca. 10 usec */
115#define HFA384X_CMD_COMPL_TIMEOUT 20000
116#define HFA384X_DL_COMPL_TIMEOUT 1000000
117
118/* Wait times for initialization; yield to other processes to avoid busy
119 * waiting for long time. */
120#define HFA384X_INIT_TIMEOUT (HZ / 2) /* 500 ms */
121#define HFA384X_ALLOC_COMPL_TIMEOUT (HZ / 20) /* 50 ms */
122
123
124static void prism2_hw_reset(struct net_device *dev);
125static void prism2_check_sta_fw_version(local_info_t *local);
126
127#ifdef PRISM2_DOWNLOAD_SUPPORT
128/* hostap_download.c */
129static const struct proc_ops prism2_download_aux_dump_proc_ops;
130static u8 * prism2_read_pda(struct net_device *dev);
131static int prism2_download(local_info_t *local,
132 struct prism2_download_param *param);
133static void prism2_download_free_data(struct prism2_download_data *dl);
134static int prism2_download_volatile(local_info_t *local,
135 struct prism2_download_data *param);
136static int prism2_download_genesis(local_info_t *local,
137 struct prism2_download_data *param);
138static int prism2_get_ram_size(local_info_t *local);
139#endif /* PRISM2_DOWNLOAD_SUPPORT */
140
141
142
143
144#ifndef final_version
145/* magic value written to SWSUPPORT0 reg. for detecting whether card is still
146 * present */
147#define HFA384X_MAGIC 0x8A32
148#endif
149
150static void hfa384x_read_regs(struct net_device *dev,
151 struct hfa384x_regs *regs)
152{
153 regs->cmd = HFA384X_INW(HFA384X_CMD_OFF);
154 regs->evstat = HFA384X_INW(HFA384X_EVSTAT_OFF);
155 regs->offset0 = HFA384X_INW(HFA384X_OFFSET0_OFF);
156 regs->offset1 = HFA384X_INW(HFA384X_OFFSET1_OFF);
157 regs->swsupport0 = HFA384X_INW(HFA384X_SWSUPPORT0_OFF);
158}
159
160
161/**
162 * __hostap_cmd_queue_free - Free Prism2 command queue entry (private)
163 * @local: pointer to private Host AP driver data
164 * @entry: Prism2 command queue entry to be freed
165 * @del_req: request the entry to be removed
166 *
167 * Internal helper function for freeing Prism2 command queue entries.
168 * Caller must have acquired local->cmdlock before calling this function.
169 */
170static inline void __hostap_cmd_queue_free(local_info_t *local,
171 struct hostap_cmd_queue *entry,
172 int del_req)
173{
174 if (del_req) {
175 entry->del_req = 1;
176 if (!list_empty(&entry->list)) {
177 list_del_init(&entry->list);
178 local->cmd_queue_len--;
179 }
180 }
181
182 if (refcount_dec_and_test(&entry->usecnt) && entry->del_req)
183 kfree(entry);
184}
185
186
187/**
188 * hostap_cmd_queue_free - Free Prism2 command queue entry
189 * @local: pointer to private Host AP driver data
190 * @entry: Prism2 command queue entry to be freed
191 * @del_req: request the entry to be removed
192 *
193 * Free a Prism2 command queue entry.
194 */
195static inline void hostap_cmd_queue_free(local_info_t *local,
196 struct hostap_cmd_queue *entry,
197 int del_req)
198{
199 unsigned long flags;
200
201 spin_lock_irqsave(&local->cmdlock, flags);
202 __hostap_cmd_queue_free(local, entry, del_req);
203 spin_unlock_irqrestore(&local->cmdlock, flags);
204}
205
206
207/**
208 * prism2_clear_cmd_queue - Free all pending Prism2 command queue entries
209 * @local: pointer to private Host AP driver data
210 */
211static void prism2_clear_cmd_queue(local_info_t *local)
212{
213 struct list_head *ptr, *n;
214 unsigned long flags;
215 struct hostap_cmd_queue *entry;
216
217 spin_lock_irqsave(&local->cmdlock, flags);
218 list_for_each_safe(ptr, n, &local->cmd_queue) {
219 entry = list_entry(ptr, struct hostap_cmd_queue, list);
220 refcount_inc(&entry->usecnt);
221 printk(KERN_DEBUG "%s: removed pending cmd_queue entry "
222 "(type=%d, cmd=0x%04x, param0=0x%04x)\n",
223 local->dev->name, entry->type, entry->cmd,
224 entry->param0);
225 __hostap_cmd_queue_free(local, entry, 1);
226 }
227 if (local->cmd_queue_len) {
228 /* This should not happen; print debug message and clear
229 * queue length. */
230 printk(KERN_DEBUG "%s: cmd_queue_len (%d) not zero after "
231 "flush\n", local->dev->name, local->cmd_queue_len);
232 local->cmd_queue_len = 0;
233 }
234 spin_unlock_irqrestore(&local->cmdlock, flags);
235}
236
237
238/**
239 * hfa384x_cmd_issue - Issue a Prism2 command to the hardware
240 * @dev: pointer to net_device
241 * @entry: Prism2 command queue entry to be issued
242 */
243static int hfa384x_cmd_issue(struct net_device *dev,
244 struct hostap_cmd_queue *entry)
245{
246 struct hostap_interface *iface;
247 local_info_t *local;
248 int tries;
249 u16 reg;
250 unsigned long flags;
251
252 iface = netdev_priv(dev);
253 local = iface->local;
254
255 if (local->func->card_present && !local->func->card_present(local))
256 return -ENODEV;
257
258 if (entry->issued) {
259 printk(KERN_DEBUG "%s: driver bug - re-issuing command @%p\n",
260 dev->name, entry);
261 }
262
263 /* wait until busy bit is clear; this should always be clear since the
264 * commands are serialized */
265 tries = HFA384X_CMD_BUSY_TIMEOUT;
266 while (HFA384X_INW(HFA384X_CMD_OFF) & HFA384X_CMD_BUSY && tries > 0) {
267 tries--;
268 udelay(1);
269 }
270#ifndef final_version
271 if (tries != HFA384X_CMD_BUSY_TIMEOUT) {
272 prism2_io_debug_error(dev, 1);
273 printk(KERN_DEBUG "%s: hfa384x_cmd_issue: cmd reg was busy "
274 "for %d usec\n", dev->name,
275 HFA384X_CMD_BUSY_TIMEOUT - tries);
276 }
277#endif
278 if (tries == 0) {
279 reg = HFA384X_INW(HFA384X_CMD_OFF);
280 prism2_io_debug_error(dev, 2);
281 printk(KERN_DEBUG "%s: hfa384x_cmd_issue - timeout - "
282 "reg=0x%04x\n", dev->name, reg);
283 return -ETIMEDOUT;
284 }
285
286 /* write command */
287 spin_lock_irqsave(&local->cmdlock, flags);
288 HFA384X_OUTW(entry->param0, HFA384X_PARAM0_OFF);
289 HFA384X_OUTW(entry->param1, HFA384X_PARAM1_OFF);
290 HFA384X_OUTW(entry->cmd, HFA384X_CMD_OFF);
291 entry->issued = 1;
292 spin_unlock_irqrestore(&local->cmdlock, flags);
293
294 return 0;
295}
296
297
298/**
299 * hfa384x_cmd - Issue a Prism2 command and wait (sleep) for completion
300 * @dev: pointer to net_device
301 * @cmd: Prism2 command code (HFA384X_CMD_CODE_*)
302 * @param0: value for Param0 register
303 * @param1: value for Param1 register (pointer; %NULL if not used)
304 * @resp0: pointer for Resp0 data or %NULL if Resp0 is not needed
305 *
306 * Issue given command (possibly after waiting in command queue) and sleep
307 * until the command is completed (or timed out or interrupted). This can be
308 * called only from user process context.
309 */
310static int hfa384x_cmd(struct net_device *dev, u16 cmd, u16 param0,
311 u16 *param1, u16 *resp0)
312{
313 struct hostap_interface *iface;
314 local_info_t *local;
315 int err, res, issue, issued = 0;
316 unsigned long flags;
317 struct hostap_cmd_queue *entry;
318 DECLARE_WAITQUEUE(wait, current);
319
320 iface = netdev_priv(dev);
321 local = iface->local;
322
323 if (local->cmd_queue_len >= HOSTAP_CMD_QUEUE_MAX_LEN) {
324 printk(KERN_DEBUG "%s: hfa384x_cmd: cmd_queue full\n",
325 dev->name);
326 return -1;
327 }
328
329 if (signal_pending(current))
330 return -EINTR;
331
332 entry = kzalloc(sizeof(*entry), GFP_ATOMIC);
333 if (entry == NULL)
334 return -ENOMEM;
335
336 refcount_set(&entry->usecnt, 1);
337 entry->type = CMD_SLEEP;
338 entry->cmd = cmd;
339 entry->param0 = param0;
340 if (param1)
341 entry->param1 = *param1;
342 init_waitqueue_head(&entry->compl);
343
344 /* prepare to wait for command completion event, but do not sleep yet
345 */
346 add_wait_queue(&entry->compl, &wait);
347 set_current_state(TASK_INTERRUPTIBLE);
348
349 spin_lock_irqsave(&local->cmdlock, flags);
350 issue = list_empty(&local->cmd_queue);
351 if (issue)
352 entry->issuing = 1;
353 list_add_tail(&entry->list, &local->cmd_queue);
354 local->cmd_queue_len++;
355 spin_unlock_irqrestore(&local->cmdlock, flags);
356
357 err = 0;
358 if (!issue)
359 goto wait_completion;
360
361 if (signal_pending(current))
362 err = -EINTR;
363
364 if (!err) {
365 if (hfa384x_cmd_issue(dev, entry))
366 err = -ETIMEDOUT;
367 else
368 issued = 1;
369 }
370
371 wait_completion:
372 if (!err && entry->type != CMD_COMPLETED) {
373 /* sleep until command is completed or timed out */
374 res = schedule_timeout(2 * HZ);
375 } else
376 res = -1;
377
378 if (!err && signal_pending(current))
379 err = -EINTR;
380
381 if (err && issued) {
382 /* the command was issued, so a CmdCompl event should occur
383 * soon; however, there's a pending signal and
384 * schedule_timeout() would be interrupted; wait a short period
385 * of time to avoid removing entry from the list before
386 * CmdCompl event */
387 udelay(300);
388 }
389
390 set_current_state(TASK_RUNNING);
391 remove_wait_queue(&entry->compl, &wait);
392
393 /* If entry->list is still in the list, it must be removed
394 * first and in this case prism2_cmd_ev() does not yet have
395 * local reference to it, and the data can be kfree()'d
396 * here. If the command completion event is still generated,
397 * it will be assigned to next (possibly) pending command, but
398 * the driver will reset the card anyway due to timeout
399 *
400 * If the entry is not in the list prism2_cmd_ev() has a local
401 * reference to it, but keeps cmdlock as long as the data is
402 * needed, so the data can be kfree()'d here. */
403
404 /* FIX: if the entry->list is in the list, it has not been completed
405 * yet, so removing it here is somewhat wrong.. this could cause
406 * references to freed memory and next list_del() causing NULL pointer
407 * dereference.. it would probably be better to leave the entry in the
408 * list and the list should be emptied during hw reset */
409
410 spin_lock_irqsave(&local->cmdlock, flags);
411 if (!list_empty(&entry->list)) {
412 printk(KERN_DEBUG "%s: hfa384x_cmd: entry still in list? "
413 "(entry=%p, type=%d, res=%d)\n", dev->name, entry,
414 entry->type, res);
415 list_del_init(&entry->list);
416 local->cmd_queue_len--;
417 }
418 spin_unlock_irqrestore(&local->cmdlock, flags);
419
420 if (err) {
421 printk(KERN_DEBUG "%s: hfa384x_cmd: interrupted; err=%d\n",
422 dev->name, err);
423 res = err;
424 goto done;
425 }
426
427 if (entry->type != CMD_COMPLETED) {
428 u16 reg = HFA384X_INW(HFA384X_EVSTAT_OFF);
429 printk(KERN_DEBUG "%s: hfa384x_cmd: command was not "
430 "completed (res=%d, entry=%p, type=%d, cmd=0x%04x, "
431 "param0=0x%04x, EVSTAT=%04x INTEN=%04x)\n", dev->name,
432 res, entry, entry->type, entry->cmd, entry->param0, reg,
433 HFA384X_INW(HFA384X_INTEN_OFF));
434 if (reg & HFA384X_EV_CMD) {
435 /* Command completion event is pending, but the
436 * interrupt was not delivered - probably an issue
437 * with pcmcia-cs configuration. */
438 printk(KERN_WARNING "%s: interrupt delivery does not "
439 "seem to work\n", dev->name);
440 }
441 prism2_io_debug_error(dev, 3);
442 res = -ETIMEDOUT;
443 goto done;
444 }
445
446 if (resp0 != NULL)
447 *resp0 = entry->resp0;
448#ifndef final_version
449 if (entry->res) {
450 printk(KERN_DEBUG "%s: CMD=0x%04x => res=0x%02x, "
451 "resp0=0x%04x\n",
452 dev->name, cmd, entry->res, entry->resp0);
453 }
454#endif /* final_version */
455
456 res = entry->res;
457 done:
458 hostap_cmd_queue_free(local, entry, 1);
459 return res;
460}
461
462
463/**
464 * hfa384x_cmd_callback - Issue a Prism2 command; callback when completed
465 * @dev: pointer to net_device
466 * @cmd: Prism2 command code (HFA384X_CMD_CODE_*)
467 * @param0: value for Param0 register
468 * @callback: command completion callback function (%NULL = no callback)
469 * @context: context data to be given to the callback function
470 *
471 * Issue given command (possibly after waiting in command queue) and use
472 * callback function to indicate command completion. This can be called both
473 * from user and interrupt context. The callback function will be called in
474 * hardware IRQ context. It can be %NULL, when no function is called when
475 * command is completed.
476 */
477static int hfa384x_cmd_callback(struct net_device *dev, u16 cmd, u16 param0,
478 void (*callback)(struct net_device *dev,
479 long context, u16 resp0,
480 u16 status),
481 long context)
482{
483 struct hostap_interface *iface;
484 local_info_t *local;
485 int issue, ret;
486 unsigned long flags;
487 struct hostap_cmd_queue *entry;
488
489 iface = netdev_priv(dev);
490 local = iface->local;
491
492 if (local->cmd_queue_len >= HOSTAP_CMD_QUEUE_MAX_LEN + 2) {
493 printk(KERN_DEBUG "%s: hfa384x_cmd: cmd_queue full\n",
494 dev->name);
495 return -1;
496 }
497
498 entry = kzalloc(sizeof(*entry), GFP_ATOMIC);
499 if (entry == NULL)
500 return -ENOMEM;
501
502 refcount_set(&entry->usecnt, 1);
503 entry->type = CMD_CALLBACK;
504 entry->cmd = cmd;
505 entry->param0 = param0;
506 entry->callback = callback;
507 entry->context = context;
508
509 spin_lock_irqsave(&local->cmdlock, flags);
510 issue = list_empty(&local->cmd_queue);
511 if (issue)
512 entry->issuing = 1;
513 list_add_tail(&entry->list, &local->cmd_queue);
514 local->cmd_queue_len++;
515 spin_unlock_irqrestore(&local->cmdlock, flags);
516
517 if (issue && hfa384x_cmd_issue(dev, entry))
518 ret = -ETIMEDOUT;
519 else
520 ret = 0;
521
522 hostap_cmd_queue_free(local, entry, ret);
523
524 return ret;
525}
526
527
528/**
529 * __hfa384x_cmd_no_wait - Issue a Prism2 command (private)
530 * @dev: pointer to net_device
531 * @cmd: Prism2 command code (HFA384X_CMD_CODE_*)
532 * @param0: value for Param0 register
533 * @io_debug_num: I/O debug error number
534 *
535 * Shared helper function for hfa384x_cmd_wait() and hfa384x_cmd_no_wait().
536 */
537static int __hfa384x_cmd_no_wait(struct net_device *dev, u16 cmd, u16 param0,
538 int io_debug_num)
539{
540 int tries;
541 u16 reg;
542
543 /* wait until busy bit is clear; this should always be clear since the
544 * commands are serialized */
545 tries = HFA384X_CMD_BUSY_TIMEOUT;
546 while (HFA384X_INW(HFA384X_CMD_OFF) & HFA384X_CMD_BUSY && tries > 0) {
547 tries--;
548 udelay(1);
549 }
550 if (tries == 0) {
551 reg = HFA384X_INW(HFA384X_CMD_OFF);
552 prism2_io_debug_error(dev, io_debug_num);
553 printk(KERN_DEBUG "%s: __hfa384x_cmd_no_wait(%d) - timeout - "
554 "reg=0x%04x\n", dev->name, io_debug_num, reg);
555 return -ETIMEDOUT;
556 }
557
558 /* write command */
559 HFA384X_OUTW(param0, HFA384X_PARAM0_OFF);
560 HFA384X_OUTW(cmd, HFA384X_CMD_OFF);
561
562 return 0;
563}
564
565
566/**
567 * hfa384x_cmd_wait - Issue a Prism2 command and busy wait for completion
568 * @dev: pointer to net_device
569 * @cmd: Prism2 command code (HFA384X_CMD_CODE_*)
570 * @param0: value for Param0 register
571 */
572static int hfa384x_cmd_wait(struct net_device *dev, u16 cmd, u16 param0)
573{
574 int res, tries;
575 u16 reg;
576
577 res = __hfa384x_cmd_no_wait(dev, cmd, param0, 4);
578 if (res)
579 return res;
580
581 /* wait for command completion */
582 if ((cmd & HFA384X_CMDCODE_MASK) == HFA384X_CMDCODE_DOWNLOAD)
583 tries = HFA384X_DL_COMPL_TIMEOUT;
584 else
585 tries = HFA384X_CMD_COMPL_TIMEOUT;
586
587 while (!(HFA384X_INW(HFA384X_EVSTAT_OFF) & HFA384X_EV_CMD) &&
588 tries > 0) {
589 tries--;
590 udelay(10);
591 }
592 if (tries == 0) {
593 reg = HFA384X_INW(HFA384X_EVSTAT_OFF);
594 prism2_io_debug_error(dev, 5);
595 printk(KERN_DEBUG "%s: hfa384x_cmd_wait - timeout2 - "
596 "reg=0x%04x\n", dev->name, reg);
597 return -ETIMEDOUT;
598 }
599
600 res = (HFA384X_INW(HFA384X_STATUS_OFF) &
601 (BIT(14) | BIT(13) | BIT(12) | BIT(11) | BIT(10) | BIT(9) |
602 BIT(8))) >> 8;
603#ifndef final_version
604 if (res) {
605 printk(KERN_DEBUG "%s: CMD=0x%04x => res=0x%02x\n",
606 dev->name, cmd, res);
607 }
608#endif
609
610 HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_EVACK_OFF);
611
612 return res;
613}
614
615
616/**
617 * hfa384x_cmd_no_wait - Issue a Prism2 command; do not wait for completion
618 * @dev: pointer to net_device
619 * @cmd: Prism2 command code (HFA384X_CMD_CODE_*)
620 * @param0: value for Param0 register
621 */
622static inline int hfa384x_cmd_no_wait(struct net_device *dev, u16 cmd,
623 u16 param0)
624{
625 return __hfa384x_cmd_no_wait(dev, cmd, param0, 6);
626}
627
628
629/**
630 * prism2_cmd_ev - Prism2 command completion event handler
631 * @dev: pointer to net_device
632 *
633 * Interrupt handler for command completion events. Called by the main
634 * interrupt handler in hardware IRQ context. Read Resp0 and status registers
635 * from the hardware and ACK the event. Depending on the issued command type
636 * either wake up the sleeping process that is waiting for command completion
637 * or call the callback function. Issue the next command, if one is pending.
638 */
639static void prism2_cmd_ev(struct net_device *dev)
640{
641 struct hostap_interface *iface;
642 local_info_t *local;
643 struct hostap_cmd_queue *entry = NULL;
644
645 iface = netdev_priv(dev);
646 local = iface->local;
647
648 spin_lock(&local->cmdlock);
649 if (!list_empty(&local->cmd_queue)) {
650 entry = list_entry(local->cmd_queue.next,
651 struct hostap_cmd_queue, list);
652 refcount_inc(&entry->usecnt);
653 list_del_init(&entry->list);
654 local->cmd_queue_len--;
655
656 if (!entry->issued) {
657 printk(KERN_DEBUG "%s: Command completion event, but "
658 "cmd not issued\n", dev->name);
659 __hostap_cmd_queue_free(local, entry, 1);
660 entry = NULL;
661 }
662 }
663 spin_unlock(&local->cmdlock);
664
665 if (!entry) {
666 HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_EVACK_OFF);
667 printk(KERN_DEBUG "%s: Command completion event, but no "
668 "pending commands\n", dev->name);
669 return;
670 }
671
672 entry->resp0 = HFA384X_INW(HFA384X_RESP0_OFF);
673 entry->res = (HFA384X_INW(HFA384X_STATUS_OFF) &
674 (BIT(14) | BIT(13) | BIT(12) | BIT(11) | BIT(10) |
675 BIT(9) | BIT(8))) >> 8;
676 HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_EVACK_OFF);
677
678 /* TODO: rest of the CmdEv handling could be moved to tasklet */
679 if (entry->type == CMD_SLEEP) {
680 entry->type = CMD_COMPLETED;
681 wake_up_interruptible(&entry->compl);
682 } else if (entry->type == CMD_CALLBACK) {
683 if (entry->callback)
684 entry->callback(dev, entry->context, entry->resp0,
685 entry->res);
686 } else {
687 printk(KERN_DEBUG "%s: Invalid command completion type %d\n",
688 dev->name, entry->type);
689 }
690 hostap_cmd_queue_free(local, entry, 1);
691
692 /* issue next command, if pending */
693 entry = NULL;
694 spin_lock(&local->cmdlock);
695 if (!list_empty(&local->cmd_queue)) {
696 entry = list_entry(local->cmd_queue.next,
697 struct hostap_cmd_queue, list);
698 if (entry->issuing) {
699 /* hfa384x_cmd() has already started issuing this
700 * command, so do not start here */
701 entry = NULL;
702 }
703 if (entry)
704 refcount_inc(&entry->usecnt);
705 }
706 spin_unlock(&local->cmdlock);
707
708 if (entry) {
709 /* issue next command; if command issuing fails, remove the
710 * entry from cmd_queue */
711 int res = hfa384x_cmd_issue(dev, entry);
712 spin_lock(&local->cmdlock);
713 __hostap_cmd_queue_free(local, entry, res);
714 spin_unlock(&local->cmdlock);
715 }
716}
717
718
719static int hfa384x_wait_offset(struct net_device *dev, u16 o_off)
720{
721 int tries = HFA384X_BAP_BUSY_TIMEOUT;
722 int res = HFA384X_INW(o_off) & HFA384X_OFFSET_BUSY;
723
724 while (res && tries > 0) {
725 tries--;
726 udelay(1);
727 res = HFA384X_INW(o_off) & HFA384X_OFFSET_BUSY;
728 }
729 return res;
730}
731
732
733/* Offset must be even */
734static int hfa384x_setup_bap(struct net_device *dev, u16 bap, u16 id,
735 int offset)
736{
737 u16 o_off, s_off;
738 int ret = 0;
739
740 if (offset % 2 || bap > 1)
741 return -EINVAL;
742
743 if (bap == BAP1) {
744 o_off = HFA384X_OFFSET1_OFF;
745 s_off = HFA384X_SELECT1_OFF;
746 } else {
747 o_off = HFA384X_OFFSET0_OFF;
748 s_off = HFA384X_SELECT0_OFF;
749 }
750
751 if (hfa384x_wait_offset(dev, o_off)) {
752 prism2_io_debug_error(dev, 7);
753 printk(KERN_DEBUG "%s: hfa384x_setup_bap - timeout before\n",
754 dev->name);
755 ret = -ETIMEDOUT;
756 goto out;
757 }
758
759 HFA384X_OUTW(id, s_off);
760 HFA384X_OUTW(offset, o_off);
761
762 if (hfa384x_wait_offset(dev, o_off)) {
763 prism2_io_debug_error(dev, 8);
764 printk(KERN_DEBUG "%s: hfa384x_setup_bap - timeout after\n",
765 dev->name);
766 ret = -ETIMEDOUT;
767 goto out;
768 }
769#ifndef final_version
770 if (HFA384X_INW(o_off) & HFA384X_OFFSET_ERR) {
771 prism2_io_debug_error(dev, 9);
772 printk(KERN_DEBUG "%s: hfa384x_setup_bap - offset error "
773 "(%d,0x04%x,%d); reg=0x%04x\n",
774 dev->name, bap, id, offset, HFA384X_INW(o_off));
775 ret = -EINVAL;
776 }
777#endif
778
779 out:
780 return ret;
781}
782
783
784static int hfa384x_get_rid(struct net_device *dev, u16 rid, void *buf, int len,
785 int exact_len)
786{
787 struct hostap_interface *iface;
788 local_info_t *local;
789 int res, rlen = 0;
790 struct hfa384x_rid_hdr rec;
791
792 iface = netdev_priv(dev);
793 local = iface->local;
794
795 if (local->no_pri) {
796 printk(KERN_DEBUG "%s: cannot get RID %04x (len=%d) - no PRI "
797 "f/w\n", dev->name, rid, len);
798 return -ENOTTY; /* Well.. not really correct, but return
799 * something unique enough.. */
800 }
801
802 if ((local->func->card_present && !local->func->card_present(local)) ||
803 local->hw_downloading)
804 return -ENODEV;
805
806 res = mutex_lock_interruptible(&local->rid_bap_mtx);
807 if (res)
808 return res;
809
810 res = hfa384x_cmd(dev, HFA384X_CMDCODE_ACCESS, rid, NULL, NULL);
811 if (res) {
812 printk(KERN_DEBUG "%s: hfa384x_get_rid: CMDCODE_ACCESS failed "
813 "(res=%d, rid=%04x, len=%d)\n",
814 dev->name, res, rid, len);
815 mutex_unlock(&local->rid_bap_mtx);
816 return res;
817 }
818
819 spin_lock_bh(&local->baplock);
820
821 res = hfa384x_setup_bap(dev, BAP0, rid, 0);
822 if (res)
823 goto unlock;
824
825 res = hfa384x_from_bap(dev, BAP0, &rec, sizeof(rec));
826 if (res)
827 goto unlock;
828
829 if (le16_to_cpu(rec.len) == 0) {
830 /* RID not available */
831 res = -ENODATA;
832 goto unlock;
833 }
834
835 rlen = (le16_to_cpu(rec.len) - 1) * 2;
836 if (exact_len && rlen != len) {
837 printk(KERN_DEBUG "%s: hfa384x_get_rid - RID len mismatch: "
838 "rid=0x%04x, len=%d (expected %d)\n",
839 dev->name, rid, rlen, len);
840 res = -ENODATA;
841 }
842
843 res = hfa384x_from_bap(dev, BAP0, buf, len);
844
845unlock:
846 spin_unlock_bh(&local->baplock);
847 mutex_unlock(&local->rid_bap_mtx);
848
849 if (res) {
850 if (res != -ENODATA)
851 printk(KERN_DEBUG "%s: hfa384x_get_rid (rid=%04x, "
852 "len=%d) - failed - res=%d\n", dev->name, rid,
853 len, res);
854 if (res == -ETIMEDOUT)
855 prism2_hw_reset(dev);
856 return res;
857 }
858
859 return rlen;
860}
861
862
863static int hfa384x_set_rid(struct net_device *dev, u16 rid, void *buf, int len)
864{
865 struct hostap_interface *iface;
866 local_info_t *local;
867 struct hfa384x_rid_hdr rec;
868 int res;
869
870 iface = netdev_priv(dev);
871 local = iface->local;
872
873 if (local->no_pri) {
874 printk(KERN_DEBUG "%s: cannot set RID %04x (len=%d) - no PRI "
875 "f/w\n", dev->name, rid, len);
876 return -ENOTTY; /* Well.. not really correct, but return
877 * something unique enough.. */
878 }
879
880 if ((local->func->card_present && !local->func->card_present(local)) ||
881 local->hw_downloading)
882 return -ENODEV;
883
884 rec.rid = cpu_to_le16(rid);
885 /* RID len in words and +1 for rec.rid */
886 rec.len = cpu_to_le16(len / 2 + len % 2 + 1);
887
888 res = mutex_lock_interruptible(&local->rid_bap_mtx);
889 if (res)
890 return res;
891
892 spin_lock_bh(&local->baplock);
893 res = hfa384x_setup_bap(dev, BAP0, rid, 0);
894 if (!res)
895 res = hfa384x_to_bap(dev, BAP0, &rec, sizeof(rec));
896 if (!res)
897 res = hfa384x_to_bap(dev, BAP0, buf, len);
898 spin_unlock_bh(&local->baplock);
899
900 if (res) {
901 printk(KERN_DEBUG "%s: hfa384x_set_rid (rid=%04x, len=%d) - "
902 "failed - res=%d\n", dev->name, rid, len, res);
903 mutex_unlock(&local->rid_bap_mtx);
904 return res;
905 }
906
907 res = hfa384x_cmd(dev, HFA384X_CMDCODE_ACCESS_WRITE, rid, NULL, NULL);
908 mutex_unlock(&local->rid_bap_mtx);
909
910 if (res) {
911 printk(KERN_DEBUG "%s: hfa384x_set_rid: CMDCODE_ACCESS_WRITE "
912 "failed (res=%d, rid=%04x, len=%d)\n",
913 dev->name, res, rid, len);
914
915 if (res == -ETIMEDOUT)
916 prism2_hw_reset(dev);
917 }
918
919 return res;
920}
921
922
923static void hfa384x_disable_interrupts(struct net_device *dev)
924{
925 /* disable interrupts and clear event status */
926 HFA384X_OUTW(0, HFA384X_INTEN_OFF);
927 HFA384X_OUTW(0xffff, HFA384X_EVACK_OFF);
928}
929
930
931static void hfa384x_enable_interrupts(struct net_device *dev)
932{
933 /* ack pending events and enable interrupts from selected events */
934 HFA384X_OUTW(0xffff, HFA384X_EVACK_OFF);
935 HFA384X_OUTW(HFA384X_EVENT_MASK, HFA384X_INTEN_OFF);
936}
937
938
939static void hfa384x_events_no_bap0(struct net_device *dev)
940{
941 HFA384X_OUTW(HFA384X_EVENT_MASK & ~HFA384X_BAP0_EVENTS,
942 HFA384X_INTEN_OFF);
943}
944
945
946static void hfa384x_events_all(struct net_device *dev)
947{
948 HFA384X_OUTW(HFA384X_EVENT_MASK, HFA384X_INTEN_OFF);
949}
950
951
952static void hfa384x_events_only_cmd(struct net_device *dev)
953{
954 HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_INTEN_OFF);
955}
956
957
958static u16 hfa384x_allocate_fid(struct net_device *dev, int len)
959{
960 u16 fid;
961 unsigned long delay;
962
963 /* FIX: this could be replace with hfa384x_cmd() if the Alloc event
964 * below would be handled like CmdCompl event (sleep here, wake up from
965 * interrupt handler */
966 if (hfa384x_cmd_wait(dev, HFA384X_CMDCODE_ALLOC, len)) {
967 printk(KERN_DEBUG "%s: cannot allocate fid, len=%d\n",
968 dev->name, len);
969 return 0xffff;
970 }
971
972 delay = jiffies + HFA384X_ALLOC_COMPL_TIMEOUT;
973 while (!(HFA384X_INW(HFA384X_EVSTAT_OFF) & HFA384X_EV_ALLOC) &&
974 time_before(jiffies, delay))
975 yield();
976 if (!(HFA384X_INW(HFA384X_EVSTAT_OFF) & HFA384X_EV_ALLOC)) {
977 printk("%s: fid allocate, len=%d - timeout\n", dev->name, len);
978 return 0xffff;
979 }
980
981 fid = HFA384X_INW(HFA384X_ALLOCFID_OFF);
982 HFA384X_OUTW(HFA384X_EV_ALLOC, HFA384X_EVACK_OFF);
983
984 return fid;
985}
986
987
988static int prism2_reset_port(struct net_device *dev)
989{
990 struct hostap_interface *iface;
991 local_info_t *local;
992 int res;
993
994 iface = netdev_priv(dev);
995 local = iface->local;
996
997 if (!local->dev_enabled)
998 return 0;
999
1000 res = hfa384x_cmd(dev, HFA384X_CMDCODE_DISABLE, 0,
1001 NULL, NULL);
1002 if (res)
1003 printk(KERN_DEBUG "%s: reset port failed to disable port\n",
1004 dev->name);
1005 else {
1006 res = hfa384x_cmd(dev, HFA384X_CMDCODE_ENABLE, 0,
1007 NULL, NULL);
1008 if (res)
1009 printk(KERN_DEBUG "%s: reset port failed to enable "
1010 "port\n", dev->name);
1011 }
1012
1013 /* It looks like at least some STA firmware versions reset
1014 * fragmentation threshold back to 2346 after enable command. Restore
1015 * the configured value, if it differs from this default. */
1016 if (local->fragm_threshold != 2346 &&
1017 hostap_set_word(dev, HFA384X_RID_FRAGMENTATIONTHRESHOLD,
1018 local->fragm_threshold)) {
1019 printk(KERN_DEBUG "%s: failed to restore fragmentation "
1020 "threshold (%d) after Port0 enable\n",
1021 dev->name, local->fragm_threshold);
1022 }
1023
1024 /* Some firmwares lose antenna selection settings on reset */
1025 (void) hostap_set_antsel(local);
1026
1027 return res;
1028}
1029
1030
1031static int prism2_get_version_info(struct net_device *dev, u16 rid,
1032 const char *txt)
1033{
1034 struct hfa384x_comp_ident comp;
1035 struct hostap_interface *iface;
1036 local_info_t *local;
1037
1038 iface = netdev_priv(dev);
1039 local = iface->local;
1040
1041 if (local->no_pri) {
1042 /* PRI f/w not yet available - cannot read RIDs */
1043 return -1;
1044 }
1045 if (hfa384x_get_rid(dev, rid, &comp, sizeof(comp), 1) < 0) {
1046 printk(KERN_DEBUG "Could not get RID for component %s\n", txt);
1047 return -1;
1048 }
1049
1050 printk(KERN_INFO "%s: %s: id=0x%02x v%d.%d.%d\n", dev->name, txt,
1051 __le16_to_cpu(comp.id), __le16_to_cpu(comp.major),
1052 __le16_to_cpu(comp.minor), __le16_to_cpu(comp.variant));
1053 return 0;
1054}
1055
1056
1057static int prism2_setup_rids(struct net_device *dev)
1058{
1059 struct hostap_interface *iface;
1060 local_info_t *local;
1061 __le16 tmp;
1062 int ret = 0;
1063
1064 iface = netdev_priv(dev);
1065 local = iface->local;
1066
1067 hostap_set_word(dev, HFA384X_RID_TICKTIME, 2000);
1068
1069 if (!local->fw_ap) {
1070 u16 tmp1 = hostap_get_porttype(local);
1071 ret = hostap_set_word(dev, HFA384X_RID_CNFPORTTYPE, tmp1);
1072 if (ret) {
1073 printk("%s: Port type setting to %d failed\n",
1074 dev->name, tmp1);
1075 goto fail;
1076 }
1077 }
1078
1079 /* Setting SSID to empty string seems to kill the card in Host AP mode
1080 */
1081 if (local->iw_mode != IW_MODE_MASTER || local->essid[0] != '\0') {
1082 ret = hostap_set_string(dev, HFA384X_RID_CNFOWNSSID,
1083 local->essid);
1084 if (ret) {
1085 printk("%s: AP own SSID setting failed\n", dev->name);
1086 goto fail;
1087 }
1088 }
1089
1090 ret = hostap_set_word(dev, HFA384X_RID_CNFMAXDATALEN,
1091 PRISM2_DATA_MAXLEN);
1092 if (ret) {
1093 printk("%s: MAC data length setting to %d failed\n",
1094 dev->name, PRISM2_DATA_MAXLEN);
1095 goto fail;
1096 }
1097
1098 if (hfa384x_get_rid(dev, HFA384X_RID_CHANNELLIST, &tmp, 2, 1) < 0) {
1099 printk("%s: Channel list read failed\n", dev->name);
1100 ret = -EINVAL;
1101 goto fail;
1102 }
1103 local->channel_mask = le16_to_cpu(tmp);
1104
1105 if (local->channel < 1 || local->channel > 14 ||
1106 !(local->channel_mask & (1 << (local->channel - 1)))) {
1107 printk(KERN_WARNING "%s: Channel setting out of range "
1108 "(%d)!\n", dev->name, local->channel);
1109 ret = -EBUSY;
1110 goto fail;
1111 }
1112
1113 ret = hostap_set_word(dev, HFA384X_RID_CNFOWNCHANNEL, local->channel);
1114 if (ret) {
1115 printk("%s: Channel setting to %d failed\n",
1116 dev->name, local->channel);
1117 goto fail;
1118 }
1119
1120 ret = hostap_set_word(dev, HFA384X_RID_CNFBEACONINT,
1121 local->beacon_int);
1122 if (ret) {
1123 printk("%s: Beacon interval setting to %d failed\n",
1124 dev->name, local->beacon_int);
1125 /* this may fail with Symbol/Lucent firmware */
1126 if (ret == -ETIMEDOUT)
1127 goto fail;
1128 }
1129
1130 ret = hostap_set_word(dev, HFA384X_RID_CNFOWNDTIMPERIOD,
1131 local->dtim_period);
1132 if (ret) {
1133 printk("%s: DTIM period setting to %d failed\n",
1134 dev->name, local->dtim_period);
1135 /* this may fail with Symbol/Lucent firmware */
1136 if (ret == -ETIMEDOUT)
1137 goto fail;
1138 }
1139
1140 ret = hostap_set_word(dev, HFA384X_RID_PROMISCUOUSMODE,
1141 local->is_promisc);
1142 if (ret)
1143 printk(KERN_INFO "%s: Setting promiscuous mode (%d) failed\n",
1144 dev->name, local->is_promisc);
1145
1146 if (!local->fw_ap) {
1147 ret = hostap_set_string(dev, HFA384X_RID_CNFDESIREDSSID,
1148 local->essid);
1149 if (ret) {
1150 printk("%s: Desired SSID setting failed\n", dev->name);
1151 goto fail;
1152 }
1153 }
1154
1155 /* Setup TXRateControl, defaults to allow use of 1, 2, 5.5, and
1156 * 11 Mbps in automatic TX rate fallback and 1 and 2 Mbps as basic
1157 * rates */
1158 if (local->tx_rate_control == 0) {
1159 local->tx_rate_control =
1160 HFA384X_RATES_1MBPS |
1161 HFA384X_RATES_2MBPS |
1162 HFA384X_RATES_5MBPS |
1163 HFA384X_RATES_11MBPS;
1164 }
1165 if (local->basic_rates == 0)
1166 local->basic_rates = HFA384X_RATES_1MBPS | HFA384X_RATES_2MBPS;
1167
1168 if (!local->fw_ap) {
1169 ret = hostap_set_word(dev, HFA384X_RID_TXRATECONTROL,
1170 local->tx_rate_control);
1171 if (ret) {
1172 printk("%s: TXRateControl setting to %d failed\n",
1173 dev->name, local->tx_rate_control);
1174 goto fail;
1175 }
1176
1177 ret = hostap_set_word(dev, HFA384X_RID_CNFSUPPORTEDRATES,
1178 local->tx_rate_control);
1179 if (ret) {
1180 printk("%s: cnfSupportedRates setting to %d failed\n",
1181 dev->name, local->tx_rate_control);
1182 }
1183
1184 ret = hostap_set_word(dev, HFA384X_RID_CNFBASICRATES,
1185 local->basic_rates);
1186 if (ret) {
1187 printk("%s: cnfBasicRates setting to %d failed\n",
1188 dev->name, local->basic_rates);
1189 }
1190
1191 ret = hostap_set_word(dev, HFA384X_RID_CREATEIBSS, 1);
1192 if (ret) {
1193 printk("%s: Create IBSS setting to 1 failed\n",
1194 dev->name);
1195 }
1196 }
1197
1198 if (local->name_set)
1199 (void) hostap_set_string(dev, HFA384X_RID_CNFOWNNAME,
1200 local->name);
1201
1202 if (hostap_set_encryption(local)) {
1203 printk(KERN_INFO "%s: could not configure encryption\n",
1204 dev->name);
1205 }
1206
1207 (void) hostap_set_antsel(local);
1208
1209 if (hostap_set_roaming(local)) {
1210 printk(KERN_INFO "%s: could not set host roaming\n",
1211 dev->name);
1212 }
1213
1214 if (local->sta_fw_ver >= PRISM2_FW_VER(1,6,3) &&
1215 hostap_set_word(dev, HFA384X_RID_CNFENHSECURITY, local->enh_sec))
1216 printk(KERN_INFO "%s: cnfEnhSecurity setting to 0x%x failed\n",
1217 dev->name, local->enh_sec);
1218
1219 /* 32-bit tallies were added in STA f/w 0.8.0, but they were apparently
1220 * not working correctly (last seven counters report bogus values).
1221 * This has been fixed in 0.8.2, so enable 32-bit tallies only
1222 * beginning with that firmware version. Another bug fix for 32-bit
1223 * tallies in 1.4.0; should 16-bit tallies be used for some other
1224 * versions, too? */
1225 if (local->sta_fw_ver >= PRISM2_FW_VER(0,8,2)) {
1226 if (hostap_set_word(dev, HFA384X_RID_CNFTHIRTY2TALLY, 1)) {
1227 printk(KERN_INFO "%s: cnfThirty2Tally setting "
1228 "failed\n", dev->name);
1229 local->tallies32 = 0;
1230 } else
1231 local->tallies32 = 1;
1232 } else
1233 local->tallies32 = 0;
1234
1235 hostap_set_auth_algs(local);
1236
1237 if (hostap_set_word(dev, HFA384X_RID_FRAGMENTATIONTHRESHOLD,
1238 local->fragm_threshold)) {
1239 printk(KERN_INFO "%s: setting FragmentationThreshold to %d "
1240 "failed\n", dev->name, local->fragm_threshold);
1241 }
1242
1243 if (hostap_set_word(dev, HFA384X_RID_RTSTHRESHOLD,
1244 local->rts_threshold)) {
1245 printk(KERN_INFO "%s: setting RTSThreshold to %d failed\n",
1246 dev->name, local->rts_threshold);
1247 }
1248
1249 if (local->manual_retry_count >= 0 &&
1250 hostap_set_word(dev, HFA384X_RID_CNFALTRETRYCOUNT,
1251 local->manual_retry_count)) {
1252 printk(KERN_INFO "%s: setting cnfAltRetryCount to %d failed\n",
1253 dev->name, local->manual_retry_count);
1254 }
1255
1256 if (local->sta_fw_ver >= PRISM2_FW_VER(1,3,1) &&
1257 hfa384x_get_rid(dev, HFA384X_RID_CNFDBMADJUST, &tmp, 2, 1) == 2) {
1258 local->rssi_to_dBm = le16_to_cpu(tmp);
1259 }
1260
1261 if (local->sta_fw_ver >= PRISM2_FW_VER(1,7,0) && local->wpa &&
1262 hostap_set_word(dev, HFA384X_RID_SSNHANDLINGMODE, 1)) {
1263 printk(KERN_INFO "%s: setting ssnHandlingMode to 1 failed\n",
1264 dev->name);
1265 }
1266
1267 if (local->sta_fw_ver >= PRISM2_FW_VER(1,7,0) && local->generic_elem &&
1268 hfa384x_set_rid(dev, HFA384X_RID_GENERICELEMENT,
1269 local->generic_elem, local->generic_elem_len)) {
1270 printk(KERN_INFO "%s: setting genericElement failed\n",
1271 dev->name);
1272 }
1273
1274 fail:
1275 return ret;
1276}
1277
1278
1279static int prism2_hw_init(struct net_device *dev, int initial)
1280{
1281 struct hostap_interface *iface;
1282 local_info_t *local;
1283 int ret, first = 1;
1284 unsigned long start, delay;
1285
1286 PDEBUG(DEBUG_FLOW, "prism2_hw_init()\n");
1287
1288 iface = netdev_priv(dev);
1289 local = iface->local;
1290
1291 clear_bit(HOSTAP_BITS_TRANSMIT, &local->bits);
1292
1293 init:
1294 /* initialize HFA 384x */
1295 ret = hfa384x_cmd_no_wait(dev, HFA384X_CMDCODE_INIT, 0);
1296 if (ret) {
1297 printk(KERN_INFO "%s: first command failed - assuming card "
1298 "does not have primary firmware\n", dev_info);
1299 }
1300
1301 if (first && (HFA384X_INW(HFA384X_EVSTAT_OFF) & HFA384X_EV_CMD)) {
1302 /* EvStat has Cmd bit set in some cases, so retry once if no
1303 * wait was needed */
1304 HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_EVACK_OFF);
1305 printk(KERN_DEBUG "%s: init command completed too quickly - "
1306 "retrying\n", dev->name);
1307 first = 0;
1308 goto init;
1309 }
1310
1311 start = jiffies;
1312 delay = jiffies + HFA384X_INIT_TIMEOUT;
1313 while (!(HFA384X_INW(HFA384X_EVSTAT_OFF) & HFA384X_EV_CMD) &&
1314 time_before(jiffies, delay))
1315 yield();
1316 if (!(HFA384X_INW(HFA384X_EVSTAT_OFF) & HFA384X_EV_CMD)) {
1317 printk(KERN_DEBUG "%s: assuming no Primary image in "
1318 "flash - card initialization not completed\n",
1319 dev_info);
1320 local->no_pri = 1;
1321#ifdef PRISM2_DOWNLOAD_SUPPORT
1322 if (local->sram_type == -1)
1323 local->sram_type = prism2_get_ram_size(local);
1324#endif /* PRISM2_DOWNLOAD_SUPPORT */
1325 return 1;
1326 }
1327 local->no_pri = 0;
1328 printk(KERN_DEBUG "prism2_hw_init: initialized in %lu ms\n",
1329 (jiffies - start) * 1000 / HZ);
1330 HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_EVACK_OFF);
1331 return 0;
1332}
1333
1334
1335static int prism2_hw_init2(struct net_device *dev, int initial)
1336{
1337 struct hostap_interface *iface;
1338 local_info_t *local;
1339 int i;
1340
1341 iface = netdev_priv(dev);
1342 local = iface->local;
1343
1344#ifdef PRISM2_DOWNLOAD_SUPPORT
1345 kfree(local->pda);
1346 if (local->no_pri)
1347 local->pda = NULL;
1348 else
1349 local->pda = prism2_read_pda(dev);
1350#endif /* PRISM2_DOWNLOAD_SUPPORT */
1351
1352 hfa384x_disable_interrupts(dev);
1353
1354#ifndef final_version
1355 HFA384X_OUTW(HFA384X_MAGIC, HFA384X_SWSUPPORT0_OFF);
1356 if (HFA384X_INW(HFA384X_SWSUPPORT0_OFF) != HFA384X_MAGIC) {
1357 printk("SWSUPPORT0 write/read failed: %04X != %04X\n",
1358 HFA384X_INW(HFA384X_SWSUPPORT0_OFF), HFA384X_MAGIC);
1359 goto failed;
1360 }
1361#endif
1362
1363 if (initial || local->pri_only) {
1364 hfa384x_events_only_cmd(dev);
1365 /* get card version information */
1366 if (prism2_get_version_info(dev, HFA384X_RID_NICID, "NIC") ||
1367 prism2_get_version_info(dev, HFA384X_RID_PRIID, "PRI")) {
1368 hfa384x_disable_interrupts(dev);
1369 goto failed;
1370 }
1371
1372 if (prism2_get_version_info(dev, HFA384X_RID_STAID, "STA")) {
1373 printk(KERN_DEBUG "%s: Failed to read STA f/w version "
1374 "- only Primary f/w present\n", dev->name);
1375 local->pri_only = 1;
1376 return 0;
1377 }
1378 local->pri_only = 0;
1379 hfa384x_disable_interrupts(dev);
1380 }
1381
1382 /* FIX: could convert allocate_fid to use sleeping CmdCompl wait and
1383 * enable interrupts before this. This would also require some sort of
1384 * sleeping AllocEv waiting */
1385
1386 /* allocate TX FIDs */
1387 local->txfid_len = PRISM2_TXFID_LEN;
1388 for (i = 0; i < PRISM2_TXFID_COUNT; i++) {
1389 local->txfid[i] = hfa384x_allocate_fid(dev, local->txfid_len);
1390 if (local->txfid[i] == 0xffff && local->txfid_len > 1600) {
1391 local->txfid[i] = hfa384x_allocate_fid(dev, 1600);
1392 if (local->txfid[i] != 0xffff) {
1393 printk(KERN_DEBUG "%s: Using shorter TX FID "
1394 "(1600 bytes)\n", dev->name);
1395 local->txfid_len = 1600;
1396 }
1397 }
1398 if (local->txfid[i] == 0xffff)
1399 goto failed;
1400 local->intransmitfid[i] = PRISM2_TXFID_EMPTY;
1401 }
1402
1403 hfa384x_events_only_cmd(dev);
1404
1405 if (initial) {
1406 u8 addr[ETH_ALEN] = {};
1407 struct list_head *ptr;
1408
1409 prism2_check_sta_fw_version(local);
1410
1411 if (hfa384x_get_rid(dev, HFA384X_RID_CNFOWNMACADDR,
1412 addr, ETH_ALEN, 1) < 0) {
1413 printk("%s: could not get own MAC address\n",
1414 dev->name);
1415 }
1416 eth_hw_addr_set(dev, addr);
1417 list_for_each(ptr, &local->hostap_interfaces) {
1418 iface = list_entry(ptr, struct hostap_interface, list);
1419 eth_hw_addr_inherit(iface->dev, dev);
1420 }
1421 } else if (local->fw_ap)
1422 prism2_check_sta_fw_version(local);
1423
1424 prism2_setup_rids(dev);
1425
1426 /* MAC is now configured, but port 0 is not yet enabled */
1427 return 0;
1428
1429 failed:
1430 if (!local->no_pri)
1431 printk(KERN_WARNING "%s: Initialization failed\n", dev_info);
1432 return 1;
1433}
1434
1435
1436static int prism2_hw_enable(struct net_device *dev, int initial)
1437{
1438 struct hostap_interface *iface;
1439 local_info_t *local;
1440 int was_resetting;
1441
1442 iface = netdev_priv(dev);
1443 local = iface->local;
1444 was_resetting = local->hw_resetting;
1445
1446 if (hfa384x_cmd(dev, HFA384X_CMDCODE_ENABLE, 0, NULL, NULL)) {
1447 printk("%s: MAC port 0 enabling failed\n", dev->name);
1448 return 1;
1449 }
1450
1451 local->hw_ready = 1;
1452 local->hw_reset_tries = 0;
1453 local->hw_resetting = 0;
1454 hfa384x_enable_interrupts(dev);
1455
1456 /* at least D-Link DWL-650 seems to require additional port reset
1457 * before it starts acting as an AP, so reset port automatically
1458 * here just in case */
1459 if (initial && prism2_reset_port(dev)) {
1460 printk("%s: MAC port 0 resetting failed\n", dev->name);
1461 return 1;
1462 }
1463
1464 if (was_resetting && netif_queue_stopped(dev)) {
1465 /* If hw_reset() was called during pending transmit, netif
1466 * queue was stopped. Wake it up now since the wlan card has
1467 * been resetted. */
1468 netif_wake_queue(dev);
1469 }
1470
1471 return 0;
1472}
1473
1474
1475static int prism2_hw_config(struct net_device *dev, int initial)
1476{
1477 struct hostap_interface *iface;
1478 local_info_t *local;
1479
1480 iface = netdev_priv(dev);
1481 local = iface->local;
1482
1483 if (local->hw_downloading)
1484 return 1;
1485
1486 if (prism2_hw_init(dev, initial)) {
1487 return local->no_pri ? 0 : 1;
1488 }
1489
1490 if (prism2_hw_init2(dev, initial))
1491 return 1;
1492
1493 /* Enable firmware if secondary image is loaded and at least one of the
1494 * netdevices is up. */
1495 if (!local->pri_only &&
1496 (initial == 0 || (initial == 2 && local->num_dev_open > 0))) {
1497 if (!local->dev_enabled)
1498 prism2_callback(local, PRISM2_CALLBACK_ENABLE);
1499 local->dev_enabled = 1;
1500 return prism2_hw_enable(dev, initial);
1501 }
1502
1503 return 0;
1504}
1505
1506
1507static void prism2_hw_shutdown(struct net_device *dev, int no_disable)
1508{
1509 struct hostap_interface *iface;
1510 local_info_t *local;
1511
1512 iface = netdev_priv(dev);
1513 local = iface->local;
1514
1515 /* Allow only command completion events during disable */
1516 hfa384x_events_only_cmd(dev);
1517
1518 local->hw_ready = 0;
1519 if (local->dev_enabled)
1520 prism2_callback(local, PRISM2_CALLBACK_DISABLE);
1521 local->dev_enabled = 0;
1522
1523 if (local->func->card_present && !local->func->card_present(local)) {
1524 printk(KERN_DEBUG "%s: card already removed or not configured "
1525 "during shutdown\n", dev->name);
1526 return;
1527 }
1528
1529 if ((no_disable & HOSTAP_HW_NO_DISABLE) == 0 &&
1530 hfa384x_cmd(dev, HFA384X_CMDCODE_DISABLE, 0, NULL, NULL))
1531 printk(KERN_WARNING "%s: Shutdown failed\n", dev_info);
1532
1533 hfa384x_disable_interrupts(dev);
1534
1535 if (no_disable & HOSTAP_HW_ENABLE_CMDCOMPL)
1536 hfa384x_events_only_cmd(dev);
1537 else
1538 prism2_clear_cmd_queue(local);
1539}
1540
1541
1542static void prism2_hw_reset(struct net_device *dev)
1543{
1544 struct hostap_interface *iface;
1545 local_info_t *local;
1546
1547#if 0
1548 static long last_reset = 0;
1549
1550 /* do not reset card more than once per second to avoid ending up in a
1551 * busy loop resetting the card */
1552 if (time_before_eq(jiffies, last_reset + HZ))
1553 return;
1554 last_reset = jiffies;
1555#endif
1556
1557 iface = netdev_priv(dev);
1558 local = iface->local;
1559
1560 if (local->hw_downloading)
1561 return;
1562
1563 if (local->hw_resetting) {
1564 printk(KERN_WARNING "%s: %s: already resetting card - "
1565 "ignoring reset request\n", dev_info, dev->name);
1566 return;
1567 }
1568
1569 local->hw_reset_tries++;
1570 if (local->hw_reset_tries > 10) {
1571 printk(KERN_WARNING "%s: too many reset tries, skipping\n",
1572 dev->name);
1573 return;
1574 }
1575
1576 printk(KERN_WARNING "%s: %s: resetting card\n", dev_info, dev->name);
1577 hfa384x_disable_interrupts(dev);
1578 local->hw_resetting = 1;
1579 if (local->func->cor_sreset) {
1580 /* Host system seems to hang in some cases with high traffic
1581 * load or shared interrupts during COR sreset. Disable shared
1582 * interrupts during reset to avoid these crashes. COS sreset
1583 * takes quite a long time, so it is unfortunate that this
1584 * seems to be needed. Anyway, I do not know of any better way
1585 * of avoiding the crash. */
1586 disable_irq(dev->irq);
1587 local->func->cor_sreset(local);
1588 enable_irq(dev->irq);
1589 }
1590 prism2_hw_shutdown(dev, 1);
1591 prism2_hw_config(dev, 0);
1592 local->hw_resetting = 0;
1593
1594#ifdef PRISM2_DOWNLOAD_SUPPORT
1595 if (local->dl_pri) {
1596 printk(KERN_DEBUG "%s: persistent download of primary "
1597 "firmware\n", dev->name);
1598 if (prism2_download_genesis(local, local->dl_pri) < 0)
1599 printk(KERN_WARNING "%s: download (PRI) failed\n",
1600 dev->name);
1601 }
1602
1603 if (local->dl_sec) {
1604 printk(KERN_DEBUG "%s: persistent download of secondary "
1605 "firmware\n", dev->name);
1606 if (prism2_download_volatile(local, local->dl_sec) < 0)
1607 printk(KERN_WARNING "%s: download (SEC) failed\n",
1608 dev->name);
1609 }
1610#endif /* PRISM2_DOWNLOAD_SUPPORT */
1611
1612 /* TODO: restore beacon TIM bits for STAs that have buffered frames */
1613}
1614
1615
1616static void prism2_schedule_reset(local_info_t *local)
1617{
1618 schedule_work(&local->reset_queue);
1619}
1620
1621
1622/* Called only as scheduled task after noticing card timeout in interrupt
1623 * context */
1624static void handle_reset_queue(struct work_struct *work)
1625{
1626 local_info_t *local = container_of(work, local_info_t, reset_queue);
1627
1628 printk(KERN_DEBUG "%s: scheduled card reset\n", local->dev->name);
1629 prism2_hw_reset(local->dev);
1630
1631 if (netif_queue_stopped(local->dev)) {
1632 int i;
1633
1634 for (i = 0; i < PRISM2_TXFID_COUNT; i++)
1635 if (local->intransmitfid[i] == PRISM2_TXFID_EMPTY) {
1636 PDEBUG(DEBUG_EXTRA, "prism2_tx_timeout: "
1637 "wake up queue\n");
1638 netif_wake_queue(local->dev);
1639 break;
1640 }
1641 }
1642}
1643
1644
1645static int prism2_get_txfid_idx(local_info_t *local)
1646{
1647 int idx, end;
1648 unsigned long flags;
1649
1650 spin_lock_irqsave(&local->txfidlock, flags);
1651 end = idx = local->next_txfid;
1652 do {
1653 if (local->intransmitfid[idx] == PRISM2_TXFID_EMPTY) {
1654 local->intransmitfid[idx] = PRISM2_TXFID_RESERVED;
1655 spin_unlock_irqrestore(&local->txfidlock, flags);
1656 return idx;
1657 }
1658 idx++;
1659 if (idx >= PRISM2_TXFID_COUNT)
1660 idx = 0;
1661 } while (idx != end);
1662 spin_unlock_irqrestore(&local->txfidlock, flags);
1663
1664 PDEBUG(DEBUG_EXTRA2, "prism2_get_txfid_idx: no room in txfid buf: "
1665 "packet dropped\n");
1666 local->dev->stats.tx_dropped++;
1667
1668 return -1;
1669}
1670
1671
1672/* Called only from hardware IRQ */
1673static void prism2_transmit_cb(struct net_device *dev, long context,
1674 u16 resp0, u16 res)
1675{
1676 struct hostap_interface *iface;
1677 local_info_t *local;
1678 int idx = (int) context;
1679
1680 iface = netdev_priv(dev);
1681 local = iface->local;
1682
1683 if (res) {
1684 printk(KERN_DEBUG "%s: prism2_transmit_cb - res=0x%02x\n",
1685 dev->name, res);
1686 return;
1687 }
1688
1689 if (idx < 0 || idx >= PRISM2_TXFID_COUNT) {
1690 printk(KERN_DEBUG "%s: prism2_transmit_cb called with invalid "
1691 "idx=%d\n", dev->name, idx);
1692 return;
1693 }
1694
1695 if (!test_and_clear_bit(HOSTAP_BITS_TRANSMIT, &local->bits)) {
1696 printk(KERN_DEBUG "%s: driver bug: prism2_transmit_cb called "
1697 "with no pending transmit\n", dev->name);
1698 }
1699
1700 if (netif_queue_stopped(dev)) {
1701 /* ready for next TX, so wake up queue that was stopped in
1702 * prism2_transmit() */
1703 netif_wake_queue(dev);
1704 }
1705
1706 spin_lock(&local->txfidlock);
1707
1708 /* With reclaim, Resp0 contains new txfid for transmit; the old txfid
1709 * will be automatically allocated for the next TX frame */
1710 local->intransmitfid[idx] = resp0;
1711
1712 PDEBUG(DEBUG_FID, "%s: prism2_transmit_cb: txfid[%d]=0x%04x, "
1713 "resp0=0x%04x, transmit_txfid=0x%04x\n",
1714 dev->name, idx, local->txfid[idx],
1715 resp0, local->intransmitfid[local->next_txfid]);
1716
1717 idx++;
1718 if (idx >= PRISM2_TXFID_COUNT)
1719 idx = 0;
1720 local->next_txfid = idx;
1721
1722 /* check if all TX buffers are occupied */
1723 do {
1724 if (local->intransmitfid[idx] == PRISM2_TXFID_EMPTY) {
1725 spin_unlock(&local->txfidlock);
1726 return;
1727 }
1728 idx++;
1729 if (idx >= PRISM2_TXFID_COUNT)
1730 idx = 0;
1731 } while (idx != local->next_txfid);
1732 spin_unlock(&local->txfidlock);
1733
1734 /* no empty TX buffers, stop queue */
1735 netif_stop_queue(dev);
1736}
1737
1738
1739/* Called only from software IRQ if PCI bus master is not used (with bus master
1740 * this can be called both from software and hardware IRQ) */
1741static int prism2_transmit(struct net_device *dev, int idx)
1742{
1743 struct hostap_interface *iface;
1744 local_info_t *local;
1745 int res;
1746
1747 iface = netdev_priv(dev);
1748 local = iface->local;
1749
1750 /* The driver tries to stop netif queue so that there would not be
1751 * more than one attempt to transmit frames going on; check that this
1752 * is really the case */
1753
1754 if (test_and_set_bit(HOSTAP_BITS_TRANSMIT, &local->bits)) {
1755 printk(KERN_DEBUG "%s: driver bug - prism2_transmit() called "
1756 "when previous TX was pending\n", dev->name);
1757 return -1;
1758 }
1759
1760 /* stop the queue for the time that transmit is pending */
1761 netif_stop_queue(dev);
1762
1763 /* transmit packet */
1764 res = hfa384x_cmd_callback(
1765 dev,
1766 HFA384X_CMDCODE_TRANSMIT | HFA384X_CMD_TX_RECLAIM,
1767 local->txfid[idx],
1768 prism2_transmit_cb, (long) idx);
1769
1770 if (res) {
1771 printk(KERN_DEBUG "%s: prism2_transmit: CMDCODE_TRANSMIT "
1772 "failed (res=%d)\n", dev->name, res);
1773 dev->stats.tx_dropped++;
1774 netif_wake_queue(dev);
1775 return -1;
1776 }
1777 netif_trans_update(dev);
1778
1779 /* Since we did not wait for command completion, the card continues
1780 * to process on the background and we will finish handling when
1781 * command completion event is handled (prism2_cmd_ev() function) */
1782
1783 return 0;
1784}
1785
1786
1787/* Send IEEE 802.11 frame (convert the header into Prism2 TX descriptor and
1788 * send the payload with this descriptor) */
1789/* Called only from software IRQ */
1790static int prism2_tx_80211(struct sk_buff *skb, struct net_device *dev)
1791{
1792 struct hostap_interface *iface;
1793 local_info_t *local;
1794 struct hfa384x_tx_frame txdesc;
1795 struct hostap_skb_tx_data *meta;
1796 int hdr_len, data_len, idx, res, ret = -1;
1797 u16 tx_control;
1798
1799 iface = netdev_priv(dev);
1800 local = iface->local;
1801
1802 meta = (struct hostap_skb_tx_data *) skb->cb;
1803
1804 prism2_callback(local, PRISM2_CALLBACK_TX_START);
1805
1806 if ((local->func->card_present && !local->func->card_present(local)) ||
1807 !local->hw_ready || local->hw_downloading || local->pri_only) {
1808 if (net_ratelimit()) {
1809 printk(KERN_DEBUG "%s: prism2_tx_80211: hw not ready -"
1810 " skipping\n", dev->name);
1811 }
1812 goto fail;
1813 }
1814
1815 memset(&txdesc, 0, sizeof(txdesc));
1816
1817 /* skb->data starts with txdesc->frame_control */
1818 hdr_len = sizeof(txdesc.header);
1819 BUILD_BUG_ON(hdr_len != 24);
1820 skb_copy_from_linear_data(skb, &txdesc.header, hdr_len);
1821 if (ieee80211_is_data(txdesc.frame_control) &&
1822 ieee80211_has_a4(txdesc.frame_control) &&
1823 skb->len >= 30) {
1824 /* Addr4 */
1825 skb_copy_from_linear_data_offset(skb, hdr_len, txdesc.addr4,
1826 ETH_ALEN);
1827 hdr_len += ETH_ALEN;
1828 }
1829
1830 tx_control = local->tx_control;
1831 if (meta->tx_cb_idx) {
1832 tx_control |= HFA384X_TX_CTRL_TX_OK;
1833 txdesc.sw_support = cpu_to_le32(meta->tx_cb_idx);
1834 }
1835 txdesc.tx_control = cpu_to_le16(tx_control);
1836 txdesc.tx_rate = meta->rate;
1837
1838 data_len = skb->len - hdr_len;
1839 txdesc.data_len = cpu_to_le16(data_len);
1840 txdesc.len = cpu_to_be16(data_len);
1841
1842 idx = prism2_get_txfid_idx(local);
1843 if (idx < 0)
1844 goto fail;
1845
1846 if (local->frame_dump & PRISM2_DUMP_TX_HDR)
1847 hostap_dump_tx_header(dev->name, &txdesc);
1848
1849 spin_lock(&local->baplock);
1850 res = hfa384x_setup_bap(dev, BAP0, local->txfid[idx], 0);
1851
1852 if (!res)
1853 res = hfa384x_to_bap(dev, BAP0, &txdesc, sizeof(txdesc));
1854 if (!res)
1855 res = hfa384x_to_bap(dev, BAP0, skb->data + hdr_len,
1856 skb->len - hdr_len);
1857 spin_unlock(&local->baplock);
1858
1859 if (!res)
1860 res = prism2_transmit(dev, idx);
1861 if (res) {
1862 printk(KERN_DEBUG "%s: prism2_tx_80211 - to BAP0 failed\n",
1863 dev->name);
1864 local->intransmitfid[idx] = PRISM2_TXFID_EMPTY;
1865 schedule_work(&local->reset_queue);
1866 goto fail;
1867 }
1868
1869 ret = 0;
1870
1871fail:
1872 prism2_callback(local, PRISM2_CALLBACK_TX_END);
1873 return ret;
1874}
1875
1876
1877/* Some SMP systems have reported number of odd errors with hostap_pci. fid
1878 * register has changed values between consecutive reads for an unknown reason.
1879 * This should really not happen, so more debugging is needed. This test
1880 * version is a bit slower, but it will detect most of such register changes
1881 * and will try to get the correct fid eventually. */
1882#define EXTRA_FID_READ_TESTS
1883
1884static u16 prism2_read_fid_reg(struct net_device *dev, u16 reg)
1885{
1886#ifdef EXTRA_FID_READ_TESTS
1887 u16 val, val2, val3;
1888 int i;
1889
1890 for (i = 0; i < 10; i++) {
1891 val = HFA384X_INW(reg);
1892 val2 = HFA384X_INW(reg);
1893 val3 = HFA384X_INW(reg);
1894
1895 if (val == val2 && val == val3)
1896 return val;
1897

1490 more lines aren’t shown here.

drivers/net/wireless/intersil/hostap/hostap_info.c+0−509

This diff is large: its 510 lines aren’t shown here.

drivers/net/wireless/intersil/hostap/hostap_ioctl.c+0−3847

This diff is large: its 3848 lines aren’t shown here.

drivers/net/wireless/intersil/hostap/hostap_main.c+0−1123

This diff is large: its 1124 lines aren’t shown here.

drivers/net/wireless/intersil/hostap/hostap_pci.c+0−445

This diff is large: its 446 lines aren’t shown here.

drivers/net/wireless/intersil/hostap/hostap_plx.c+0−617

This diff is large: its 618 lines aren’t shown here.

drivers/net/wireless/intersil/hostap/hostap_proc.c+0−411

This diff is large: its 412 lines aren’t shown here.

drivers/net/wireless/intersil/hostap/hostap_wlan.h+0−1051

This diff is large: its 1052 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/Kconfig+0−143

This diff is large: its 144 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/Makefile+0−15

This diff is large: its 16 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/airport.c+0−268

This diff is large: its 269 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/cfg.c+0−291

This diff is large: its 292 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/cfg.h+0−15

This diff is large: its 16 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/fw.c+0−387

This diff is large: its 388 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/fw.h+0−21

This diff is large: its 22 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/hermes.c+0−778

This diff is large: its 779 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/hermes.h+0−534

This diff is large: its 535 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/hermes_dld.c+0−477

This diff is large: its 478 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/hermes_dld.h+0−52

This diff is large: its 53 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/hermes_rid.h+0−165

This diff is large: its 166 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/hw.c+0−1362

This diff is large: its 1363 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/hw.h+0−60

This diff is large: its 61 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/main.c+0−2414

This diff is large: its 2415 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/main.h+0−50

This diff is large: its 51 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/mic.c+0−89

This diff is large: its 90 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/mic.h+0−23

This diff is large: its 24 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/orinoco.h+0−251

This diff is large: its 252 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/orinoco_cs.c+0−350

This diff is large: its 351 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/orinoco_nortel.c+0−314

This diff is large: its 315 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/orinoco_pci.c+0−257

This diff is large: its 258 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/orinoco_pci.h+0−54

This diff is large: its 55 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/orinoco_plx.c+0−362

This diff is large: its 363 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/orinoco_tmd.c+0−237

This diff is large: its 238 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/orinoco_usb.c+0−1787

This diff is large: its 1788 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/scan.c+0−259

This diff is large: its 260 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/scan.h+0−21

This diff is large: its 22 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/spectrum_cs.c+0−328

This diff is large: its 329 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/wext.c+0−1428

This diff is large: its 1429 lines aren’t shown here.

drivers/net/wireless/intersil/orinoco/wext.h+0−13

This diff is large: its 14 lines aren’t shown here.

drivers/net/wireless/legacy/Kconfig+0−55

This diff is large: its 56 lines aren’t shown here.

drivers/net/wireless/legacy/Makefile+0−6

This diff is large: its 7 lines aren’t shown here.

drivers/net/wireless/legacy/ray_cs.c+0−2824

This diff is large: its 2825 lines aren’t shown here.

drivers/net/wireless/legacy/ray_cs.h+0−74

This diff is large: its 75 lines aren’t shown here.

drivers/net/wireless/legacy/rayctl.h+0−734

This diff is large: its 735 lines aren’t shown here.

drivers/net/wireless/legacy/rndis_wlan.c+0−3760

This diff is large: its 3761 lines aren’t shown here.

drivers/net/wireless/legacy/wl3501.h+0−615

This diff is large: its 616 lines aren’t shown here.

drivers/net/wireless/legacy/wl3501_cs.c+0−2036

This diff is large: its 2037 lines aren’t shown here.

drivers/net/wireless/marvell/libertas/Kconfig+1−8

This diff is large: its 24 lines aren’t shown here.

drivers/net/wireless/marvell/libertas/Makefile+0−1

This diff is large: its 7 lines aren’t shown here.

drivers/net/wireless/marvell/libertas/if_cs.c+0−957

This diff is large: its 958 lines aren’t shown here.

drivers/net/wireless/marvell/mwifiex/cmdevt.c+0−8

This diff is large: its 22 lines aren’t shown here.

drivers/net/wireless/microchip/wilc1000/cfg80211.c+9−15

This diff is large: its 70 lines aren’t shown here.

drivers/net/wireless/microchip/wilc1000/hif.c+23−23

This diff is large: its 157 lines aren’t shown here.

drivers/net/wireless/microchip/wilc1000/hif.h+22−20

This diff is large: its 97 lines aren’t shown here.

drivers/net/wireless/microchip/wilc1000/sdio.c+5−4

This diff is large: its 23 lines aren’t shown here.

drivers/net/wireless/purelifi/plfxlc/usb.c+4−1

This diff is large: its 14 lines aren’t shown here.

drivers/net/wireless/ralink/rt2x00/rt2800.h+4−0

This diff is large: its 9 lines aren’t shown here.

drivers/net/wireless/ralink/rt2x00/rt2800lib.c+69−14

This diff is large: its 145 lines aren’t shown here.

drivers/net/wireless/ralink/rt2x00/rt2x00.h+3−0

This diff is large: its 10 lines aren’t shown here.

drivers/net/wireless/ralink/rt2x00/rt2x00dev.c+3−0

This diff is large: its 24 lines aren’t shown here.

drivers/net/wireless/ralink/rt2x00/rt2x00mac.c+11−0

This diff is large: its 18 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/base.c+0−8

This diff is large: its 29 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/pci.c+0−1

This diff is large: its 8 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/pci.h+0−1

This diff is large: its 8 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/rtl8188ee/sw.c+0−3

This diff is large: its 10 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/rtl8192c/phy_common.c+0−4

This diff is large: its 13 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/rtl8192ce/sw.c+0−3

This diff is large: its 10 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/rtl8192de/sw.c+0−3

This diff is large: its 10 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/rtl8192ee/dm.c+2−9

This diff is large: its 65 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/rtl8192ee/hw.c+0−1

This diff is large: its 8 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/rtl8192ee/sw.c+0−3

This diff is large: its 10 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/rtl8192se/sw.c+0−3

This diff is large: its 10 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/rtl8723ae/sw.c+0−3

This diff is large: its 10 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/rtl8723be/sw.c+0−3

This diff is large: its 10 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/rtl8821ae/sw.c+0−3

This diff is large: its 10 lines aren’t shown here.

drivers/net/wireless/realtek/rtlwifi/wifi.h+0−17

This diff is large: its 84 lines aren’t shown here.

drivers/net/wireless/realtek/rtw88/mac80211.c+2−2

This diff is large: its 12 lines aren’t shown here.

drivers/net/wireless/realtek/rtw88/tx.c+1−2

This diff is large: its 11 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/acpi.c+66−15

This diff is large: its 107 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/acpi.h+31−1

This diff is large: its 39 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/cam.c+15−1

This diff is large: its 30 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/coex.c+2−2

This diff is large: its 16 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/core.c+79−16

This diff is large: its 181 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/core.h+38−2

This diff is large: its 123 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/debug.h+1−0

This diff is large: its 8 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/efuse.c+8−3

This diff is large: its 39 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/efuse.h+15−2

This diff is large: its 24 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/efuse_be.c+420−0

This diff is large: its 421 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/mac.c+13−3

This diff is large: its 48 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/mac.h+4−0

This diff is large: its 18 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/mac_be.c+4−0

This diff is large: its 18 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/pci.c+240−83

This diff is large: its 665 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/pci.h+515−0

This diff is large: its 631 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/pci_be.c+509−0

This diff is large: its 510 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/phy.h+16−0

This diff is large: its 23 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/reg.h+437−0

This diff is large: its 507 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/regd.c+168−7

This diff is large: its 270 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/rtw8851b.c+4−1

This diff is large: its 25 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/rtw8851be.c+3−0

This diff is large: its 24 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/rtw8852a.c+4−1

This diff is large: its 25 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/rtw8852ae.c+4−0

This diff is large: its 32 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/rtw8852b.c+4−1

This diff is large: its 25 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/rtw8852be.c+4−0

This diff is large: its 32 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/rtw8852c.c+28−1

This diff is large: its 53 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/rtw8852c.h+18−2

This diff is large: its 28 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/rtw8852ce.c+4−0

This diff is large: its 32 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/rtw8922a.c+363−0

This diff is large: its 364 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/rtw8922a.h+73−0

This diff is large: its 74 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/rtw8922ae.c+88−0

This diff is large: its 89 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/sar.c+3−1

This diff is large: its 20 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/ser.c+6−0

This diff is large: its 20 lines aren’t shown here.

drivers/net/wireless/realtek/rtw89/txrx.h+4−0

This diff is large: its 20 lines aren’t shown here.

drivers/net/wireless/zydas/Kconfig+0−19

This diff is large: its 26 lines aren’t shown here.

drivers/net/wireless/zydas/Makefile+0−2

This diff is large: its 5 lines aren’t shown here.

drivers/net/wireless/zydas/zd1201.c+0−1909

This diff is large: its 1910 lines aren’t shown here.

drivers/net/wireless/zydas/zd1201.h+0−144

This diff is large: its 145 lines aren’t shown here.

include/linux/ieee80211.h+2−2

This diff is large: its 14 lines aren’t shown here.

include/net/cfg80211.h+3−0

This diff is large: its 17 lines aren’t shown here.

include/uapi/linux/nl80211.h+14−8

This diff is large: its 36 lines aren’t shown here.

net/mac80211/scan.c+43−5

This diff is large: its 69 lines aren’t shown here.

net/rfkill/core.c+2−2

This diff is large: its 14 lines aren’t shown here.

net/wireless/nl80211.c+1−0

This diff is large: its 8 lines aren’t shown here.

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t