xref: /openbmc/linux/drivers/net/wireless/atmel/atmel.c (revision a17922de)
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 
75 MODULE_AUTHOR("Simon Kelley");
76 MODULE_DESCRIPTION("Support for Atmel at76c50x 802.11 wireless ethernet cards.");
77 MODULE_LICENSE("GPL");
78 MODULE_SUPPORTED_DEVICE("Atmel at76c50x wireless cards");
79 
80 /* The name of the firmware file to be loaded
81    over-rides any automatic selection */
82 static char *firmware = NULL;
83 module_param(firmware, charp, 0);
84 
85 /* table of firmware file names */
86 static struct {
87 	AtmelFWType fw_type;
88 	const char *fw_file;
89 	const char *fw_file_ext;
90 } fw_table[] = {
91 	{ ATMEL_FW_TYPE_502,		"atmel_at76c502",	"bin" },
92 	{ ATMEL_FW_TYPE_502D,		"atmel_at76c502d",	"bin" },
93 	{ ATMEL_FW_TYPE_502E,		"atmel_at76c502e",	"bin" },
94 	{ ATMEL_FW_TYPE_502_3COM,	"atmel_at76c502_3com",	"bin" },
95 	{ ATMEL_FW_TYPE_504,		"atmel_at76c504",	"bin" },
96 	{ ATMEL_FW_TYPE_504_2958,	"atmel_at76c504_2958",	"bin" },
97 	{ ATMEL_FW_TYPE_504A_2958,	"atmel_at76c504a_2958",	"bin" },
98 	{ ATMEL_FW_TYPE_506,		"atmel_at76c506",	"bin" },
99 	{ ATMEL_FW_TYPE_NONE,		NULL,			NULL }
100 };
101 MODULE_FIRMWARE("atmel_at76c502-wpa.bin");
102 MODULE_FIRMWARE("atmel_at76c502.bin");
103 MODULE_FIRMWARE("atmel_at76c502d-wpa.bin");
104 MODULE_FIRMWARE("atmel_at76c502d.bin");
105 MODULE_FIRMWARE("atmel_at76c502e-wpa.bin");
106 MODULE_FIRMWARE("atmel_at76c502e.bin");
107 MODULE_FIRMWARE("atmel_at76c502_3com-wpa.bin");
108 MODULE_FIRMWARE("atmel_at76c502_3com.bin");
109 MODULE_FIRMWARE("atmel_at76c504-wpa.bin");
110 MODULE_FIRMWARE("atmel_at76c504.bin");
111 MODULE_FIRMWARE("atmel_at76c504_2958-wpa.bin");
112 MODULE_FIRMWARE("atmel_at76c504_2958.bin");
113 MODULE_FIRMWARE("atmel_at76c504a_2958-wpa.bin");
114 MODULE_FIRMWARE("atmel_at76c504a_2958.bin");
115 MODULE_FIRMWARE("atmel_at76c506-wpa.bin");
116 MODULE_FIRMWARE("atmel_at76c506.bin");
117 
118 #define MAX_SSID_LENGTH 32
119 #define MGMT_JIFFIES (256 * HZ / 100)
120 
121 #define MAX_BSS_ENTRIES	64
122 
123 /* registers */
124 #define GCR  0x00    /* (SIR0)  General Configuration Register */
125 #define BSR  0x02    /* (SIR1)  Bank Switching Select Register */
126 #define AR   0x04
127 #define DR   0x08
128 #define MR1  0x12    /* Mirror Register 1 */
129 #define MR2  0x14    /* Mirror Register 2 */
130 #define MR3  0x16    /* Mirror Register 3 */
131 #define MR4  0x18    /* Mirror Register 4 */
132 
133 #define GPR1                            0x0c
134 #define GPR2                            0x0e
135 #define GPR3                            0x10
136 /*
137  * Constants for the GCR register.
138  */
139 #define GCR_REMAP     0x0400          /* Remap internal SRAM to 0 */
140 #define GCR_SWRES     0x0080          /* BIU reset (ARM and PAI are NOT reset) */
141 #define GCR_CORES     0x0060          /* Core Reset (ARM and PAI are reset) */
142 #define GCR_ENINT     0x0002          /* Enable Interrupts */
143 #define GCR_ACKINT    0x0008          /* Acknowledge Interrupts */
144 
145 #define BSS_SRAM      0x0200          /* AMBA module selection --> SRAM */
146 #define BSS_IRAM      0x0100          /* AMBA module selection --> IRAM */
147 /*
148  *Constants for the MR registers.
149  */
150 #define MAC_INIT_COMPLETE       0x0001        /* MAC init has been completed */
151 #define MAC_BOOT_COMPLETE       0x0010        /* MAC boot has been completed */
152 #define MAC_INIT_OK             0x0002        /* MAC boot has been completed */
153 
154 #define MIB_MAX_DATA_BYTES    212
155 #define MIB_HEADER_SIZE       4    /* first four fields */
156 
157 struct get_set_mib {
158 	u8 type;
159 	u8 size;
160 	u8 index;
161 	u8 reserved;
162 	u8 data[MIB_MAX_DATA_BYTES];
163 };
164 
165 struct rx_desc {
166 	u32          Next;
167 	u16          MsduPos;
168 	u16          MsduSize;
169 
170 	u8           State;
171 	u8           Status;
172 	u8           Rate;
173 	u8           Rssi;
174 	u8           LinkQuality;
175 	u8           PreambleType;
176 	u16          Duration;
177 	u32          RxTime;
178 };
179 
180 #define RX_DESC_FLAG_VALID       0x80
181 #define RX_DESC_FLAG_CONSUMED    0x40
182 #define RX_DESC_FLAG_IDLE        0x00
183 
184 #define RX_STATUS_SUCCESS        0x00
185 
186 #define RX_DESC_MSDU_POS_OFFSET      4
187 #define RX_DESC_MSDU_SIZE_OFFSET     6
188 #define RX_DESC_FLAGS_OFFSET         8
189 #define RX_DESC_STATUS_OFFSET        9
190 #define RX_DESC_RSSI_OFFSET          11
191 #define RX_DESC_LINK_QUALITY_OFFSET  12
192 #define RX_DESC_PREAMBLE_TYPE_OFFSET 13
193 #define RX_DESC_DURATION_OFFSET      14
194 #define RX_DESC_RX_TIME_OFFSET       16
195 
196 struct tx_desc {
197 	u32       NextDescriptor;
198 	u16       TxStartOfFrame;
199 	u16       TxLength;
200 
201 	u8        TxState;
202 	u8        TxStatus;
203 	u8        RetryCount;
204 
205 	u8        TxRate;
206 
207 	u8        KeyIndex;
208 	u8        ChiperType;
209 	u8        ChipreLength;
210 	u8        Reserved1;
211 
212 	u8        Reserved;
213 	u8        PacketType;
214 	u16       HostTxLength;
215 };
216 
217 #define TX_DESC_NEXT_OFFSET          0
218 #define TX_DESC_POS_OFFSET           4
219 #define TX_DESC_SIZE_OFFSET          6
220 #define TX_DESC_FLAGS_OFFSET         8
221 #define TX_DESC_STATUS_OFFSET        9
222 #define TX_DESC_RETRY_OFFSET         10
223 #define TX_DESC_RATE_OFFSET          11
224 #define TX_DESC_KEY_INDEX_OFFSET     12
225 #define TX_DESC_CIPHER_TYPE_OFFSET   13
226 #define TX_DESC_CIPHER_LENGTH_OFFSET 14
227 #define TX_DESC_PACKET_TYPE_OFFSET   17
228 #define TX_DESC_HOST_LENGTH_OFFSET   18
229 
230 /*
231  * Host-MAC interface
232  */
233 
234 #define TX_STATUS_SUCCESS       0x00
235 
236 #define TX_FIRM_OWN             0x80
237 #define TX_DONE                 0x40
238 
239 #define TX_ERROR                0x01
240 
241 #define TX_PACKET_TYPE_DATA     0x01
242 #define TX_PACKET_TYPE_MGMT     0x02
243 
244 #define ISR_EMPTY               0x00        /* no bits set in ISR */
245 #define ISR_TxCOMPLETE          0x01        /* packet transmitted */
246 #define ISR_RxCOMPLETE          0x02        /* packet received */
247 #define ISR_RxFRAMELOST         0x04        /* Rx Frame lost */
248 #define ISR_FATAL_ERROR         0x08        /* Fatal error */
249 #define ISR_COMMAND_COMPLETE    0x10        /* command completed */
250 #define ISR_OUT_OF_RANGE        0x20        /* command completed */
251 #define ISR_IBSS_MERGE          0x40        /* (4.1.2.30): IBSS merge */
252 #define ISR_GENERIC_IRQ         0x80
253 
254 #define Local_Mib_Type          0x01
255 #define Mac_Address_Mib_Type    0x02
256 #define Mac_Mib_Type            0x03
257 #define Statistics_Mib_Type     0x04
258 #define Mac_Mgmt_Mib_Type       0x05
259 #define Mac_Wep_Mib_Type        0x06
260 #define Phy_Mib_Type            0x07
261 #define Multi_Domain_MIB        0x08
262 
263 #define MAC_MGMT_MIB_CUR_BSSID_POS            14
264 #define MAC_MIB_FRAG_THRESHOLD_POS            8
265 #define MAC_MIB_RTS_THRESHOLD_POS             10
266 #define MAC_MIB_SHORT_RETRY_POS               16
267 #define MAC_MIB_LONG_RETRY_POS                17
268 #define MAC_MIB_SHORT_RETRY_LIMIT_POS         16
269 #define MAC_MGMT_MIB_BEACON_PER_POS           0
270 #define MAC_MGMT_MIB_STATION_ID_POS           6
271 #define MAC_MGMT_MIB_CUR_PRIVACY_POS          11
272 #define MAC_MGMT_MIB_CUR_BSSID_POS            14
273 #define MAC_MGMT_MIB_PS_MODE_POS              53
274 #define MAC_MGMT_MIB_LISTEN_INTERVAL_POS      54
275 #define MAC_MGMT_MIB_MULTI_DOMAIN_IMPLEMENTED 56
276 #define MAC_MGMT_MIB_MULTI_DOMAIN_ENABLED     57
277 #define PHY_MIB_CHANNEL_POS                   14
278 #define PHY_MIB_RATE_SET_POS                  20
279 #define PHY_MIB_REG_DOMAIN_POS                26
280 #define LOCAL_MIB_AUTO_TX_RATE_POS            3
281 #define LOCAL_MIB_SSID_SIZE                   5
282 #define LOCAL_MIB_TX_PROMISCUOUS_POS          6
283 #define LOCAL_MIB_TX_MGMT_RATE_POS            7
284 #define LOCAL_MIB_TX_CONTROL_RATE_POS         8
285 #define LOCAL_MIB_PREAMBLE_TYPE               9
286 #define MAC_ADDR_MIB_MAC_ADDR_POS             0
287 
288 #define         CMD_Set_MIB_Vars              0x01
289 #define         CMD_Get_MIB_Vars              0x02
290 #define         CMD_Scan                      0x03
291 #define         CMD_Join                      0x04
292 #define         CMD_Start                     0x05
293 #define         CMD_EnableRadio               0x06
294 #define         CMD_DisableRadio              0x07
295 #define         CMD_SiteSurvey                0x0B
296 
297 #define         CMD_STATUS_IDLE                   0x00
298 #define         CMD_STATUS_COMPLETE               0x01
299 #define         CMD_STATUS_UNKNOWN                0x02
300 #define         CMD_STATUS_INVALID_PARAMETER      0x03
301 #define         CMD_STATUS_FUNCTION_NOT_SUPPORTED 0x04
302 #define         CMD_STATUS_TIME_OUT               0x07
303 #define         CMD_STATUS_IN_PROGRESS            0x08
304 #define         CMD_STATUS_REJECTED_RADIO_OFF     0x09
305 #define         CMD_STATUS_HOST_ERROR             0xFF
306 #define         CMD_STATUS_BUSY                   0xFE
307 
308 #define CMD_BLOCK_COMMAND_OFFSET        0
309 #define CMD_BLOCK_STATUS_OFFSET         1
310 #define CMD_BLOCK_PARAMETERS_OFFSET     4
311 
312 #define SCAN_OPTIONS_SITE_SURVEY        0x80
313 
314 #define MGMT_FRAME_BODY_OFFSET		24
315 #define MAX_AUTHENTICATION_RETRIES	3
316 #define MAX_ASSOCIATION_RETRIES		3
317 
318 #define AUTHENTICATION_RESPONSE_TIME_OUT  1000
319 
320 #define MAX_WIRELESS_BODY  2316 /* mtu is 2312, CRC is 4 */
321 #define LOOP_RETRY_LIMIT   500000
322 
323 #define ACTIVE_MODE	1
324 #define PS_MODE		2
325 
326 #define MAX_ENCRYPTION_KEYS 4
327 #define MAX_ENCRYPTION_KEY_SIZE 40
328 
329 /*
330  * 802.11 related definitions
331  */
332 
333 /*
334  * Regulatory Domains
335  */
336 
337 #define REG_DOMAIN_FCC		0x10	/* Channels	1-11	USA				*/
338 #define REG_DOMAIN_DOC		0x20	/* Channel	1-11	Canada				*/
339 #define REG_DOMAIN_ETSI		0x30	/* Channel	1-13	Europe (ex Spain/France)	*/
340 #define REG_DOMAIN_SPAIN	0x31	/* Channel	10-11	Spain				*/
341 #define REG_DOMAIN_FRANCE	0x32	/* Channel	10-13	France				*/
342 #define REG_DOMAIN_MKK		0x40	/* Channel	14	Japan				*/
343 #define REG_DOMAIN_MKK1		0x41	/* Channel	1-14	Japan(MKK1)			*/
344 #define REG_DOMAIN_ISRAEL	0x50	/* Channel	3-9	ISRAEL				*/
345 
346 #define BSS_TYPE_AD_HOC		1
347 #define BSS_TYPE_INFRASTRUCTURE 2
348 
349 #define SCAN_TYPE_ACTIVE	0
350 #define SCAN_TYPE_PASSIVE	1
351 
352 #define LONG_PREAMBLE		0
353 #define SHORT_PREAMBLE		1
354 #define AUTO_PREAMBLE		2
355 
356 #define DATA_FRAME_WS_HEADER_SIZE   30
357 
358 /* promiscuous mode control */
359 #define PROM_MODE_OFF			0x0
360 #define PROM_MODE_UNKNOWN		0x1
361 #define PROM_MODE_CRC_FAILED		0x2
362 #define PROM_MODE_DUPLICATED		0x4
363 #define PROM_MODE_MGMT			0x8
364 #define PROM_MODE_CTRL			0x10
365 #define PROM_MODE_BAD_PROTOCOL		0x20
366 
367 #define IFACE_INT_STATUS_OFFSET		0
368 #define IFACE_INT_MASK_OFFSET		1
369 #define IFACE_LOCKOUT_HOST_OFFSET	2
370 #define IFACE_LOCKOUT_MAC_OFFSET	3
371 #define IFACE_FUNC_CTRL_OFFSET		28
372 #define IFACE_MAC_STAT_OFFSET		30
373 #define IFACE_GENERIC_INT_TYPE_OFFSET	32
374 
375 #define CIPHER_SUITE_NONE     0
376 #define CIPHER_SUITE_WEP_64   1
377 #define CIPHER_SUITE_TKIP     2
378 #define CIPHER_SUITE_AES      3
379 #define CIPHER_SUITE_CCX      4
380 #define CIPHER_SUITE_WEP_128  5
381 
382 /*
383  * IFACE MACROS & definitions
384  */
385 
386 /*
387  * FuncCtrl field:
388  */
389 #define FUNC_CTRL_TxENABLE		0x10
390 #define FUNC_CTRL_RxENABLE		0x20
391 #define FUNC_CTRL_INIT_COMPLETE		0x01
392 
393 /* A stub firmware image which reads the MAC address from NVRAM on the card.
394    For copyright information and source see the end of this file. */
395 static u8 mac_reader[] = {
396 	0x06, 0x00, 0x00, 0xea, 0x04, 0x00, 0x00, 0xea, 0x03, 0x00, 0x00, 0xea, 0x02, 0x00, 0x00, 0xea,
397 	0x01, 0x00, 0x00, 0xea, 0x00, 0x00, 0x00, 0xea, 0xff, 0xff, 0xff, 0xea, 0xfe, 0xff, 0xff, 0xea,
398 	0xd3, 0x00, 0xa0, 0xe3, 0x00, 0xf0, 0x21, 0xe1, 0x0e, 0x04, 0xa0, 0xe3, 0x00, 0x10, 0xa0, 0xe3,
399 	0x81, 0x11, 0xa0, 0xe1, 0x00, 0x10, 0x81, 0xe3, 0x00, 0x10, 0x80, 0xe5, 0x1c, 0x10, 0x90, 0xe5,
400 	0x10, 0x10, 0xc1, 0xe3, 0x1c, 0x10, 0x80, 0xe5, 0x01, 0x10, 0xa0, 0xe3, 0x08, 0x10, 0x80, 0xe5,
401 	0x02, 0x03, 0xa0, 0xe3, 0x00, 0x10, 0xa0, 0xe3, 0xb0, 0x10, 0xc0, 0xe1, 0xb4, 0x10, 0xc0, 0xe1,
402 	0xb8, 0x10, 0xc0, 0xe1, 0xbc, 0x10, 0xc0, 0xe1, 0x56, 0xdc, 0xa0, 0xe3, 0x21, 0x00, 0x00, 0xeb,
403 	0x0a, 0x00, 0xa0, 0xe3, 0x1a, 0x00, 0x00, 0xeb, 0x10, 0x00, 0x00, 0xeb, 0x07, 0x00, 0x00, 0xeb,
404 	0x02, 0x03, 0xa0, 0xe3, 0x02, 0x14, 0xa0, 0xe3, 0xb4, 0x10, 0xc0, 0xe1, 0x4c, 0x10, 0x9f, 0xe5,
405 	0xbc, 0x10, 0xc0, 0xe1, 0x10, 0x10, 0xa0, 0xe3, 0xb8, 0x10, 0xc0, 0xe1, 0xfe, 0xff, 0xff, 0xea,
406 	0x00, 0x40, 0x2d, 0xe9, 0x00, 0x20, 0xa0, 0xe3, 0x02, 0x3c, 0xa0, 0xe3, 0x00, 0x10, 0xa0, 0xe3,
407 	0x28, 0x00, 0x9f, 0xe5, 0x37, 0x00, 0x00, 0xeb, 0x00, 0x40, 0xbd, 0xe8, 0x1e, 0xff, 0x2f, 0xe1,
408 	0x00, 0x40, 0x2d, 0xe9, 0x12, 0x2e, 0xa0, 0xe3, 0x06, 0x30, 0xa0, 0xe3, 0x00, 0x10, 0xa0, 0xe3,
409 	0x02, 0x04, 0xa0, 0xe3, 0x2f, 0x00, 0x00, 0xeb, 0x00, 0x40, 0xbd, 0xe8, 0x1e, 0xff, 0x2f, 0xe1,
410 	0x00, 0x02, 0x00, 0x02, 0x80, 0x01, 0x90, 0xe0, 0x01, 0x00, 0x00, 0x0a, 0x01, 0x00, 0x50, 0xe2,
411 	0xfc, 0xff, 0xff, 0xea, 0x1e, 0xff, 0x2f, 0xe1, 0x80, 0x10, 0xa0, 0xe3, 0xf3, 0x06, 0xa0, 0xe3,
412 	0x00, 0x10, 0x80, 0xe5, 0x00, 0x10, 0xa0, 0xe3, 0x00, 0x10, 0x80, 0xe5, 0x01, 0x10, 0xa0, 0xe3,
413 	0x04, 0x10, 0x80, 0xe5, 0x00, 0x10, 0x80, 0xe5, 0x0e, 0x34, 0xa0, 0xe3, 0x1c, 0x10, 0x93, 0xe5,
414 	0x02, 0x1a, 0x81, 0xe3, 0x1c, 0x10, 0x83, 0xe5, 0x58, 0x11, 0x9f, 0xe5, 0x30, 0x10, 0x80, 0xe5,
415 	0x54, 0x11, 0x9f, 0xe5, 0x34, 0x10, 0x80, 0xe5, 0x38, 0x10, 0x80, 0xe5, 0x3c, 0x10, 0x80, 0xe5,
416 	0x10, 0x10, 0x90, 0xe5, 0x08, 0x00, 0x90, 0xe5, 0x1e, 0xff, 0x2f, 0xe1, 0xf3, 0x16, 0xa0, 0xe3,
417 	0x08, 0x00, 0x91, 0xe5, 0x05, 0x00, 0xa0, 0xe3, 0x0c, 0x00, 0x81, 0xe5, 0x10, 0x00, 0x91, 0xe5,
418 	0x02, 0x00, 0x10, 0xe3, 0xfc, 0xff, 0xff, 0x0a, 0xff, 0x00, 0xa0, 0xe3, 0x0c, 0x00, 0x81, 0xe5,
419 	0x10, 0x00, 0x91, 0xe5, 0x02, 0x00, 0x10, 0xe3, 0xfc, 0xff, 0xff, 0x0a, 0x08, 0x00, 0x91, 0xe5,
420 	0x10, 0x00, 0x91, 0xe5, 0x01, 0x00, 0x10, 0xe3, 0xfc, 0xff, 0xff, 0x0a, 0x08, 0x00, 0x91, 0xe5,
421 	0xff, 0x00, 0x00, 0xe2, 0x1e, 0xff, 0x2f, 0xe1, 0x30, 0x40, 0x2d, 0xe9, 0x00, 0x50, 0xa0, 0xe1,
422 	0x03, 0x40, 0xa0, 0xe1, 0xa2, 0x02, 0xa0, 0xe1, 0x08, 0x00, 0x00, 0xe2, 0x03, 0x00, 0x80, 0xe2,
423 	0xd8, 0x10, 0x9f, 0xe5, 0x00, 0x00, 0xc1, 0xe5, 0x01, 0x20, 0xc1, 0xe5, 0xe2, 0xff, 0xff, 0xeb,
424 	0x01, 0x00, 0x10, 0xe3, 0xfc, 0xff, 0xff, 0x1a, 0x14, 0x00, 0xa0, 0xe3, 0xc4, 0xff, 0xff, 0xeb,
425 	0x04, 0x20, 0xa0, 0xe1, 0x05, 0x10, 0xa0, 0xe1, 0x02, 0x00, 0xa0, 0xe3, 0x01, 0x00, 0x00, 0xeb,
426 	0x30, 0x40, 0xbd, 0xe8, 0x1e, 0xff, 0x2f, 0xe1, 0x70, 0x40, 0x2d, 0xe9, 0xf3, 0x46, 0xa0, 0xe3,
427 	0x00, 0x30, 0xa0, 0xe3, 0x00, 0x00, 0x50, 0xe3, 0x08, 0x00, 0x00, 0x9a, 0x8c, 0x50, 0x9f, 0xe5,
428 	0x03, 0x60, 0xd5, 0xe7, 0x0c, 0x60, 0x84, 0xe5, 0x10, 0x60, 0x94, 0xe5, 0x02, 0x00, 0x16, 0xe3,
429 	0xfc, 0xff, 0xff, 0x0a, 0x01, 0x30, 0x83, 0xe2, 0x00, 0x00, 0x53, 0xe1, 0xf7, 0xff, 0xff, 0x3a,
430 	0xff, 0x30, 0xa0, 0xe3, 0x0c, 0x30, 0x84, 0xe5, 0x08, 0x00, 0x94, 0xe5, 0x10, 0x00, 0x94, 0xe5,
431 	0x01, 0x00, 0x10, 0xe3, 0xfc, 0xff, 0xff, 0x0a, 0x08, 0x00, 0x94, 0xe5, 0x00, 0x00, 0xa0, 0xe3,
432 	0x00, 0x00, 0x52, 0xe3, 0x0b, 0x00, 0x00, 0x9a, 0x10, 0x50, 0x94, 0xe5, 0x02, 0x00, 0x15, 0xe3,
433 	0xfc, 0xff, 0xff, 0x0a, 0x0c, 0x30, 0x84, 0xe5, 0x10, 0x50, 0x94, 0xe5, 0x01, 0x00, 0x15, 0xe3,
434 	0xfc, 0xff, 0xff, 0x0a, 0x08, 0x50, 0x94, 0xe5, 0x01, 0x50, 0xc1, 0xe4, 0x01, 0x00, 0x80, 0xe2,
435 	0x02, 0x00, 0x50, 0xe1, 0xf3, 0xff, 0xff, 0x3a, 0xc8, 0x00, 0xa0, 0xe3, 0x98, 0xff, 0xff, 0xeb,
436 	0x70, 0x40, 0xbd, 0xe8, 0x1e, 0xff, 0x2f, 0xe1, 0x01, 0x0c, 0x00, 0x02, 0x01, 0x02, 0x00, 0x02,
437 	0x00, 0x01, 0x00, 0x02
438 };
439 
440 struct atmel_private {
441 	void *card; /* Bus dependent structure varies for PCcard */
442 	int (*present_callback)(void *); /* And callback which uses it */
443 	char firmware_id[32];
444 	AtmelFWType firmware_type;
445 	u8 *firmware;
446 	int firmware_length;
447 	struct timer_list management_timer;
448 	struct net_device *dev;
449 	struct device *sys_dev;
450 	struct iw_statistics wstats;
451 	spinlock_t irqlock, timerlock;	/* spinlocks */
452 	enum { BUS_TYPE_PCCARD, BUS_TYPE_PCI } bus_type;
453 	enum {
454 		CARD_TYPE_PARALLEL_FLASH,
455 		CARD_TYPE_SPI_FLASH,
456 		CARD_TYPE_EEPROM
457 	} card_type;
458 	int do_rx_crc; /* If we need to CRC incoming packets */
459 	int probe_crc; /* set if we don't yet know */
460 	int crc_ok_cnt, crc_ko_cnt; /* counters for probing */
461 	u16 rx_desc_head;
462 	u16 tx_desc_free, tx_desc_head, tx_desc_tail, tx_desc_previous;
463 	u16 tx_free_mem, tx_buff_head, tx_buff_tail;
464 
465 	u16 frag_seq, frag_len, frag_no;
466 	u8 frag_source[6];
467 
468 	u8 wep_is_on, default_key, exclude_unencrypted, encryption_level;
469 	u8 group_cipher_suite, pairwise_cipher_suite;
470 	u8 wep_keys[MAX_ENCRYPTION_KEYS][MAX_ENCRYPTION_KEY_SIZE];
471 	int wep_key_len[MAX_ENCRYPTION_KEYS];
472 	int use_wpa, radio_on_broken; /* firmware dependent stuff. */
473 
474 	u16 host_info_base;
475 	struct host_info_struct {
476 		/* NB this is matched to the hardware, don't change. */
477 		u8 volatile int_status;
478 		u8 volatile int_mask;
479 		u8 volatile lockout_host;
480 		u8 volatile lockout_mac;
481 
482 		u16 tx_buff_pos;
483 		u16 tx_buff_size;
484 		u16 tx_desc_pos;
485 		u16 tx_desc_count;
486 
487 		u16 rx_buff_pos;
488 		u16 rx_buff_size;
489 		u16 rx_desc_pos;
490 		u16 rx_desc_count;
491 
492 		u16 build_version;
493 		u16 command_pos;
494 
495 		u16 major_version;
496 		u16 minor_version;
497 
498 		u16 func_ctrl;
499 		u16 mac_status;
500 		u16 generic_IRQ_type;
501 		u8  reserved[2];
502 	} host_info;
503 
504 	enum {
505 		STATION_STATE_SCANNING,
506 		STATION_STATE_JOINNING,
507 		STATION_STATE_AUTHENTICATING,
508 		STATION_STATE_ASSOCIATING,
509 		STATION_STATE_READY,
510 		STATION_STATE_REASSOCIATING,
511 		STATION_STATE_DOWN,
512 		STATION_STATE_MGMT_ERROR
513 	} station_state;
514 
515 	int operating_mode, power_mode;
516 	unsigned long last_qual;
517 	int beacons_this_sec;
518 	int channel;
519 	int reg_domain, config_reg_domain;
520 	int tx_rate;
521 	int auto_tx_rate;
522 	int rts_threshold;
523 	int frag_threshold;
524 	int long_retry, short_retry;
525 	int preamble;
526 	int default_beacon_period, beacon_period, listen_interval;
527 	int CurrentAuthentTransactionSeqNum, ExpectedAuthentTransactionSeqNum;
528 	int AuthenticationRequestRetryCnt, AssociationRequestRetryCnt, ReAssociationRequestRetryCnt;
529 	enum {
530 		SITE_SURVEY_IDLE,
531 		SITE_SURVEY_IN_PROGRESS,
532 		SITE_SURVEY_COMPLETED
533 	} site_survey_state;
534 	unsigned long last_survey;
535 
536 	int station_was_associated, station_is_associated;
537 	int fast_scan;
538 
539 	struct bss_info {
540 		int channel;
541 		int SSIDsize;
542 		int RSSI;
543 		int UsingWEP;
544 		int preamble;
545 		int beacon_period;
546 		int BSStype;
547 		u8 BSSID[6];
548 		u8 SSID[MAX_SSID_LENGTH];
549 	} BSSinfo[MAX_BSS_ENTRIES];
550 	int BSS_list_entries, current_BSS;
551 	int connect_to_any_BSS;
552 	int SSID_size, new_SSID_size;
553 	u8 CurrentBSSID[6], BSSID[6];
554 	u8 SSID[MAX_SSID_LENGTH], new_SSID[MAX_SSID_LENGTH];
555 	u64 last_beacon_timestamp;
556 	u8 rx_buf[MAX_WIRELESS_BODY];
557 };
558 
559 static u8 atmel_basic_rates[4] = {0x82, 0x84, 0x0b, 0x16};
560 
561 static const struct {
562 	int reg_domain;
563 	int min, max;
564 	char *name;
565 } channel_table[] = { { REG_DOMAIN_FCC, 1, 11, "USA" },
566 		      { REG_DOMAIN_DOC, 1, 11, "Canada" },
567 		      { REG_DOMAIN_ETSI, 1, 13, "Europe" },
568 		      { REG_DOMAIN_SPAIN, 10, 11, "Spain" },
569 		      { REG_DOMAIN_FRANCE, 10, 13, "France" },
570 		      { REG_DOMAIN_MKK, 14, 14, "MKK" },
571 		      { REG_DOMAIN_MKK1, 1, 14, "MKK1" },
572 		      { REG_DOMAIN_ISRAEL, 3, 9, "Israel"} };
573 
574 static void build_wpa_mib(struct atmel_private *priv);
575 static int atmel_ioctl(struct net_device *dev, struct ifreq *rq, int cmd);
576 static void atmel_copy_to_card(struct net_device *dev, u16 dest,
577 			       const unsigned char *src, u16 len);
578 static void atmel_copy_to_host(struct net_device *dev, unsigned char *dest,
579 			       u16 src, u16 len);
580 static void atmel_set_gcr(struct net_device *dev, u16 mask);
581 static void atmel_clear_gcr(struct net_device *dev, u16 mask);
582 static int atmel_lock_mac(struct atmel_private *priv);
583 static void atmel_wmem32(struct atmel_private *priv, u16 pos, u32 data);
584 static void atmel_command_irq(struct atmel_private *priv);
585 static int atmel_validate_channel(struct atmel_private *priv, int channel);
586 static void atmel_management_frame(struct atmel_private *priv,
587 				   struct ieee80211_hdr *header,
588 				   u16 frame_len, u8 rssi);
589 static void atmel_management_timer(struct timer_list *t);
590 static void atmel_send_command(struct atmel_private *priv, int command,
591 			       void *cmd, int cmd_size);
592 static int atmel_send_command_wait(struct atmel_private *priv, int command,
593 				   void *cmd, int cmd_size);
594 static void atmel_transmit_management_frame(struct atmel_private *priv,
595 					    struct ieee80211_hdr *header,
596 					    u8 *body, int body_len);
597 
598 static u8 atmel_get_mib8(struct atmel_private *priv, u8 type, u8 index);
599 static void atmel_set_mib8(struct atmel_private *priv, u8 type, u8 index,
600 			   u8 data);
601 static void atmel_set_mib16(struct atmel_private *priv, u8 type, u8 index,
602 			    u16 data);
603 static void atmel_set_mib(struct atmel_private *priv, u8 type, u8 index,
604 			  u8 *data, int data_len);
605 static void atmel_get_mib(struct atmel_private *priv, u8 type, u8 index,
606 			  u8 *data, int data_len);
607 static void atmel_scan(struct atmel_private *priv, int specific_ssid);
608 static void atmel_join_bss(struct atmel_private *priv, int bss_index);
609 static void atmel_smooth_qual(struct atmel_private *priv);
610 static void atmel_writeAR(struct net_device *dev, u16 data);
611 static int probe_atmel_card(struct net_device *dev);
612 static int reset_atmel_card(struct net_device *dev);
613 static void atmel_enter_state(struct atmel_private *priv, int new_state);
614 int atmel_open (struct net_device *dev);
615 
616 static inline u16 atmel_hi(struct atmel_private *priv, u16 offset)
617 {
618 	return priv->host_info_base + offset;
619 }
620 
621 static inline u16 atmel_co(struct atmel_private *priv, u16 offset)
622 {
623 	return priv->host_info.command_pos + offset;
624 }
625 
626 static inline u16 atmel_rx(struct atmel_private *priv, u16 offset, u16 desc)
627 {
628 	return priv->host_info.rx_desc_pos + (sizeof(struct rx_desc) * desc) + offset;
629 }
630 
631 static inline u16 atmel_tx(struct atmel_private *priv, u16 offset, u16 desc)
632 {
633 	return priv->host_info.tx_desc_pos + (sizeof(struct tx_desc) * desc) + offset;
634 }
635 
636 static inline u8 atmel_read8(struct net_device *dev, u16 offset)
637 {
638 	return inb(dev->base_addr + offset);
639 }
640 
641 static inline void atmel_write8(struct net_device *dev, u16 offset, u8 data)
642 {
643 	outb(data, dev->base_addr + offset);
644 }
645 
646 static inline u16 atmel_read16(struct net_device *dev, u16 offset)
647 {
648 	return inw(dev->base_addr + offset);
649 }
650 
651 static inline void atmel_write16(struct net_device *dev, u16 offset, u16 data)
652 {
653 	outw(data, dev->base_addr + offset);
654 }
655 
656 static inline u8 atmel_rmem8(struct atmel_private *priv, u16 pos)
657 {
658 	atmel_writeAR(priv->dev, pos);
659 	return atmel_read8(priv->dev, DR);
660 }
661 
662 static inline void atmel_wmem8(struct atmel_private *priv, u16 pos, u16 data)
663 {
664 	atmel_writeAR(priv->dev, pos);
665 	atmel_write8(priv->dev, DR, data);
666 }
667 
668 static inline u16 atmel_rmem16(struct atmel_private *priv, u16 pos)
669 {
670 	atmel_writeAR(priv->dev, pos);
671 	return atmel_read16(priv->dev, DR);
672 }
673 
674 static inline void atmel_wmem16(struct atmel_private *priv, u16 pos, u16 data)
675 {
676 	atmel_writeAR(priv->dev, pos);
677 	atmel_write16(priv->dev, DR, data);
678 }
679 
680 static const struct iw_handler_def atmel_handler_def;
681 
682 static void tx_done_irq(struct atmel_private *priv)
683 {
684 	int i;
685 
686 	for (i = 0;
687 	     atmel_rmem8(priv, atmel_tx(priv, TX_DESC_FLAGS_OFFSET, priv->tx_desc_head)) == TX_DONE &&
688 		     i < priv->host_info.tx_desc_count;
689 	     i++) {
690 		u8 status = atmel_rmem8(priv, atmel_tx(priv, TX_DESC_STATUS_OFFSET, priv->tx_desc_head));
691 		u16 msdu_size = atmel_rmem16(priv, atmel_tx(priv, TX_DESC_SIZE_OFFSET, priv->tx_desc_head));
692 		u8 type = atmel_rmem8(priv, atmel_tx(priv, TX_DESC_PACKET_TYPE_OFFSET, priv->tx_desc_head));
693 
694 		atmel_wmem8(priv, atmel_tx(priv, TX_DESC_FLAGS_OFFSET, priv->tx_desc_head), 0);
695 
696 		priv->tx_free_mem += msdu_size;
697 		priv->tx_desc_free++;
698 
699 		if (priv->tx_buff_head + msdu_size > (priv->host_info.tx_buff_pos + priv->host_info.tx_buff_size))
700 			priv->tx_buff_head = 0;
701 		else
702 			priv->tx_buff_head += msdu_size;
703 
704 		if (priv->tx_desc_head < (priv->host_info.tx_desc_count - 1))
705 			priv->tx_desc_head++ ;
706 		else
707 			priv->tx_desc_head = 0;
708 
709 		if (type == TX_PACKET_TYPE_DATA) {
710 			if (status == TX_STATUS_SUCCESS)
711 				priv->dev->stats.tx_packets++;
712 			else
713 				priv->dev->stats.tx_errors++;
714 			netif_wake_queue(priv->dev);
715 		}
716 	}
717 }
718 
719 static u16 find_tx_buff(struct atmel_private *priv, u16 len)
720 {
721 	u16 bottom_free = priv->host_info.tx_buff_size - priv->tx_buff_tail;
722 
723 	if (priv->tx_desc_free == 3 || priv->tx_free_mem < len)
724 		return 0;
725 
726 	if (bottom_free >= len)
727 		return priv->host_info.tx_buff_pos + priv->tx_buff_tail;
728 
729 	if (priv->tx_free_mem - bottom_free >= len) {
730 		priv->tx_buff_tail = 0;
731 		return priv->host_info.tx_buff_pos;
732 	}
733 
734 	return 0;
735 }
736 
737 static void tx_update_descriptor(struct atmel_private *priv, int is_bcast,
738 				 u16 len, u16 buff, u8 type)
739 {
740 	atmel_wmem16(priv, atmel_tx(priv, TX_DESC_POS_OFFSET, priv->tx_desc_tail), buff);
741 	atmel_wmem16(priv, atmel_tx(priv, TX_DESC_SIZE_OFFSET, priv->tx_desc_tail), len);
742 	if (!priv->use_wpa)
743 		atmel_wmem16(priv, atmel_tx(priv, TX_DESC_HOST_LENGTH_OFFSET, priv->tx_desc_tail), len);
744 	atmel_wmem8(priv, atmel_tx(priv, TX_DESC_PACKET_TYPE_OFFSET, priv->tx_desc_tail), type);
745 	atmel_wmem8(priv, atmel_tx(priv, TX_DESC_RATE_OFFSET, priv->tx_desc_tail), priv->tx_rate);
746 	atmel_wmem8(priv, atmel_tx(priv, TX_DESC_RETRY_OFFSET, priv->tx_desc_tail), 0);
747 	if (priv->use_wpa) {
748 		int cipher_type, cipher_length;
749 		if (is_bcast) {
750 			cipher_type = priv->group_cipher_suite;
751 			if (cipher_type == CIPHER_SUITE_WEP_64 ||
752 			    cipher_type == CIPHER_SUITE_WEP_128)
753 				cipher_length = 8;
754 			else if (cipher_type == CIPHER_SUITE_TKIP)
755 				cipher_length = 12;
756 			else if (priv->pairwise_cipher_suite == CIPHER_SUITE_WEP_64 ||
757 				 priv->pairwise_cipher_suite == CIPHER_SUITE_WEP_128) {
758 				cipher_type = priv->pairwise_cipher_suite;
759 				cipher_length = 8;
760 			} else {
761 				cipher_type = CIPHER_SUITE_NONE;
762 				cipher_length = 0;
763 			}
764 		} else {
765 			cipher_type = priv->pairwise_cipher_suite;
766 			if (cipher_type == CIPHER_SUITE_WEP_64 ||
767 			    cipher_type == CIPHER_SUITE_WEP_128)
768 				cipher_length = 8;
769 			else if (cipher_type == CIPHER_SUITE_TKIP)
770 				cipher_length = 12;
771 			else if (priv->group_cipher_suite == CIPHER_SUITE_WEP_64 ||
772 				 priv->group_cipher_suite == CIPHER_SUITE_WEP_128) {
773 				cipher_type = priv->group_cipher_suite;
774 				cipher_length = 8;
775 			} else {
776 				cipher_type = CIPHER_SUITE_NONE;
777 				cipher_length = 0;
778 			}
779 		}
780 
781 		atmel_wmem8(priv, atmel_tx(priv, TX_DESC_CIPHER_TYPE_OFFSET, priv->tx_desc_tail),
782 			    cipher_type);
783 		atmel_wmem8(priv, atmel_tx(priv, TX_DESC_CIPHER_LENGTH_OFFSET, priv->tx_desc_tail),
784 			    cipher_length);
785 	}
786 	atmel_wmem32(priv, atmel_tx(priv, TX_DESC_NEXT_OFFSET, priv->tx_desc_tail), 0x80000000L);
787 	atmel_wmem8(priv, atmel_tx(priv, TX_DESC_FLAGS_OFFSET, priv->tx_desc_tail), TX_FIRM_OWN);
788 	if (priv->tx_desc_previous != priv->tx_desc_tail)
789 		atmel_wmem32(priv, atmel_tx(priv, TX_DESC_NEXT_OFFSET, priv->tx_desc_previous), 0);
790 	priv->tx_desc_previous = priv->tx_desc_tail;
791 	if (priv->tx_desc_tail < (priv->host_info.tx_desc_count - 1))
792 		priv->tx_desc_tail++;
793 	else
794 		priv->tx_desc_tail = 0;
795 	priv->tx_desc_free--;
796 	priv->tx_free_mem -= len;
797 }
798 
799 static netdev_tx_t start_tx(struct sk_buff *skb, struct net_device *dev)
800 {
801 	static const u8 SNAP_RFC1024[6] = { 0xaa, 0xaa, 0x03, 0x00, 0x00, 0x00 };
802 	struct atmel_private *priv = netdev_priv(dev);
803 	struct ieee80211_hdr header;
804 	unsigned long flags;
805 	u16 buff, frame_ctl, len = (ETH_ZLEN < skb->len) ? skb->len : ETH_ZLEN;
806 
807 	if (priv->card && priv->present_callback &&
808 	    !(*priv->present_callback)(priv->card)) {
809 		dev->stats.tx_errors++;
810 		dev_kfree_skb(skb);
811 		return NETDEV_TX_OK;
812 	}
813 
814 	if (priv->station_state != STATION_STATE_READY) {
815 		dev->stats.tx_errors++;
816 		dev_kfree_skb(skb);
817 		return NETDEV_TX_OK;
818 	}
819 
820 	/* first ensure the timer func cannot run */
821 	spin_lock_bh(&priv->timerlock);
822 	/* then stop the hardware ISR */
823 	spin_lock_irqsave(&priv->irqlock, flags);
824 	/* nb doing the above in the opposite order will deadlock */
825 
826 	/* The Wireless Header is 30 bytes. In the Ethernet packet we "cut" the
827 	   12 first bytes (containing DA/SA) and put them in the appropriate
828 	   fields of the Wireless Header. Thus the packet length is then the
829 	   initial + 18 (+30-12) */
830 
831 	if (!(buff = find_tx_buff(priv, len + 18))) {
832 		dev->stats.tx_dropped++;
833 		spin_unlock_irqrestore(&priv->irqlock, flags);
834 		spin_unlock_bh(&priv->timerlock);
835 		netif_stop_queue(dev);
836 		return NETDEV_TX_BUSY;
837 	}
838 
839 	frame_ctl = IEEE80211_FTYPE_DATA;
840 	header.duration_id = 0;
841 	header.seq_ctrl = 0;
842 	if (priv->wep_is_on)
843 		frame_ctl |= IEEE80211_FCTL_PROTECTED;
844 	if (priv->operating_mode == IW_MODE_ADHOC) {
845 		skb_copy_from_linear_data(skb, &header.addr1, ETH_ALEN);
846 		memcpy(&header.addr2, dev->dev_addr, ETH_ALEN);
847 		memcpy(&header.addr3, priv->BSSID, ETH_ALEN);
848 	} else {
849 		frame_ctl |= IEEE80211_FCTL_TODS;
850 		memcpy(&header.addr1, priv->CurrentBSSID, ETH_ALEN);
851 		memcpy(&header.addr2, dev->dev_addr, ETH_ALEN);
852 		skb_copy_from_linear_data(skb, &header.addr3, ETH_ALEN);
853 	}
854 
855 	if (priv->use_wpa)
856 		memcpy(&header.addr4, SNAP_RFC1024, ETH_ALEN);
857 
858 	header.frame_control = cpu_to_le16(frame_ctl);
859 	/* Copy the wireless header into the card */
860 	atmel_copy_to_card(dev, buff, (unsigned char *)&header, DATA_FRAME_WS_HEADER_SIZE);
861 	/* Copy the packet sans its 802.3 header addresses which have been replaced */
862 	atmel_copy_to_card(dev, buff + DATA_FRAME_WS_HEADER_SIZE, skb->data + 12, len - 12);
863 	priv->tx_buff_tail += len - 12 + DATA_FRAME_WS_HEADER_SIZE;
864 
865 	/* low bit of first byte of destination tells us if broadcast */
866 	tx_update_descriptor(priv, *(skb->data) & 0x01, len + 18, buff, TX_PACKET_TYPE_DATA);
867 	dev->stats.tx_bytes += len;
868 
869 	spin_unlock_irqrestore(&priv->irqlock, flags);
870 	spin_unlock_bh(&priv->timerlock);
871 	dev_kfree_skb(skb);
872 
873 	return NETDEV_TX_OK;
874 }
875 
876 static void atmel_transmit_management_frame(struct atmel_private *priv,
877 					    struct ieee80211_hdr *header,
878 					    u8 *body, int body_len)
879 {
880 	u16 buff;
881 	int len = MGMT_FRAME_BODY_OFFSET + body_len;
882 
883 	if (!(buff = find_tx_buff(priv, len)))
884 		return;
885 
886 	atmel_copy_to_card(priv->dev, buff, (u8 *)header, MGMT_FRAME_BODY_OFFSET);
887 	atmel_copy_to_card(priv->dev, buff + MGMT_FRAME_BODY_OFFSET, body, body_len);
888 	priv->tx_buff_tail += len;
889 	tx_update_descriptor(priv, header->addr1[0] & 0x01, len, buff, TX_PACKET_TYPE_MGMT);
890 }
891 
892 static void fast_rx_path(struct atmel_private *priv,
893 			 struct ieee80211_hdr *header,
894 			 u16 msdu_size, u16 rx_packet_loc, u32 crc)
895 {
896 	/* fast path: unfragmented packet copy directly into skbuf */
897 	u8 mac4[6];
898 	struct sk_buff	*skb;
899 	unsigned char *skbp;
900 
901 	/* get the final, mac 4 header field, this tells us encapsulation */
902 	atmel_copy_to_host(priv->dev, mac4, rx_packet_loc + 24, 6);
903 	msdu_size -= 6;
904 
905 	if (priv->do_rx_crc) {
906 		crc = crc32_le(crc, mac4, 6);
907 		msdu_size -= 4;
908 	}
909 
910 	if (!(skb = dev_alloc_skb(msdu_size + 14))) {
911 		priv->dev->stats.rx_dropped++;
912 		return;
913 	}
914 
915 	skb_reserve(skb, 2);
916 	skbp = skb_put(skb, msdu_size + 12);
917 	atmel_copy_to_host(priv->dev, skbp + 12, rx_packet_loc + 30, msdu_size);
918 
919 	if (priv->do_rx_crc) {
920 		u32 netcrc;
921 		crc = crc32_le(crc, skbp + 12, msdu_size);
922 		atmel_copy_to_host(priv->dev, (void *)&netcrc, rx_packet_loc + 30 + msdu_size, 4);
923 		if ((crc ^ 0xffffffff) != netcrc) {
924 			priv->dev->stats.rx_crc_errors++;
925 			dev_kfree_skb(skb);
926 			return;
927 		}
928 	}
929 
930 	memcpy(skbp, header->addr1, ETH_ALEN); /* destination address */
931 	if (le16_to_cpu(header->frame_control) & IEEE80211_FCTL_FROMDS)
932 		memcpy(&skbp[ETH_ALEN], header->addr3, ETH_ALEN);
933 	else
934 		memcpy(&skbp[ETH_ALEN], header->addr2, ETH_ALEN); /* source address */
935 
936 	skb->protocol = eth_type_trans(skb, priv->dev);
937 	skb->ip_summed = CHECKSUM_NONE;
938 	netif_rx(skb);
939 	priv->dev->stats.rx_bytes += 12 + msdu_size;
940 	priv->dev->stats.rx_packets++;
941 }
942 
943 /* Test to see if the packet in card memory at packet_loc has a valid CRC
944    It doesn't matter that this is slow: it is only used to proble the first few
945    packets. */
946 static int probe_crc(struct atmel_private *priv, u16 packet_loc, u16 msdu_size)
947 {
948 	int i = msdu_size - 4;
949 	u32 netcrc, crc = 0xffffffff;
950 
951 	if (msdu_size < 4)
952 		return 0;
953 
954 	atmel_copy_to_host(priv->dev, (void *)&netcrc, packet_loc + i, 4);
955 
956 	atmel_writeAR(priv->dev, packet_loc);
957 	while (i--) {
958 		u8 octet = atmel_read8(priv->dev, DR);
959 		crc = crc32_le(crc, &octet, 1);
960 	}
961 
962 	return (crc ^ 0xffffffff) == netcrc;
963 }
964 
965 static void frag_rx_path(struct atmel_private *priv,
966 			 struct ieee80211_hdr *header,
967 			 u16 msdu_size, u16 rx_packet_loc, u32 crc, u16 seq_no,
968 			 u8 frag_no, int more_frags)
969 {
970 	u8 mac4[ETH_ALEN];
971 	u8 source[ETH_ALEN];
972 	struct sk_buff *skb;
973 
974 	if (le16_to_cpu(header->frame_control) & IEEE80211_FCTL_FROMDS)
975 		memcpy(source, header->addr3, ETH_ALEN);
976 	else
977 		memcpy(source, header->addr2, ETH_ALEN);
978 
979 	rx_packet_loc += 24; /* skip header */
980 
981 	if (priv->do_rx_crc)
982 		msdu_size -= 4;
983 
984 	if (frag_no == 0) { /* first fragment */
985 		atmel_copy_to_host(priv->dev, mac4, rx_packet_loc, ETH_ALEN);
986 		msdu_size -= ETH_ALEN;
987 		rx_packet_loc += ETH_ALEN;
988 
989 		if (priv->do_rx_crc)
990 			crc = crc32_le(crc, mac4, 6);
991 
992 		priv->frag_seq = seq_no;
993 		priv->frag_no = 1;
994 		priv->frag_len = msdu_size;
995 		memcpy(priv->frag_source, source, ETH_ALEN);
996 		memcpy(&priv->rx_buf[ETH_ALEN], source, ETH_ALEN);
997 		memcpy(priv->rx_buf, header->addr1, ETH_ALEN);
998 
999 		atmel_copy_to_host(priv->dev, &priv->rx_buf[12], rx_packet_loc, msdu_size);
1000 
1001 		if (priv->do_rx_crc) {
1002 			u32 netcrc;
1003 			crc = crc32_le(crc, &priv->rx_buf[12], msdu_size);
1004 			atmel_copy_to_host(priv->dev, (void *)&netcrc, rx_packet_loc + msdu_size, 4);
1005 			if ((crc ^ 0xffffffff) != netcrc) {
1006 				priv->dev->stats.rx_crc_errors++;
1007 				eth_broadcast_addr(priv->frag_source);
1008 			}
1009 		}
1010 
1011 	} else if (priv->frag_no == frag_no &&
1012 		   priv->frag_seq == seq_no &&
1013 		   memcmp(priv->frag_source, source, ETH_ALEN) == 0) {
1014 
1015 		atmel_copy_to_host(priv->dev, &priv->rx_buf[12 + priv->frag_len],
1016 				   rx_packet_loc, msdu_size);
1017 		if (priv->do_rx_crc) {
1018 			u32 netcrc;
1019 			crc = crc32_le(crc,
1020 				       &priv->rx_buf[12 + priv->frag_len],
1021 				       msdu_size);
1022 			atmel_copy_to_host(priv->dev, (void *)&netcrc, rx_packet_loc + msdu_size, 4);
1023 			if ((crc ^ 0xffffffff) != netcrc) {
1024 				priv->dev->stats.rx_crc_errors++;
1025 				eth_broadcast_addr(priv->frag_source);
1026 				more_frags = 1; /* don't send broken assembly */
1027 			}
1028 		}
1029 
1030 		priv->frag_len += msdu_size;
1031 		priv->frag_no++;
1032 
1033 		if (!more_frags) { /* last one */
1034 			eth_broadcast_addr(priv->frag_source);
1035 			if (!(skb = dev_alloc_skb(priv->frag_len + 14))) {
1036 				priv->dev->stats.rx_dropped++;
1037 			} else {
1038 				skb_reserve(skb, 2);
1039 				skb_put_data(skb, priv->rx_buf,
1040 				             priv->frag_len + 12);
1041 				skb->protocol = eth_type_trans(skb, priv->dev);
1042 				skb->ip_summed = CHECKSUM_NONE;
1043 				netif_rx(skb);
1044 				priv->dev->stats.rx_bytes += priv->frag_len + 12;
1045 				priv->dev->stats.rx_packets++;
1046 			}
1047 		}
1048 	} else
1049 		priv->wstats.discard.fragment++;
1050 }
1051 
1052 static void rx_done_irq(struct atmel_private *priv)
1053 {
1054 	int i;
1055 	struct ieee80211_hdr header;
1056 
1057 	for (i = 0;
1058 	     atmel_rmem8(priv, atmel_rx(priv, RX_DESC_FLAGS_OFFSET, priv->rx_desc_head)) == RX_DESC_FLAG_VALID &&
1059 		     i < priv->host_info.rx_desc_count;
1060 	     i++) {
1061 
1062 		u16 msdu_size, rx_packet_loc, frame_ctl, seq_control;
1063 		u8 status = atmel_rmem8(priv, atmel_rx(priv, RX_DESC_STATUS_OFFSET, priv->rx_desc_head));
1064 		u32 crc = 0xffffffff;
1065 
1066 		if (status != RX_STATUS_SUCCESS) {
1067 			if (status == 0xc1) /* determined by experiment */
1068 				priv->wstats.discard.nwid++;
1069 			else
1070 				priv->dev->stats.rx_errors++;
1071 			goto next;
1072 		}
1073 
1074 		msdu_size = atmel_rmem16(priv, atmel_rx(priv, RX_DESC_MSDU_SIZE_OFFSET, priv->rx_desc_head));
1075 		rx_packet_loc = atmel_rmem16(priv, atmel_rx(priv, RX_DESC_MSDU_POS_OFFSET, priv->rx_desc_head));
1076 
1077 		if (msdu_size < 30) {
1078 			priv->dev->stats.rx_errors++;
1079 			goto next;
1080 		}
1081 
1082 		/* Get header as far as end of seq_ctrl */
1083 		atmel_copy_to_host(priv->dev, (char *)&header, rx_packet_loc, 24);
1084 		frame_ctl = le16_to_cpu(header.frame_control);
1085 		seq_control = le16_to_cpu(header.seq_ctrl);
1086 
1087 		/* probe for CRC use here if needed  once five packets have
1088 		   arrived with the same crc status, we assume we know what's
1089 		   happening and stop probing */
1090 		if (priv->probe_crc) {
1091 			if (!priv->wep_is_on || !(frame_ctl & IEEE80211_FCTL_PROTECTED)) {
1092 				priv->do_rx_crc = probe_crc(priv, rx_packet_loc, msdu_size);
1093 			} else {
1094 				priv->do_rx_crc = probe_crc(priv, rx_packet_loc + 24, msdu_size - 24);
1095 			}
1096 			if (priv->do_rx_crc) {
1097 				if (priv->crc_ok_cnt++ > 5)
1098 					priv->probe_crc = 0;
1099 			} else {
1100 				if (priv->crc_ko_cnt++ > 5)
1101 					priv->probe_crc = 0;
1102 			}
1103 		}
1104 
1105 		/* don't CRC header when WEP in use */
1106 		if (priv->do_rx_crc && (!priv->wep_is_on || !(frame_ctl & IEEE80211_FCTL_PROTECTED))) {
1107 			crc = crc32_le(0xffffffff, (unsigned char *)&header, 24);
1108 		}
1109 		msdu_size -= 24; /* header */
1110 
1111 		if ((frame_ctl & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_DATA) {
1112 			int more_fragments = frame_ctl & IEEE80211_FCTL_MOREFRAGS;
1113 			u8 packet_fragment_no = seq_control & IEEE80211_SCTL_FRAG;
1114 			u16 packet_sequence_no = (seq_control & IEEE80211_SCTL_SEQ) >> 4;
1115 
1116 			if (!more_fragments && packet_fragment_no == 0) {
1117 				fast_rx_path(priv, &header, msdu_size, rx_packet_loc, crc);
1118 			} else {
1119 				frag_rx_path(priv, &header, msdu_size, rx_packet_loc, crc,
1120 					     packet_sequence_no, packet_fragment_no, more_fragments);
1121 			}
1122 		}
1123 
1124 		if ((frame_ctl & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_MGMT) {
1125 			/* copy rest of packet into buffer */
1126 			atmel_copy_to_host(priv->dev, (unsigned char *)&priv->rx_buf, rx_packet_loc + 24, msdu_size);
1127 
1128 			/* we use the same buffer for frag reassembly and control packets */
1129 			eth_broadcast_addr(priv->frag_source);
1130 
1131 			if (priv->do_rx_crc) {
1132 				/* last 4 octets is crc */
1133 				msdu_size -= 4;
1134 				crc = crc32_le(crc, (unsigned char *)&priv->rx_buf, msdu_size);
1135 				if ((crc ^ 0xffffffff) != (*((u32 *)&priv->rx_buf[msdu_size]))) {
1136 					priv->dev->stats.rx_crc_errors++;
1137 					goto next;
1138 				}
1139 			}
1140 
1141 			atmel_management_frame(priv, &header, msdu_size,
1142 					       atmel_rmem8(priv, atmel_rx(priv, RX_DESC_RSSI_OFFSET, priv->rx_desc_head)));
1143 		}
1144 
1145 next:
1146 		/* release descriptor */
1147 		atmel_wmem8(priv, atmel_rx(priv, RX_DESC_FLAGS_OFFSET, priv->rx_desc_head), RX_DESC_FLAG_CONSUMED);
1148 
1149 		if (priv->rx_desc_head < (priv->host_info.rx_desc_count - 1))
1150 			priv->rx_desc_head++;
1151 		else
1152 			priv->rx_desc_head = 0;
1153 	}
1154 }
1155 
1156 static irqreturn_t service_interrupt(int irq, void *dev_id)
1157 {
1158 	struct net_device *dev = (struct net_device *) dev_id;
1159 	struct atmel_private *priv = netdev_priv(dev);
1160 	u8 isr;
1161 	int i = -1;
1162 	static const u8 irq_order[] = {
1163 		ISR_OUT_OF_RANGE,
1164 		ISR_RxCOMPLETE,
1165 		ISR_TxCOMPLETE,
1166 		ISR_RxFRAMELOST,
1167 		ISR_FATAL_ERROR,
1168 		ISR_COMMAND_COMPLETE,
1169 		ISR_IBSS_MERGE,
1170 		ISR_GENERIC_IRQ
1171 	};
1172 
1173 	if (priv->card && priv->present_callback &&
1174 	    !(*priv->present_callback)(priv->card))
1175 		return IRQ_HANDLED;
1176 
1177 	/* In this state upper-level code assumes it can mess with
1178 	   the card unhampered by interrupts which may change register state.
1179 	   Note that even though the card shouldn't generate interrupts
1180 	   the inturrupt line may be shared. This allows card setup
1181 	   to go on without disabling interrupts for a long time. */
1182 	if (priv->station_state == STATION_STATE_DOWN)
1183 		return IRQ_NONE;
1184 
1185 	atmel_clear_gcr(dev, GCR_ENINT); /* disable interrupts */
1186 
1187 	while (1) {
1188 		if (!atmel_lock_mac(priv)) {
1189 			/* failed to contact card */
1190 			printk(KERN_ALERT "%s: failed to contact MAC.\n", dev->name);
1191 			return IRQ_HANDLED;
1192 		}
1193 
1194 		isr = atmel_rmem8(priv, atmel_hi(priv, IFACE_INT_STATUS_OFFSET));
1195 		atmel_wmem8(priv, atmel_hi(priv, IFACE_LOCKOUT_MAC_OFFSET), 0);
1196 
1197 		if (!isr) {
1198 			atmel_set_gcr(dev, GCR_ENINT); /* enable interrupts */
1199 			return i == -1 ? IRQ_NONE : IRQ_HANDLED;
1200 		}
1201 
1202 		atmel_set_gcr(dev, GCR_ACKINT); /* acknowledge interrupt */
1203 
1204 		for (i = 0; i < ARRAY_SIZE(irq_order); i++)
1205 			if (isr & irq_order[i])
1206 				break;
1207 
1208 		if (!atmel_lock_mac(priv)) {
1209 			/* failed to contact card */
1210 			printk(KERN_ALERT "%s: failed to contact MAC.\n", dev->name);
1211 			return IRQ_HANDLED;
1212 		}
1213 
1214 		isr = atmel_rmem8(priv, atmel_hi(priv, IFACE_INT_STATUS_OFFSET));
1215 		isr ^= irq_order[i];
1216 		atmel_wmem8(priv, atmel_hi(priv, IFACE_INT_STATUS_OFFSET), isr);
1217 		atmel_wmem8(priv, atmel_hi(priv, IFACE_LOCKOUT_MAC_OFFSET), 0);
1218 
1219 		switch (irq_order[i]) {
1220 
1221 		case ISR_OUT_OF_RANGE:
1222 			if (priv->operating_mode == IW_MODE_INFRA &&
1223 			    priv->station_state == STATION_STATE_READY) {
1224 				priv->station_is_associated = 0;
1225 				atmel_scan(priv, 1);
1226 			}
1227 			break;
1228 
1229 		case ISR_RxFRAMELOST:
1230 			priv->wstats.discard.misc++;
1231 			/* fall through */
1232 		case ISR_RxCOMPLETE:
1233 			rx_done_irq(priv);
1234 			break;
1235 
1236 		case ISR_TxCOMPLETE:
1237 			tx_done_irq(priv);
1238 			break;
1239 
1240 		case ISR_FATAL_ERROR:
1241 			printk(KERN_ALERT "%s: *** FATAL error interrupt ***\n", dev->name);
1242 			atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
1243 			break;
1244 
1245 		case ISR_COMMAND_COMPLETE:
1246 			atmel_command_irq(priv);
1247 			break;
1248 
1249 		case ISR_IBSS_MERGE:
1250 			atmel_get_mib(priv, Mac_Mgmt_Mib_Type, MAC_MGMT_MIB_CUR_BSSID_POS,
1251 				      priv->CurrentBSSID, 6);
1252 			/* The WPA stuff cares about the current AP address */
1253 			if (priv->use_wpa)
1254 				build_wpa_mib(priv);
1255 			break;
1256 		case ISR_GENERIC_IRQ:
1257 			printk(KERN_INFO "%s: Generic_irq received.\n", dev->name);
1258 			break;
1259 		}
1260 	}
1261 }
1262 
1263 static struct iw_statistics *atmel_get_wireless_stats(struct net_device *dev)
1264 {
1265 	struct atmel_private *priv = netdev_priv(dev);
1266 
1267 	/* update the link quality here in case we are seeing no beacons
1268 	   at all to drive the process */
1269 	atmel_smooth_qual(priv);
1270 
1271 	priv->wstats.status = priv->station_state;
1272 
1273 	if (priv->operating_mode == IW_MODE_INFRA) {
1274 		if (priv->station_state != STATION_STATE_READY) {
1275 			priv->wstats.qual.qual = 0;
1276 			priv->wstats.qual.level = 0;
1277 			priv->wstats.qual.updated = (IW_QUAL_QUAL_INVALID
1278 					| IW_QUAL_LEVEL_INVALID);
1279 		}
1280 		priv->wstats.qual.noise = 0;
1281 		priv->wstats.qual.updated |= IW_QUAL_NOISE_INVALID;
1282 	} else {
1283 		/* Quality levels cannot be determined in ad-hoc mode,
1284 		   because we can 'hear' more that one remote station. */
1285 		priv->wstats.qual.qual = 0;
1286 		priv->wstats.qual.level	= 0;
1287 		priv->wstats.qual.noise	= 0;
1288 		priv->wstats.qual.updated = IW_QUAL_QUAL_INVALID
1289 					| IW_QUAL_LEVEL_INVALID
1290 					| IW_QUAL_NOISE_INVALID;
1291 		priv->wstats.miss.beacon = 0;
1292 	}
1293 
1294 	return &priv->wstats;
1295 }
1296 
1297 static int atmel_set_mac_address(struct net_device *dev, void *p)
1298 {
1299 	struct sockaddr *addr = p;
1300 
1301 	memcpy (dev->dev_addr, addr->sa_data, dev->addr_len);
1302 	return atmel_open(dev);
1303 }
1304 
1305 EXPORT_SYMBOL(atmel_open);
1306 
1307 int atmel_open(struct net_device *dev)
1308 {
1309 	struct atmel_private *priv = netdev_priv(dev);
1310 	int i, channel, err;
1311 
1312 	/* any scheduled timer is no longer needed and might screw things up.. */
1313 	del_timer_sync(&priv->management_timer);
1314 
1315 	/* Interrupts will not touch the card once in this state... */
1316 	priv->station_state = STATION_STATE_DOWN;
1317 
1318 	if (priv->new_SSID_size) {
1319 		memcpy(priv->SSID, priv->new_SSID, priv->new_SSID_size);
1320 		priv->SSID_size = priv->new_SSID_size;
1321 		priv->new_SSID_size = 0;
1322 	}
1323 	priv->BSS_list_entries = 0;
1324 
1325 	priv->AuthenticationRequestRetryCnt = 0;
1326 	priv->AssociationRequestRetryCnt = 0;
1327 	priv->ReAssociationRequestRetryCnt = 0;
1328 	priv->CurrentAuthentTransactionSeqNum = 0x0001;
1329 	priv->ExpectedAuthentTransactionSeqNum = 0x0002;
1330 
1331 	priv->site_survey_state = SITE_SURVEY_IDLE;
1332 	priv->station_is_associated = 0;
1333 
1334 	err = reset_atmel_card(dev);
1335 	if (err)
1336 		return err;
1337 
1338 	if (priv->config_reg_domain) {
1339 		priv->reg_domain = priv->config_reg_domain;
1340 		atmel_set_mib8(priv, Phy_Mib_Type, PHY_MIB_REG_DOMAIN_POS, priv->reg_domain);
1341 	} else {
1342 		priv->reg_domain = atmel_get_mib8(priv, Phy_Mib_Type, PHY_MIB_REG_DOMAIN_POS);
1343 		for (i = 0; i < ARRAY_SIZE(channel_table); i++)
1344 			if (priv->reg_domain == channel_table[i].reg_domain)
1345 				break;
1346 		if (i == ARRAY_SIZE(channel_table)) {
1347 			priv->reg_domain = REG_DOMAIN_MKK1;
1348 			printk(KERN_ALERT "%s: failed to get regulatory domain: assuming MKK1.\n", dev->name);
1349 		}
1350 	}
1351 
1352 	if ((channel = atmel_validate_channel(priv, priv->channel)))
1353 		priv->channel = channel;
1354 
1355 	/* this moves station_state on.... */
1356 	atmel_scan(priv, 1);
1357 
1358 	atmel_set_gcr(priv->dev, GCR_ENINT); /* enable interrupts */
1359 	return 0;
1360 }
1361 
1362 static int atmel_close(struct net_device *dev)
1363 {
1364 	struct atmel_private *priv = netdev_priv(dev);
1365 
1366 	/* Send event to userspace that we are disassociating */
1367 	if (priv->station_state == STATION_STATE_READY) {
1368 		union iwreq_data wrqu;
1369 
1370 		wrqu.data.length = 0;
1371 		wrqu.data.flags = 0;
1372 		wrqu.ap_addr.sa_family = ARPHRD_ETHER;
1373 		eth_zero_addr(wrqu.ap_addr.sa_data);
1374 		wireless_send_event(priv->dev, SIOCGIWAP, &wrqu, NULL);
1375 	}
1376 
1377 	atmel_enter_state(priv, STATION_STATE_DOWN);
1378 
1379 	if (priv->bus_type == BUS_TYPE_PCCARD)
1380 		atmel_write16(dev, GCR, 0x0060);
1381 	atmel_write16(dev, GCR, 0x0040);
1382 	return 0;
1383 }
1384 
1385 static int atmel_validate_channel(struct atmel_private *priv, int channel)
1386 {
1387 	/* check that channel is OK, if so return zero,
1388 	   else return suitable default channel */
1389 	int i;
1390 
1391 	for (i = 0; i < ARRAY_SIZE(channel_table); i++)
1392 		if (priv->reg_domain == channel_table[i].reg_domain) {
1393 			if (channel >= channel_table[i].min &&
1394 			    channel <= channel_table[i].max)
1395 				return 0;
1396 			else
1397 				return channel_table[i].min;
1398 		}
1399 	return 0;
1400 }
1401 
1402 static int atmel_proc_show(struct seq_file *m, void *v)
1403 {
1404 	struct atmel_private *priv = m->private;
1405 	int i;
1406 	char *s, *r, *c;
1407 
1408 	seq_printf(m, "Driver version:\t\t%d.%d\n", DRIVER_MAJOR, DRIVER_MINOR);
1409 
1410 	if (priv->station_state != STATION_STATE_DOWN) {
1411 		seq_printf(m,
1412 			   "Firmware version:\t%d.%d build %d\n"
1413 			   "Firmware location:\t",
1414 			   priv->host_info.major_version,
1415 			   priv->host_info.minor_version,
1416 			   priv->host_info.build_version);
1417 
1418 		if (priv->card_type != CARD_TYPE_EEPROM)
1419 			seq_puts(m, "on card\n");
1420 		else if (priv->firmware)
1421 			seq_printf(m, "%s loaded by host\n", priv->firmware_id);
1422 		else
1423 			seq_printf(m, "%s loaded by hotplug\n", priv->firmware_id);
1424 
1425 		switch (priv->card_type) {
1426 		case CARD_TYPE_PARALLEL_FLASH:
1427 			c = "Parallel flash";
1428 			break;
1429 		case CARD_TYPE_SPI_FLASH:
1430 			c = "SPI flash\n";
1431 			break;
1432 		case CARD_TYPE_EEPROM:
1433 			c = "EEPROM";
1434 			break;
1435 		default:
1436 			c = "<unknown>";
1437 		}
1438 
1439 		r = "<unknown>";
1440 		for (i = 0; i < ARRAY_SIZE(channel_table); i++)
1441 			if (priv->reg_domain == channel_table[i].reg_domain)
1442 				r = channel_table[i].name;
1443 
1444 		seq_printf(m, "MAC memory type:\t%s\n", c);
1445 		seq_printf(m, "Regulatory domain:\t%s\n", r);
1446 		seq_printf(m, "Host CRC checking:\t%s\n",
1447 			 priv->do_rx_crc ? "On" : "Off");
1448 		seq_printf(m, "WPA-capable firmware:\t%s\n",
1449 			 priv->use_wpa ? "Yes" : "No");
1450 	}
1451 
1452 	switch (priv->station_state) {
1453 	case STATION_STATE_SCANNING:
1454 		s = "Scanning";
1455 		break;
1456 	case STATION_STATE_JOINNING:
1457 		s = "Joining";
1458 		break;
1459 	case STATION_STATE_AUTHENTICATING:
1460 		s = "Authenticating";
1461 		break;
1462 	case STATION_STATE_ASSOCIATING:
1463 		s = "Associating";
1464 		break;
1465 	case STATION_STATE_READY:
1466 		s = "Ready";
1467 		break;
1468 	case STATION_STATE_REASSOCIATING:
1469 		s = "Reassociating";
1470 		break;
1471 	case STATION_STATE_MGMT_ERROR:
1472 		s = "Management error";
1473 		break;
1474 	case STATION_STATE_DOWN:
1475 		s = "Down";
1476 		break;
1477 	default:
1478 		s = "<unknown>";
1479 	}
1480 
1481 	seq_printf(m, "Current state:\t\t%s\n", s);
1482 	return 0;
1483 }
1484 
1485 static const struct net_device_ops atmel_netdev_ops = {
1486 	.ndo_open 		= atmel_open,
1487 	.ndo_stop		= atmel_close,
1488 	.ndo_set_mac_address 	= atmel_set_mac_address,
1489 	.ndo_start_xmit 	= start_tx,
1490 	.ndo_do_ioctl 		= atmel_ioctl,
1491 	.ndo_validate_addr	= eth_validate_addr,
1492 };
1493 
1494 struct net_device *init_atmel_card(unsigned short irq, unsigned long port,
1495 				   const AtmelFWType fw_type,
1496 				   struct device *sys_dev,
1497 				   int (*card_present)(void *), void *card)
1498 {
1499 	struct net_device *dev;
1500 	struct atmel_private *priv;
1501 	int rc;
1502 
1503 	/* Create the network device object. */
1504 	dev = alloc_etherdev(sizeof(*priv));
1505 	if (!dev)
1506 		return NULL;
1507 
1508 	if (dev_alloc_name(dev, dev->name) < 0) {
1509 		printk(KERN_ERR "atmel: Couldn't get name!\n");
1510 		goto err_out_free;
1511 	}
1512 
1513 	priv = netdev_priv(dev);
1514 	priv->dev = dev;
1515 	priv->sys_dev = sys_dev;
1516 	priv->present_callback = card_present;
1517 	priv->card = card;
1518 	priv->firmware = NULL;
1519 	priv->firmware_type = fw_type;
1520 	if (firmware) /* module parameter */
1521 		strlcpy(priv->firmware_id, firmware, sizeof(priv->firmware_id));
1522 	priv->bus_type = card_present ? BUS_TYPE_PCCARD : BUS_TYPE_PCI;
1523 	priv->station_state = STATION_STATE_DOWN;
1524 	priv->do_rx_crc = 0;
1525 	/* For PCMCIA cards, some chips need CRC, some don't
1526 	   so we have to probe. */
1527 	if (priv->bus_type == BUS_TYPE_PCCARD) {
1528 		priv->probe_crc = 1;
1529 		priv->crc_ok_cnt = priv->crc_ko_cnt = 0;
1530 	} else
1531 		priv->probe_crc = 0;
1532 	priv->last_qual = jiffies;
1533 	priv->last_beacon_timestamp = 0;
1534 	memset(priv->frag_source, 0xff, sizeof(priv->frag_source));
1535 	eth_zero_addr(priv->BSSID);
1536 	priv->CurrentBSSID[0] = 0xFF; /* Initialize to something invalid.... */
1537 	priv->station_was_associated = 0;
1538 
1539 	priv->last_survey = jiffies;
1540 	priv->preamble = LONG_PREAMBLE;
1541 	priv->operating_mode = IW_MODE_INFRA;
1542 	priv->connect_to_any_BSS = 0;
1543 	priv->config_reg_domain = 0;
1544 	priv->reg_domain = 0;
1545 	priv->tx_rate = 3;
1546 	priv->auto_tx_rate = 1;
1547 	priv->channel = 4;
1548 	priv->power_mode = 0;
1549 	priv->SSID[0] = '\0';
1550 	priv->SSID_size = 0;
1551 	priv->new_SSID_size = 0;
1552 	priv->frag_threshold = 2346;
1553 	priv->rts_threshold = 2347;
1554 	priv->short_retry = 7;
1555 	priv->long_retry = 4;
1556 
1557 	priv->wep_is_on = 0;
1558 	priv->default_key = 0;
1559 	priv->encryption_level = 0;
1560 	priv->exclude_unencrypted = 0;
1561 	priv->group_cipher_suite = priv->pairwise_cipher_suite = CIPHER_SUITE_NONE;
1562 	priv->use_wpa = 0;
1563 	memset(priv->wep_keys, 0, sizeof(priv->wep_keys));
1564 	memset(priv->wep_key_len, 0, sizeof(priv->wep_key_len));
1565 
1566 	priv->default_beacon_period = priv->beacon_period = 100;
1567 	priv->listen_interval = 1;
1568 
1569 	timer_setup(&priv->management_timer, atmel_management_timer, 0);
1570 	spin_lock_init(&priv->irqlock);
1571 	spin_lock_init(&priv->timerlock);
1572 
1573 	dev->netdev_ops = &atmel_netdev_ops;
1574 	dev->wireless_handlers = &atmel_handler_def;
1575 	dev->irq = irq;
1576 	dev->base_addr = port;
1577 
1578 	/* MTU range: 68 - 2312 */
1579 	dev->min_mtu = 68;
1580 	dev->max_mtu = MAX_WIRELESS_BODY - ETH_FCS_LEN;
1581 
1582 	SET_NETDEV_DEV(dev, sys_dev);
1583 
1584 	if ((rc = request_irq(dev->irq, service_interrupt, IRQF_SHARED, dev->name, dev))) {
1585 		printk(KERN_ERR "%s: register interrupt %d failed, rc %d\n", dev->name, irq, rc);
1586 		goto err_out_free;
1587 	}
1588 
1589 	if (!request_region(dev->base_addr, 32,
1590 			    priv->bus_type == BUS_TYPE_PCCARD ?  "atmel_cs" : "atmel_pci")) {
1591 		goto err_out_irq;
1592 	}
1593 
1594 	if (register_netdev(dev))
1595 		goto err_out_res;
1596 
1597 	if (!probe_atmel_card(dev)) {
1598 		unregister_netdev(dev);
1599 		goto err_out_res;
1600 	}
1601 
1602 	netif_carrier_off(dev);
1603 
1604 	if (!proc_create_single_data("driver/atmel", 0, NULL, atmel_proc_show,
1605 			priv))
1606 		printk(KERN_WARNING "atmel: unable to create /proc entry.\n");
1607 
1608 	printk(KERN_INFO "%s: Atmel at76c50x. Version %d.%d. MAC %pM\n",
1609 	       dev->name, DRIVER_MAJOR, DRIVER_MINOR, dev->dev_addr);
1610 
1611 	return dev;
1612 
1613 err_out_res:
1614 	release_region(dev->base_addr, 32);
1615 err_out_irq:
1616 	free_irq(dev->irq, dev);
1617 err_out_free:
1618 	free_netdev(dev);
1619 	return NULL;
1620 }
1621 
1622 EXPORT_SYMBOL(init_atmel_card);
1623 
1624 void stop_atmel_card(struct net_device *dev)
1625 {
1626 	struct atmel_private *priv = netdev_priv(dev);
1627 
1628 	/* put a brick on it... */
1629 	if (priv->bus_type == BUS_TYPE_PCCARD)
1630 		atmel_write16(dev, GCR, 0x0060);
1631 	atmel_write16(dev, GCR, 0x0040);
1632 
1633 	del_timer_sync(&priv->management_timer);
1634 	unregister_netdev(dev);
1635 	remove_proc_entry("driver/atmel", NULL);
1636 	free_irq(dev->irq, dev);
1637 	kfree(priv->firmware);
1638 	release_region(dev->base_addr, 32);
1639 	free_netdev(dev);
1640 }
1641 
1642 EXPORT_SYMBOL(stop_atmel_card);
1643 
1644 static int atmel_set_essid(struct net_device *dev,
1645 			   struct iw_request_info *info,
1646 			   struct iw_point *dwrq,
1647 			   char *extra)
1648 {
1649 	struct atmel_private *priv = netdev_priv(dev);
1650 
1651 	/* Check if we asked for `any' */
1652 	if (dwrq->flags == 0) {
1653 		priv->connect_to_any_BSS = 1;
1654 	} else {
1655 		int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
1656 
1657 		priv->connect_to_any_BSS = 0;
1658 
1659 		/* Check the size of the string */
1660 		if (dwrq->length > MAX_SSID_LENGTH)
1661 			 return -E2BIG;
1662 		if (index != 0)
1663 			return -EINVAL;
1664 
1665 		memcpy(priv->new_SSID, extra, dwrq->length);
1666 		priv->new_SSID_size = dwrq->length;
1667 	}
1668 
1669 	return -EINPROGRESS;
1670 }
1671 
1672 static int atmel_get_essid(struct net_device *dev,
1673 			   struct iw_request_info *info,
1674 			   struct iw_point *dwrq,
1675 			   char *extra)
1676 {
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 
1693 static int atmel_get_wap(struct net_device *dev,
1694 			 struct iw_request_info *info,
1695 			 struct sockaddr *awrq,
1696 			 char *extra)
1697 {
1698 	struct atmel_private *priv = netdev_priv(dev);
1699 	memcpy(awrq->sa_data, priv->CurrentBSSID, ETH_ALEN);
1700 	awrq->sa_family = ARPHRD_ETHER;
1701 
1702 	return 0;
1703 }
1704 
1705 static int atmel_set_encode(struct net_device *dev,
1706 			    struct iw_request_info *info,
1707 			    struct iw_point *dwrq,
1708 			    char *extra)
1709 {
1710 	struct atmel_private *priv = netdev_priv(dev);
1711 
1712 	/* Basic checking: do we have a key to set ?
1713 	 * Note : with the new API, it's impossible to get a NULL pointer.
1714 	 * Therefore, we need to check a key size == 0 instead.
1715 	 * New version of iwconfig properly set the IW_ENCODE_NOKEY flag
1716 	 * when no key is present (only change flags), but older versions
1717 	 * don't do it. - Jean II */
1718 	if (dwrq->length > 0) {
1719 		int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
1720 		int current_index = priv->default_key;
1721 		/* Check the size of the key */
1722 		if (dwrq->length > 13) {
1723 			return -EINVAL;
1724 		}
1725 		/* Check the index (none -> use current) */
1726 		if (index < 0 || index >= 4)
1727 			index = current_index;
1728 		else
1729 			priv->default_key = index;
1730 		/* Set the length */
1731 		if (dwrq->length > 5)
1732 			priv->wep_key_len[index] = 13;
1733 		else
1734 			if (dwrq->length > 0)
1735 				priv->wep_key_len[index] = 5;
1736 			else
1737 				/* Disable the key */
1738 				priv->wep_key_len[index] = 0;
1739 		/* Check if the key is not marked as invalid */
1740 		if (!(dwrq->flags & IW_ENCODE_NOKEY)) {
1741 			/* Cleanup */
1742 			memset(priv->wep_keys[index], 0, 13);
1743 			/* Copy the key in the driver */
1744 			memcpy(priv->wep_keys[index], extra, dwrq->length);
1745 		}
1746 		/* WE specify that if a valid key is set, encryption
1747 		 * should be enabled (user may turn it off later)
1748 		 * This is also how "iwconfig ethX key on" works */
1749 		if (index == current_index &&
1750 		    priv->wep_key_len[index] > 0) {
1751 			priv->wep_is_on = 1;
1752 			priv->exclude_unencrypted = 1;
1753 			if (priv->wep_key_len[index] > 5) {
1754 				priv->pairwise_cipher_suite = CIPHER_SUITE_WEP_128;
1755 				priv->encryption_level = 2;
1756 			} else {
1757 				priv->pairwise_cipher_suite = CIPHER_SUITE_WEP_64;
1758 				priv->encryption_level = 1;
1759 			}
1760 		}
1761 	} else {
1762 		/* Do we want to just set the transmit key index ? */
1763 		int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
1764 		if (index >= 0 && index < 4) {
1765 			priv->default_key = index;
1766 		} else
1767 			/* Don't complain if only change the mode */
1768 			if (!(dwrq->flags & IW_ENCODE_MODE))
1769 				return -EINVAL;
1770 	}
1771 	/* Read the flags */
1772 	if (dwrq->flags & IW_ENCODE_DISABLED) {
1773 		priv->wep_is_on = 0;
1774 		priv->encryption_level = 0;
1775 		priv->pairwise_cipher_suite = CIPHER_SUITE_NONE;
1776 	} else {
1777 		priv->wep_is_on = 1;
1778 		if (priv->wep_key_len[priv->default_key] > 5) {
1779 			priv->pairwise_cipher_suite = CIPHER_SUITE_WEP_128;
1780 			priv->encryption_level = 2;
1781 		} else {
1782 			priv->pairwise_cipher_suite = CIPHER_SUITE_WEP_64;
1783 			priv->encryption_level = 1;
1784 		}
1785 	}
1786 	if (dwrq->flags & IW_ENCODE_RESTRICTED)
1787 		priv->exclude_unencrypted = 1;
1788 	if (dwrq->flags & IW_ENCODE_OPEN)
1789 		priv->exclude_unencrypted = 0;
1790 
1791 	return -EINPROGRESS;		/* Call commit handler */
1792 }
1793 
1794 static int atmel_get_encode(struct net_device *dev,
1795 			    struct iw_request_info *info,
1796 			    struct iw_point *dwrq,
1797 			    char *extra)
1798 {
1799 	struct atmel_private *priv = netdev_priv(dev);
1800 	int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
1801 
1802 	if (!priv->wep_is_on)
1803 		dwrq->flags = IW_ENCODE_DISABLED;
1804 	else {
1805 		if (priv->exclude_unencrypted)
1806 			dwrq->flags = IW_ENCODE_RESTRICTED;
1807 		else
1808 			dwrq->flags = IW_ENCODE_OPEN;
1809 	}
1810 		/* Which key do we want ? -1 -> tx index */
1811 	if (index < 0 || index >= 4)
1812 		index = priv->default_key;
1813 	dwrq->flags |= index + 1;
1814 	/* Copy the key to the user buffer */
1815 	dwrq->length = priv->wep_key_len[index];
1816 	if (dwrq->length > 16) {
1817 		dwrq->length = 0;
1818 	} else {
1819 		memset(extra, 0, 16);
1820 		memcpy(extra, priv->wep_keys[index], dwrq->length);
1821 	}
1822 
1823 	return 0;
1824 }
1825 
1826 static int atmel_set_encodeext(struct net_device *dev,
1827 			    struct iw_request_info *info,
1828 			    union iwreq_data *wrqu,
1829 			    char *extra)
1830 {
1831 	struct atmel_private *priv = netdev_priv(dev);
1832 	struct iw_point *encoding = &wrqu->encoding;
1833 	struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
1834 	int idx, key_len, alg = ext->alg, set_key = 1;
1835 
1836 	/* Determine and validate the key index */
1837 	idx = encoding->flags & IW_ENCODE_INDEX;
1838 	if (idx) {
1839 		if (idx < 1 || idx > 4)
1840 			return -EINVAL;
1841 		idx--;
1842 	} else
1843 		idx = priv->default_key;
1844 
1845 	if (encoding->flags & IW_ENCODE_DISABLED)
1846 	    alg = IW_ENCODE_ALG_NONE;
1847 
1848 	if (ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY) {
1849 		priv->default_key = idx;
1850 		set_key = ext->key_len > 0 ? 1 : 0;
1851 	}
1852 
1853 	if (set_key) {
1854 		/* Set the requested key first */
1855 		switch (alg) {
1856 		case IW_ENCODE_ALG_NONE:
1857 			priv->wep_is_on = 0;
1858 			priv->encryption_level = 0;
1859 			priv->pairwise_cipher_suite = CIPHER_SUITE_NONE;
1860 			break;
1861 		case IW_ENCODE_ALG_WEP:
1862 			if (ext->key_len > 5) {
1863 				priv->wep_key_len[idx] = 13;
1864 				priv->pairwise_cipher_suite = CIPHER_SUITE_WEP_128;
1865 				priv->encryption_level = 2;
1866 			} else if (ext->key_len > 0) {
1867 				priv->wep_key_len[idx] = 5;
1868 				priv->pairwise_cipher_suite = CIPHER_SUITE_WEP_64;
1869 				priv->encryption_level = 1;
1870 			} else {
1871 				return -EINVAL;
1872 			}
1873 			priv->wep_is_on = 1;
1874 			memset(priv->wep_keys[idx], 0, 13);
1875 			key_len = min ((int)ext->key_len, priv->wep_key_len[idx]);
1876 			memcpy(priv->wep_keys[idx], ext->key, key_len);
1877 			break;
1878 		default:
1879 			return -EINVAL;
1880 		}
1881 	}
1882 
1883 	return -EINPROGRESS;
1884 }
1885 
1886 static int atmel_get_encodeext(struct net_device *dev,
1887 			    struct iw_request_info *info,
1888 			    union iwreq_data *wrqu,
1889 			    char *extra)
1890 {
1891 	struct atmel_private *priv = netdev_priv(dev);
1892 	struct iw_point *encoding = &wrqu->encoding;
1893 	struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
1894 	int idx, max_key_len;
1895 
1896 	max_key_len = encoding->length - sizeof(*ext);
1897 	if (max_key_len < 0)
1898 		return -EINVAL;
1899 
1900 	idx = encoding->flags & IW_ENCODE_INDEX;
1901 	if (idx) {
1902 		if (idx < 1 || idx > 4)
1903 			return -EINVAL;
1904 		idx--;
1905 	} else
1906 		idx = priv->default_key;
1907 
1908 	encoding->flags = idx + 1;
1909 	memset(ext, 0, sizeof(*ext));
1910 
1911 	if (!priv->wep_is_on) {
1912 		ext->alg = IW_ENCODE_ALG_NONE;
1913 		ext->key_len = 0;
1914 		encoding->flags |= IW_ENCODE_DISABLED;
1915 	} else {
1916 		if (priv->encryption_level > 0)
1917 			ext->alg = IW_ENCODE_ALG_WEP;
1918 		else
1919 			return -EINVAL;
1920 
1921 		ext->key_len = priv->wep_key_len[idx];
1922 		memcpy(ext->key, priv->wep_keys[idx], ext->key_len);
1923 		encoding->flags |= IW_ENCODE_ENABLED;
1924 	}
1925 
1926 	return 0;
1927 }
1928 
1929 static int atmel_set_auth(struct net_device *dev,
1930 			       struct iw_request_info *info,
1931 			       union iwreq_data *wrqu, char *extra)
1932 {
1933 	struct atmel_private *priv = netdev_priv(dev);
1934 	struct iw_param *param = &wrqu->param;
1935 
1936 	switch (param->flags & IW_AUTH_INDEX) {
1937 	case IW_AUTH_WPA_VERSION:
1938 	case IW_AUTH_CIPHER_PAIRWISE:
1939 	case IW_AUTH_CIPHER_GROUP:
1940 	case IW_AUTH_KEY_MGMT:
1941 	case IW_AUTH_RX_UNENCRYPTED_EAPOL:
1942 	case IW_AUTH_PRIVACY_INVOKED:
1943 		/*
1944 		 * atmel does not use these parameters
1945 		 */
1946 		break;
1947 
1948 	case IW_AUTH_DROP_UNENCRYPTED:
1949 		priv->exclude_unencrypted = param->value ? 1 : 0;
1950 		break;
1951 
1952 	case IW_AUTH_80211_AUTH_ALG: {
1953 			if (param->value & IW_AUTH_ALG_SHARED_KEY) {
1954 				priv->exclude_unencrypted = 1;
1955 			} else if (param->value & IW_AUTH_ALG_OPEN_SYSTEM) {
1956 				priv->exclude_unencrypted = 0;
1957 			} else
1958 				return -EINVAL;
1959 			break;
1960 		}
1961 
1962 	case IW_AUTH_WPA_ENABLED:
1963 		/* Silently accept disable of WPA */
1964 		if (param->value > 0)
1965 			return -EOPNOTSUPP;
1966 		break;
1967 
1968 	default:
1969 		return -EOPNOTSUPP;
1970 	}
1971 	return -EINPROGRESS;
1972 }
1973 
1974 static int atmel_get_auth(struct net_device *dev,
1975 			       struct iw_request_info *info,
1976 			       union iwreq_data *wrqu, char *extra)
1977 {
1978 	struct atmel_private *priv = netdev_priv(dev);
1979 	struct iw_param *param = &wrqu->param;
1980 
1981 	switch (param->flags & IW_AUTH_INDEX) {
1982 	case IW_AUTH_DROP_UNENCRYPTED:
1983 		param->value = priv->exclude_unencrypted;
1984 		break;
1985 
1986 	case IW_AUTH_80211_AUTH_ALG:
1987 		if (priv->exclude_unencrypted == 1)
1988 			param->value = IW_AUTH_ALG_SHARED_KEY;
1989 		else
1990 			param->value = IW_AUTH_ALG_OPEN_SYSTEM;
1991 		break;
1992 
1993 	case IW_AUTH_WPA_ENABLED:
1994 		param->value = 0;
1995 		break;
1996 
1997 	default:
1998 		return -EOPNOTSUPP;
1999 	}
2000 	return 0;
2001 }
2002 
2003 
2004 static int atmel_get_name(struct net_device *dev,
2005 			  struct iw_request_info *info,
2006 			  char *cwrq,
2007 			  char *extra)
2008 {
2009 	strcpy(cwrq, "IEEE 802.11-DS");
2010 	return 0;
2011 }
2012 
2013 static int atmel_set_rate(struct net_device *dev,
2014 			  struct iw_request_info *info,
2015 			  struct iw_param *vwrq,
2016 			  char *extra)
2017 {
2018 	struct atmel_private *priv = netdev_priv(dev);
2019 
2020 	if (vwrq->fixed == 0) {
2021 		priv->tx_rate = 3;
2022 		priv->auto_tx_rate = 1;
2023 	} else {
2024 		priv->auto_tx_rate = 0;
2025 
2026 		/* Which type of value ? */
2027 		if ((vwrq->value < 4) && (vwrq->value >= 0)) {
2028 			/* Setting by rate index */
2029 			priv->tx_rate = vwrq->value;
2030 		} else {
2031 		/* Setting by frequency value */
2032 			switch (vwrq->value) {
2033 			case  1000000:
2034 				priv->tx_rate = 0;
2035 				break;
2036 			case  2000000:
2037 				priv->tx_rate = 1;
2038 				break;
2039 			case  5500000:
2040 				priv->tx_rate = 2;
2041 				break;
2042 			case 11000000:
2043 				priv->tx_rate = 3;
2044 				break;
2045 			default:
2046 				return -EINVAL;
2047 			}
2048 		}
2049 	}
2050 
2051 	return -EINPROGRESS;
2052 }
2053 
2054 static int atmel_set_mode(struct net_device *dev,
2055 			  struct iw_request_info *info,
2056 			  __u32 *uwrq,
2057 			  char *extra)
2058 {
2059 	struct atmel_private *priv = netdev_priv(dev);
2060 
2061 	if (*uwrq != IW_MODE_ADHOC && *uwrq != IW_MODE_INFRA)
2062 		return -EINVAL;
2063 
2064 	priv->operating_mode = *uwrq;
2065 	return -EINPROGRESS;
2066 }
2067 
2068 static int atmel_get_mode(struct net_device *dev,
2069 			  struct iw_request_info *info,
2070 			  __u32 *uwrq,
2071 			  char *extra)
2072 {
2073 	struct atmel_private *priv = netdev_priv(dev);
2074 
2075 	*uwrq = priv->operating_mode;
2076 	return 0;
2077 }
2078 
2079 static int atmel_get_rate(struct net_device *dev,
2080 			 struct iw_request_info *info,
2081 			 struct iw_param *vwrq,
2082 			 char *extra)
2083 {
2084 	struct atmel_private *priv = netdev_priv(dev);
2085 
2086 	if (priv->auto_tx_rate) {
2087 		vwrq->fixed = 0;
2088 		vwrq->value = 11000000;
2089 	} else {
2090 		vwrq->fixed = 1;
2091 		switch (priv->tx_rate) {
2092 		case 0:
2093 			vwrq->value =  1000000;
2094 			break;
2095 		case 1:
2096 			vwrq->value =  2000000;
2097 			break;
2098 		case 2:
2099 			vwrq->value =  5500000;
2100 			break;
2101 		case 3:
2102 			vwrq->value = 11000000;
2103 			break;
2104 		}
2105 	}
2106 	return 0;
2107 }
2108 
2109 static int atmel_set_power(struct net_device *dev,
2110 			   struct iw_request_info *info,
2111 			   struct iw_param *vwrq,
2112 			   char *extra)
2113 {
2114 	struct atmel_private *priv = netdev_priv(dev);
2115 	priv->power_mode = vwrq->disabled ? 0 : 1;
2116 	return -EINPROGRESS;
2117 }
2118 
2119 static int atmel_get_power(struct net_device *dev,
2120 			   struct iw_request_info *info,
2121 			   struct iw_param *vwrq,
2122 			   char *extra)
2123 {
2124 	struct atmel_private *priv = netdev_priv(dev);
2125 	vwrq->disabled = priv->power_mode ? 0 : 1;
2126 	vwrq->flags = IW_POWER_ON;
2127 	return 0;
2128 }
2129 
2130 static int atmel_set_retry(struct net_device *dev,
2131 			   struct iw_request_info *info,
2132 			   struct iw_param *vwrq,
2133 			   char *extra)
2134 {
2135 	struct atmel_private *priv = netdev_priv(dev);
2136 
2137 	if (!vwrq->disabled && (vwrq->flags & IW_RETRY_LIMIT)) {
2138 		if (vwrq->flags & IW_RETRY_LONG)
2139 			priv->long_retry = vwrq->value;
2140 		else if (vwrq->flags & IW_RETRY_SHORT)
2141 			priv->short_retry = vwrq->value;
2142 		else {
2143 			/* No modifier : set both */
2144 			priv->long_retry = vwrq->value;
2145 			priv->short_retry = vwrq->value;
2146 		}
2147 		return -EINPROGRESS;
2148 	}
2149 
2150 	return -EINVAL;
2151 }
2152 
2153 static int atmel_get_retry(struct net_device *dev,
2154 			   struct iw_request_info *info,
2155 			   struct iw_param *vwrq,
2156 			   char *extra)
2157 {
2158 	struct atmel_private *priv = netdev_priv(dev);
2159 
2160 	vwrq->disabled = 0;      /* Can't be disabled */
2161 
2162 	/* Note : by default, display the short retry number */
2163 	if (vwrq->flags & IW_RETRY_LONG) {
2164 		vwrq->flags = IW_RETRY_LIMIT | IW_RETRY_LONG;
2165 		vwrq->value = priv->long_retry;
2166 	} else {
2167 		vwrq->flags = IW_RETRY_LIMIT;
2168 		vwrq->value = priv->short_retry;
2169 		if (priv->long_retry != priv->short_retry)
2170 			vwrq->flags |= IW_RETRY_SHORT;
2171 	}
2172 
2173 	return 0;
2174 }
2175 
2176 static int atmel_set_rts(struct net_device *dev,
2177 			 struct iw_request_info *info,
2178 			 struct iw_param *vwrq,
2179 			 char *extra)
2180 {
2181 	struct atmel_private *priv = netdev_priv(dev);
2182 	int rthr = vwrq->value;
2183 
2184 	if (vwrq->disabled)
2185 		rthr = 2347;
2186 	if ((rthr < 0) || (rthr > 2347)) {
2187 		return -EINVAL;
2188 	}
2189 	priv->rts_threshold = rthr;
2190 
2191 	return -EINPROGRESS;		/* Call commit handler */
2192 }
2193 
2194 static int atmel_get_rts(struct net_device *dev,
2195 			 struct iw_request_info *info,
2196 			 struct iw_param *vwrq,
2197 			 char *extra)
2198 {
2199 	struct atmel_private *priv = netdev_priv(dev);
2200 
2201 	vwrq->value = priv->rts_threshold;
2202 	vwrq->disabled = (vwrq->value >= 2347);
2203 	vwrq->fixed = 1;
2204 
2205 	return 0;
2206 }
2207 
2208 static int atmel_set_frag(struct net_device *dev,
2209 			  struct iw_request_info *info,
2210 			  struct iw_param *vwrq,
2211 			  char *extra)
2212 {
2213 	struct atmel_private *priv = netdev_priv(dev);
2214 	int fthr = vwrq->value;
2215 
2216 	if (vwrq->disabled)
2217 		fthr = 2346;
2218 	if ((fthr < 256) || (fthr > 2346)) {
2219 		return -EINVAL;
2220 	}
2221 	fthr &= ~0x1;	/* Get an even value - is it really needed ??? */
2222 	priv->frag_threshold = fthr;
2223 
2224 	return -EINPROGRESS;		/* Call commit handler */
2225 }
2226 
2227 static int atmel_get_frag(struct net_device *dev,
2228 			  struct iw_request_info *info,
2229 			  struct iw_param *vwrq,
2230 			  char *extra)
2231 {
2232 	struct atmel_private *priv = netdev_priv(dev);
2233 
2234 	vwrq->value = priv->frag_threshold;
2235 	vwrq->disabled = (vwrq->value >= 2346);
2236 	vwrq->fixed = 1;
2237 
2238 	return 0;
2239 }
2240 
2241 static int atmel_set_freq(struct net_device *dev,
2242 			  struct iw_request_info *info,
2243 			  struct iw_freq *fwrq,
2244 			  char *extra)
2245 {
2246 	struct atmel_private *priv = netdev_priv(dev);
2247 	int rc = -EINPROGRESS;		/* Call commit handler */
2248 
2249 	/* If setting by frequency, convert to a channel */
2250 	if (fwrq->e == 1) {
2251 		int f = fwrq->m / 100000;
2252 
2253 		/* Hack to fall through... */
2254 		fwrq->e = 0;
2255 		fwrq->m = ieee80211_frequency_to_channel(f);
2256 	}
2257 	/* Setting by channel number */
2258 	if (fwrq->m < 0 || fwrq->m > 1000 || fwrq->e > 0)
2259 		rc = -EOPNOTSUPP;
2260 	else {
2261 		int channel = fwrq->m;
2262 		if (atmel_validate_channel(priv, channel) == 0) {
2263 			priv->channel = channel;
2264 		} else {
2265 			rc = -EINVAL;
2266 		}
2267 	}
2268 	return rc;
2269 }
2270 
2271 static int atmel_get_freq(struct net_device *dev,
2272 			  struct iw_request_info *info,
2273 			  struct iw_freq *fwrq,
2274 			  char *extra)
2275 {
2276 	struct atmel_private *priv = netdev_priv(dev);
2277 
2278 	fwrq->m = priv->channel;
2279 	fwrq->e = 0;
2280 	return 0;
2281 }
2282 
2283 static int atmel_set_scan(struct net_device *dev,
2284 			  struct iw_request_info *info,
2285 			  struct iw_point *dwrq,
2286 			  char *extra)
2287 {
2288 	struct atmel_private *priv = netdev_priv(dev);
2289 	unsigned long flags;
2290 
2291 	/* Note : you may have realised that, as this is a SET operation,
2292 	 * this is privileged and therefore a normal user can't
2293 	 * perform scanning.
2294 	 * This is not an error, while the device perform scanning,
2295 	 * traffic doesn't flow, so it's a perfect DoS...
2296 	 * Jean II */
2297 
2298 	if (priv->station_state == STATION_STATE_DOWN)
2299 		return -EAGAIN;
2300 
2301 	/* Timeout old surveys. */
2302 	if (time_after(jiffies, priv->last_survey + 20 * HZ))
2303 		priv->site_survey_state = SITE_SURVEY_IDLE;
2304 	priv->last_survey = jiffies;
2305 
2306 	/* Initiate a scan command */
2307 	if (priv->site_survey_state == SITE_SURVEY_IN_PROGRESS)
2308 		return -EBUSY;
2309 
2310 	del_timer_sync(&priv->management_timer);
2311 	spin_lock_irqsave(&priv->irqlock, flags);
2312 
2313 	priv->site_survey_state = SITE_SURVEY_IN_PROGRESS;
2314 	priv->fast_scan = 0;
2315 	atmel_scan(priv, 0);
2316 	spin_unlock_irqrestore(&priv->irqlock, flags);
2317 
2318 	return 0;
2319 }
2320 
2321 static int atmel_get_scan(struct net_device *dev,
2322 			  struct iw_request_info *info,
2323 			  struct iw_point *dwrq,
2324 			  char *extra)
2325 {
2326 	struct atmel_private *priv = netdev_priv(dev);
2327 	int i;
2328 	char *current_ev = extra;
2329 	struct iw_event	iwe;
2330 
2331 	if (priv->site_survey_state != SITE_SURVEY_COMPLETED)
2332 		return -EAGAIN;
2333 
2334 	for (i = 0; i < priv->BSS_list_entries; i++) {
2335 		iwe.cmd = SIOCGIWAP;
2336 		iwe.u.ap_addr.sa_family = ARPHRD_ETHER;
2337 		memcpy(iwe.u.ap_addr.sa_data, priv->BSSinfo[i].BSSID, ETH_ALEN);
2338 		current_ev = iwe_stream_add_event(info, current_ev,
2339 						  extra + IW_SCAN_MAX_DATA,
2340 						  &iwe, IW_EV_ADDR_LEN);
2341 
2342 		iwe.u.data.length =  priv->BSSinfo[i].SSIDsize;
2343 		if (iwe.u.data.length > 32)
2344 			iwe.u.data.length = 32;
2345 		iwe.cmd = SIOCGIWESSID;
2346 		iwe.u.data.flags = 1;
2347 		current_ev = iwe_stream_add_point(info, current_ev,
2348 						  extra + IW_SCAN_MAX_DATA,
2349 						  &iwe, priv->BSSinfo[i].SSID);
2350 
2351 		iwe.cmd = SIOCGIWMODE;
2352 		iwe.u.mode = priv->BSSinfo[i].BSStype;
2353 		current_ev = iwe_stream_add_event(info, current_ev,
2354 						  extra + IW_SCAN_MAX_DATA,
2355 						  &iwe, IW_EV_UINT_LEN);
2356 
2357 		iwe.cmd = SIOCGIWFREQ;
2358 		iwe.u.freq.m = priv->BSSinfo[i].channel;
2359 		iwe.u.freq.e = 0;
2360 		current_ev = iwe_stream_add_event(info, current_ev,
2361 						  extra + IW_SCAN_MAX_DATA,
2362 						  &iwe, IW_EV_FREQ_LEN);
2363 
2364 		/* Add quality statistics */
2365 		iwe.cmd = IWEVQUAL;
2366 		iwe.u.qual.level = priv->BSSinfo[i].RSSI;
2367 		iwe.u.qual.qual  = iwe.u.qual.level;
2368 		/* iwe.u.qual.noise  = SOMETHING */
2369 		current_ev = iwe_stream_add_event(info, current_ev,
2370 						  extra + IW_SCAN_MAX_DATA,
2371 						  &iwe, IW_EV_QUAL_LEN);
2372 
2373 
2374 		iwe.cmd = SIOCGIWENCODE;
2375 		if (priv->BSSinfo[i].UsingWEP)
2376 			iwe.u.data.flags = IW_ENCODE_ENABLED | IW_ENCODE_NOKEY;
2377 		else
2378 			iwe.u.data.flags = IW_ENCODE_DISABLED;
2379 		iwe.u.data.length = 0;
2380 		current_ev = iwe_stream_add_point(info, current_ev,
2381 						  extra + IW_SCAN_MAX_DATA,
2382 						  &iwe, NULL);
2383 	}
2384 
2385 	/* Length of data */
2386 	dwrq->length = (current_ev - extra);
2387 	dwrq->flags = 0;
2388 
2389 	return 0;
2390 }
2391 
2392 static int atmel_get_range(struct net_device *dev,
2393 			   struct iw_request_info *info,
2394 			   struct iw_point *dwrq,
2395 			   char *extra)
2396 {
2397 	struct atmel_private *priv = netdev_priv(dev);
2398 	struct iw_range *range = (struct iw_range *) extra;
2399 	int k, i, j;
2400 
2401 	dwrq->length = sizeof(struct iw_range);
2402 	memset(range, 0, sizeof(struct iw_range));
2403 	range->min_nwid = 0x0000;
2404 	range->max_nwid = 0x0000;
2405 	range->num_channels = 0;
2406 	for (j = 0; j < ARRAY_SIZE(channel_table); j++)
2407 		if (priv->reg_domain == channel_table[j].reg_domain) {
2408 			range->num_channels = channel_table[j].max - channel_table[j].min + 1;
2409 			break;
2410 		}
2411 	if (range->num_channels != 0) {
2412 		for (k = 0, i = channel_table[j].min; i <= channel_table[j].max; i++) {
2413 			range->freq[k].i = i; /* List index */
2414 
2415 			/* Values in MHz -> * 10^5 * 10 */
2416 			range->freq[k].m = 100000 *
2417 			 ieee80211_channel_to_frequency(i, NL80211_BAND_2GHZ);
2418 			range->freq[k++].e = 1;
2419 		}
2420 		range->num_frequency = k;
2421 	}
2422 
2423 	range->max_qual.qual = 100;
2424 	range->max_qual.level = 100;
2425 	range->max_qual.noise = 0;
2426 	range->max_qual.updated = IW_QUAL_NOISE_INVALID;
2427 
2428 	range->avg_qual.qual = 50;
2429 	range->avg_qual.level = 50;
2430 	range->avg_qual.noise = 0;
2431 	range->avg_qual.updated = IW_QUAL_NOISE_INVALID;
2432 
2433 	range->sensitivity = 0;
2434 
2435 	range->bitrate[0] =  1000000;
2436 	range->bitrate[1] =  2000000;
2437 	range->bitrate[2] =  5500000;
2438 	range->bitrate[3] = 11000000;
2439 	range->num_bitrates = 4;
2440 
2441 	range->min_rts = 0;
2442 	range->max_rts = 2347;
2443 	range->min_frag = 256;
2444 	range->max_frag = 2346;
2445 
2446 	range->encoding_size[0] = 5;
2447 	range->encoding_size[1] = 13;
2448 	range->num_encoding_sizes = 2;
2449 	range->max_encoding_tokens = 4;
2450 
2451 	range->pmp_flags = IW_POWER_ON;
2452 	range->pmt_flags = IW_POWER_ON;
2453 	range->pm_capa = 0;
2454 
2455 	range->we_version_source = WIRELESS_EXT;
2456 	range->we_version_compiled = WIRELESS_EXT;
2457 	range->retry_capa = IW_RETRY_LIMIT ;
2458 	range->retry_flags = IW_RETRY_LIMIT;
2459 	range->r_time_flags = 0;
2460 	range->min_retry = 1;
2461 	range->max_retry = 65535;
2462 
2463 	return 0;
2464 }
2465 
2466 static int atmel_set_wap(struct net_device *dev,
2467 			 struct iw_request_info *info,
2468 			 struct sockaddr *awrq,
2469 			 char *extra)
2470 {
2471 	struct atmel_private *priv = netdev_priv(dev);
2472 	int i;
2473 	static const u8 any[] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF };
2474 	static const u8 off[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
2475 	unsigned long flags;
2476 
2477 	if (awrq->sa_family != ARPHRD_ETHER)
2478 		return -EINVAL;
2479 
2480 	if (!memcmp(any, awrq->sa_data, 6) ||
2481 	    !memcmp(off, awrq->sa_data, 6)) {
2482 		del_timer_sync(&priv->management_timer);
2483 		spin_lock_irqsave(&priv->irqlock, flags);
2484 		atmel_scan(priv, 1);
2485 		spin_unlock_irqrestore(&priv->irqlock, flags);
2486 		return 0;
2487 	}
2488 
2489 	for (i = 0; i < priv->BSS_list_entries; i++) {
2490 		if (memcmp(priv->BSSinfo[i].BSSID, awrq->sa_data, 6) == 0) {
2491 			if (!priv->wep_is_on && priv->BSSinfo[i].UsingWEP) {
2492 				return -EINVAL;
2493 			} else if  (priv->wep_is_on && !priv->BSSinfo[i].UsingWEP) {
2494 				return -EINVAL;
2495 			} else {
2496 				del_timer_sync(&priv->management_timer);
2497 				spin_lock_irqsave(&priv->irqlock, flags);
2498 				atmel_join_bss(priv, i);
2499 				spin_unlock_irqrestore(&priv->irqlock, flags);
2500 				return 0;
2501 			}
2502 		}
2503 	}
2504 
2505 	return -EINVAL;
2506 }
2507 
2508 static int atmel_config_commit(struct net_device *dev,
2509 			       struct iw_request_info *info,	/* NULL */
2510 			       void *zwrq,			/* NULL */
2511 			       char *extra)			/* NULL */
2512 {
2513 	return atmel_open(dev);
2514 }
2515 
2516 static const iw_handler atmel_handler[] =
2517 {
2518 	(iw_handler) atmel_config_commit,	/* SIOCSIWCOMMIT */
2519 	(iw_handler) atmel_get_name,		/* SIOCGIWNAME */
2520 	(iw_handler) NULL,			/* SIOCSIWNWID */
2521 	(iw_handler) NULL,			/* SIOCGIWNWID */
2522 	(iw_handler) atmel_set_freq,		/* SIOCSIWFREQ */
2523 	(iw_handler) atmel_get_freq,		/* SIOCGIWFREQ */
2524 	(iw_handler) atmel_set_mode,		/* SIOCSIWMODE */
2525 	(iw_handler) atmel_get_mode,		/* SIOCGIWMODE */
2526 	(iw_handler) NULL,			/* SIOCSIWSENS */
2527 	(iw_handler) NULL,			/* SIOCGIWSENS */
2528 	(iw_handler) NULL,			/* SIOCSIWRANGE */
2529 	(iw_handler) atmel_get_range,           /* SIOCGIWRANGE */
2530 	(iw_handler) NULL,			/* SIOCSIWPRIV */
2531 	(iw_handler) NULL,			/* SIOCGIWPRIV */
2532 	(iw_handler) NULL,			/* SIOCSIWSTATS */
2533 	(iw_handler) NULL,			/* SIOCGIWSTATS */
2534 	(iw_handler) NULL,			/* SIOCSIWSPY */
2535 	(iw_handler) NULL,			/* SIOCGIWSPY */
2536 	(iw_handler) NULL,			/* -- hole -- */
2537 	(iw_handler) NULL,			/* -- hole -- */
2538 	(iw_handler) atmel_set_wap,		/* SIOCSIWAP */
2539 	(iw_handler) atmel_get_wap,		/* SIOCGIWAP */
2540 	(iw_handler) NULL,			/* -- hole -- */
2541 	(iw_handler) NULL,			/* SIOCGIWAPLIST */
2542 	(iw_handler) atmel_set_scan,		/* SIOCSIWSCAN */
2543 	(iw_handler) atmel_get_scan,		/* SIOCGIWSCAN */
2544 	(iw_handler) atmel_set_essid,		/* SIOCSIWESSID */
2545 	(iw_handler) atmel_get_essid,		/* SIOCGIWESSID */
2546 	(iw_handler) NULL,			/* SIOCSIWNICKN */
2547 	(iw_handler) NULL,			/* SIOCGIWNICKN */
2548 	(iw_handler) NULL,			/* -- hole -- */
2549 	(iw_handler) NULL,			/* -- hole -- */
2550 	(iw_handler) atmel_set_rate,		/* SIOCSIWRATE */
2551 	(iw_handler) atmel_get_rate,		/* SIOCGIWRATE */
2552 	(iw_handler) atmel_set_rts,		/* SIOCSIWRTS */
2553 	(iw_handler) atmel_get_rts,		/* SIOCGIWRTS */
2554 	(iw_handler) atmel_set_frag,		/* SIOCSIWFRAG */
2555 	(iw_handler) atmel_get_frag,		/* SIOCGIWFRAG */
2556 	(iw_handler) NULL,			/* SIOCSIWTXPOW */
2557 	(iw_handler) NULL,			/* SIOCGIWTXPOW */
2558 	(iw_handler) atmel_set_retry,		/* SIOCSIWRETRY */
2559 	(iw_handler) atmel_get_retry,		/* SIOCGIWRETRY */
2560 	(iw_handler) atmel_set_encode,		/* SIOCSIWENCODE */
2561 	(iw_handler) atmel_get_encode,		/* SIOCGIWENCODE */
2562 	(iw_handler) atmel_set_power,		/* SIOCSIWPOWER */
2563 	(iw_handler) atmel_get_power,		/* SIOCGIWPOWER */
2564 	(iw_handler) NULL,			/* -- hole -- */
2565 	(iw_handler) NULL,			/* -- hole -- */
2566 	(iw_handler) NULL,			/* SIOCSIWGENIE */
2567 	(iw_handler) NULL,			/* SIOCGIWGENIE */
2568 	(iw_handler) atmel_set_auth,		/* SIOCSIWAUTH */
2569 	(iw_handler) atmel_get_auth,		/* SIOCGIWAUTH */
2570 	(iw_handler) atmel_set_encodeext,	/* SIOCSIWENCODEEXT */
2571 	(iw_handler) atmel_get_encodeext,	/* SIOCGIWENCODEEXT */
2572 	(iw_handler) NULL,			/* SIOCSIWPMKSA */
2573 };
2574 
2575 static const iw_handler atmel_private_handler[] =
2576 {
2577 	NULL,				/* SIOCIWFIRSTPRIV */
2578 };
2579 
2580 struct atmel_priv_ioctl {
2581 	char id[32];
2582 	unsigned char __user *data;
2583 	unsigned short len;
2584 };
2585 
2586 #define ATMELFWL	SIOCIWFIRSTPRIV
2587 #define ATMELIDIFC	ATMELFWL + 1
2588 #define ATMELRD		ATMELFWL + 2
2589 #define ATMELMAGIC 0x51807
2590 #define REGDOMAINSZ 20
2591 
2592 static const struct iw_priv_args atmel_private_args[] = {
2593 	{
2594 		.cmd = ATMELFWL,
2595 		.set_args = IW_PRIV_TYPE_BYTE
2596 				| IW_PRIV_SIZE_FIXED
2597 				| sizeof(struct atmel_priv_ioctl),
2598 		.get_args = IW_PRIV_TYPE_NONE,
2599 		.name = "atmelfwl"
2600 	}, {
2601 		.cmd = ATMELIDIFC,
2602 		.set_args = IW_PRIV_TYPE_NONE,
2603 		.get_args = IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1,
2604 		.name = "atmelidifc"
2605 	}, {
2606 		.cmd = ATMELRD,
2607 		.set_args = IW_PRIV_TYPE_CHAR | REGDOMAINSZ,
2608 		.get_args = IW_PRIV_TYPE_NONE,
2609 		.name = "regdomain"
2610 	},
2611 };
2612 
2613 static const struct iw_handler_def atmel_handler_def = {
2614 	.num_standard	= ARRAY_SIZE(atmel_handler),
2615 	.num_private	= ARRAY_SIZE(atmel_private_handler),
2616 	.num_private_args = ARRAY_SIZE(atmel_private_args),
2617 	.standard	= (iw_handler *) atmel_handler,
2618 	.private	= (iw_handler *) atmel_private_handler,
2619 	.private_args	= (struct iw_priv_args *) atmel_private_args,
2620 	.get_wireless_stats = atmel_get_wireless_stats
2621 };
2622 
2623 static int atmel_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
2624 {
2625 	int i, rc = 0;
2626 	struct atmel_private *priv = netdev_priv(dev);
2627 	struct atmel_priv_ioctl com;
2628 	struct iwreq *wrq = (struct iwreq *) rq;
2629 	unsigned char *new_firmware;
2630 	char domain[REGDOMAINSZ + 1];
2631 
2632 	switch (cmd) {
2633 	case ATMELIDIFC:
2634 		wrq->u.param.value = ATMELMAGIC;
2635 		break;
2636 
2637 	case ATMELFWL:
2638 		if (copy_from_user(&com, rq->ifr_data, sizeof(com))) {
2639 			rc = -EFAULT;
2640 			break;
2641 		}
2642 
2643 		if (!capable(CAP_NET_ADMIN)) {
2644 			rc = -EPERM;
2645 			break;
2646 		}
2647 
2648 		new_firmware = memdup_user(com.data, com.len);
2649 		if (IS_ERR(new_firmware)) {
2650 			rc = PTR_ERR(new_firmware);
2651 			break;
2652 		}
2653 
2654 		kfree(priv->firmware);
2655 
2656 		priv->firmware = new_firmware;
2657 		priv->firmware_length = com.len;
2658 		strncpy(priv->firmware_id, com.id, 31);
2659 		priv->firmware_id[31] = '\0';
2660 		break;
2661 
2662 	case ATMELRD:
2663 		if (copy_from_user(domain, rq->ifr_data, REGDOMAINSZ)) {
2664 			rc = -EFAULT;
2665 			break;
2666 		}
2667 
2668 		if (!capable(CAP_NET_ADMIN)) {
2669 			rc = -EPERM;
2670 			break;
2671 		}
2672 
2673 		domain[REGDOMAINSZ] = 0;
2674 		rc = -EINVAL;
2675 		for (i = 0; i < ARRAY_SIZE(channel_table); i++) {
2676 			if (!strcasecmp(channel_table[i].name, domain)) {
2677 				priv->config_reg_domain = channel_table[i].reg_domain;
2678 				rc = 0;
2679 			}
2680 		}
2681 
2682 		if (rc == 0 &&  priv->station_state != STATION_STATE_DOWN)
2683 			rc = atmel_open(dev);
2684 		break;
2685 
2686 	default:
2687 		rc = -EOPNOTSUPP;
2688 	}
2689 
2690 	return rc;
2691 }
2692 
2693 struct auth_body {
2694 	__le16 alg;
2695 	__le16 trans_seq;
2696 	__le16 status;
2697 	u8 el_id;
2698 	u8 chall_text_len;
2699 	u8 chall_text[253];
2700 };
2701 
2702 static void atmel_enter_state(struct atmel_private *priv, int new_state)
2703 {
2704 	int old_state = priv->station_state;
2705 
2706 	if (new_state == old_state)
2707 		return;
2708 
2709 	priv->station_state = new_state;
2710 
2711 	if (new_state == STATION_STATE_READY) {
2712 		netif_start_queue(priv->dev);
2713 		netif_carrier_on(priv->dev);
2714 	}
2715 
2716 	if (old_state == STATION_STATE_READY) {
2717 		netif_carrier_off(priv->dev);
2718 		if (netif_running(priv->dev))
2719 			netif_stop_queue(priv->dev);
2720 		priv->last_beacon_timestamp = 0;
2721 	}
2722 }
2723 
2724 static void atmel_scan(struct atmel_private *priv, int specific_ssid)
2725 {
2726 	struct {
2727 		u8 BSSID[ETH_ALEN];
2728 		u8 SSID[MAX_SSID_LENGTH];
2729 		u8 scan_type;
2730 		u8 channel;
2731 		__le16 BSS_type;
2732 		__le16 min_channel_time;
2733 		__le16 max_channel_time;
2734 		u8 options;
2735 		u8 SSID_size;
2736 	} cmd;
2737 
2738 	eth_broadcast_addr(cmd.BSSID);
2739 
2740 	if (priv->fast_scan) {
2741 		cmd.SSID_size = priv->SSID_size;
2742 		memcpy(cmd.SSID, priv->SSID, priv->SSID_size);
2743 		cmd.min_channel_time = cpu_to_le16(10);
2744 		cmd.max_channel_time = cpu_to_le16(50);
2745 	} else {
2746 		priv->BSS_list_entries = 0;
2747 		cmd.SSID_size = 0;
2748 		cmd.min_channel_time = cpu_to_le16(10);
2749 		cmd.max_channel_time = cpu_to_le16(120);
2750 	}
2751 
2752 	cmd.options = 0;
2753 
2754 	if (!specific_ssid)
2755 		cmd.options |= SCAN_OPTIONS_SITE_SURVEY;
2756 
2757 	cmd.channel = (priv->channel & 0x7f);
2758 	cmd.scan_type = SCAN_TYPE_ACTIVE;
2759 	cmd.BSS_type = cpu_to_le16(priv->operating_mode == IW_MODE_ADHOC ?
2760 		BSS_TYPE_AD_HOC : BSS_TYPE_INFRASTRUCTURE);
2761 
2762 	atmel_send_command(priv, CMD_Scan, &cmd, sizeof(cmd));
2763 
2764 	/* This must come after all hardware access to avoid being messed up
2765 	   by stuff happening in interrupt context after we leave STATE_DOWN */
2766 	atmel_enter_state(priv, STATION_STATE_SCANNING);
2767 }
2768 
2769 static void join(struct atmel_private *priv, int type)
2770 {
2771 	struct {
2772 		u8 BSSID[6];
2773 		u8 SSID[MAX_SSID_LENGTH];
2774 		u8 BSS_type; /* this is a short in a scan command - weird */
2775 		u8 channel;
2776 		__le16 timeout;
2777 		u8 SSID_size;
2778 		u8 reserved;
2779 	} cmd;
2780 
2781 	cmd.SSID_size = priv->SSID_size;
2782 	memcpy(cmd.SSID, priv->SSID, priv->SSID_size);
2783 	memcpy(cmd.BSSID, priv->CurrentBSSID, ETH_ALEN);
2784 	cmd.channel = (priv->channel & 0x7f);
2785 	cmd.BSS_type = type;
2786 	cmd.timeout = cpu_to_le16(2000);
2787 
2788 	atmel_send_command(priv, CMD_Join, &cmd, sizeof(cmd));
2789 }
2790 
2791 static void start(struct atmel_private *priv, int type)
2792 {
2793 	struct {
2794 		u8 BSSID[6];
2795 		u8 SSID[MAX_SSID_LENGTH];
2796 		u8 BSS_type;
2797 		u8 channel;
2798 		u8 SSID_size;
2799 		u8 reserved[3];
2800 	} cmd;
2801 
2802 	cmd.SSID_size = priv->SSID_size;
2803 	memcpy(cmd.SSID, priv->SSID, priv->SSID_size);
2804 	memcpy(cmd.BSSID, priv->BSSID, ETH_ALEN);
2805 	cmd.BSS_type = type;
2806 	cmd.channel = (priv->channel & 0x7f);
2807 
2808 	atmel_send_command(priv, CMD_Start, &cmd, sizeof(cmd));
2809 }
2810 
2811 static void handle_beacon_probe(struct atmel_private *priv, u16 capability,
2812 				u8 channel)
2813 {
2814 	int rejoin = 0;
2815 	int new = capability & WLAN_CAPABILITY_SHORT_PREAMBLE ?
2816 		SHORT_PREAMBLE : LONG_PREAMBLE;
2817 
2818 	if (priv->preamble != new) {
2819 		priv->preamble = new;
2820 		rejoin = 1;
2821 		atmel_set_mib8(priv, Local_Mib_Type, LOCAL_MIB_PREAMBLE_TYPE, new);
2822 	}
2823 
2824 	if (priv->channel != channel) {
2825 		priv->channel = channel;
2826 		rejoin = 1;
2827 		atmel_set_mib8(priv, Phy_Mib_Type, PHY_MIB_CHANNEL_POS, channel);
2828 	}
2829 
2830 	if (rejoin) {
2831 		priv->station_is_associated = 0;
2832 		atmel_enter_state(priv, STATION_STATE_JOINNING);
2833 
2834 		if (priv->operating_mode == IW_MODE_INFRA)
2835 			join(priv, BSS_TYPE_INFRASTRUCTURE);
2836 		else
2837 			join(priv, BSS_TYPE_AD_HOC);
2838 	}
2839 }
2840 
2841 static void send_authentication_request(struct atmel_private *priv, u16 system,
2842 					u8 *challenge, int challenge_len)
2843 {
2844 	struct ieee80211_hdr header;
2845 	struct auth_body auth;
2846 
2847 	header.frame_control = cpu_to_le16(IEEE80211_FTYPE_MGMT | IEEE80211_STYPE_AUTH);
2848 	header.duration_id = cpu_to_le16(0x8000);
2849 	header.seq_ctrl = 0;
2850 	memcpy(header.addr1, priv->CurrentBSSID, ETH_ALEN);
2851 	memcpy(header.addr2, priv->dev->dev_addr, ETH_ALEN);
2852 	memcpy(header.addr3, priv->CurrentBSSID, ETH_ALEN);
2853 
2854 	if (priv->wep_is_on && priv->CurrentAuthentTransactionSeqNum != 1)
2855 		/* no WEP for authentication frames with TrSeqNo 1 */
2856 		header.frame_control |=  cpu_to_le16(IEEE80211_FCTL_PROTECTED);
2857 
2858 	auth.alg = cpu_to_le16(system);
2859 
2860 	auth.status = 0;
2861 	auth.trans_seq = cpu_to_le16(priv->CurrentAuthentTransactionSeqNum);
2862 	priv->ExpectedAuthentTransactionSeqNum = priv->CurrentAuthentTransactionSeqNum+1;
2863 	priv->CurrentAuthentTransactionSeqNum += 2;
2864 
2865 	if (challenge_len != 0)	{
2866 		auth.el_id = 16; /* challenge_text */
2867 		auth.chall_text_len = challenge_len;
2868 		memcpy(auth.chall_text, challenge, challenge_len);
2869 		atmel_transmit_management_frame(priv, &header, (u8 *)&auth, 8 + challenge_len);
2870 	} else {
2871 		atmel_transmit_management_frame(priv, &header, (u8 *)&auth, 6);
2872 	}
2873 }
2874 
2875 static void send_association_request(struct atmel_private *priv, int is_reassoc)
2876 {
2877 	u8 *ssid_el_p;
2878 	int bodysize;
2879 	struct ieee80211_hdr header;
2880 	struct ass_req_format {
2881 		__le16 capability;
2882 		__le16 listen_interval;
2883 		u8 ap[ETH_ALEN]; /* nothing after here directly accessible */
2884 		u8 ssid_el_id;
2885 		u8 ssid_len;
2886 		u8 ssid[MAX_SSID_LENGTH];
2887 		u8 sup_rates_el_id;
2888 		u8 sup_rates_len;
2889 		u8 rates[4];
2890 	} body;
2891 
2892 	header.frame_control = cpu_to_le16(IEEE80211_FTYPE_MGMT |
2893 		(is_reassoc ? IEEE80211_STYPE_REASSOC_REQ : IEEE80211_STYPE_ASSOC_REQ));
2894 	header.duration_id = cpu_to_le16(0x8000);
2895 	header.seq_ctrl = 0;
2896 
2897 	memcpy(header.addr1, priv->CurrentBSSID, ETH_ALEN);
2898 	memcpy(header.addr2, priv->dev->dev_addr, ETH_ALEN);
2899 	memcpy(header.addr3, priv->CurrentBSSID, ETH_ALEN);
2900 
2901 	body.capability = cpu_to_le16(WLAN_CAPABILITY_ESS);
2902 	if (priv->wep_is_on)
2903 		body.capability |= cpu_to_le16(WLAN_CAPABILITY_PRIVACY);
2904 	if (priv->preamble == SHORT_PREAMBLE)
2905 		body.capability |= cpu_to_le16(WLAN_CAPABILITY_SHORT_PREAMBLE);
2906 
2907 	body.listen_interval = cpu_to_le16(priv->listen_interval * priv->beacon_period);
2908 
2909 	/* current AP address - only in reassoc frame */
2910 	if (is_reassoc) {
2911 		memcpy(body.ap, priv->CurrentBSSID, ETH_ALEN);
2912 		ssid_el_p = &body.ssid_el_id;
2913 		bodysize = 18 + priv->SSID_size;
2914 	} else {
2915 		ssid_el_p = &body.ap[0];
2916 		bodysize = 12 + priv->SSID_size;
2917 	}
2918 
2919 	ssid_el_p[0] = WLAN_EID_SSID;
2920 	ssid_el_p[1] = priv->SSID_size;
2921 	memcpy(ssid_el_p + 2, priv->SSID, priv->SSID_size);
2922 	ssid_el_p[2 + priv->SSID_size] = WLAN_EID_SUPP_RATES;
2923 	ssid_el_p[3 + priv->SSID_size] = 4; /* len of supported rates */
2924 	memcpy(ssid_el_p + 4 + priv->SSID_size, atmel_basic_rates, 4);
2925 
2926 	atmel_transmit_management_frame(priv, &header, (void *)&body, bodysize);
2927 }
2928 
2929 static int is_frame_from_current_bss(struct atmel_private *priv,
2930 				     struct ieee80211_hdr *header)
2931 {
2932 	if (le16_to_cpu(header->frame_control) & IEEE80211_FCTL_FROMDS)
2933 		return memcmp(header->addr3, priv->CurrentBSSID, 6) == 0;
2934 	else
2935 		return memcmp(header->addr2, priv->CurrentBSSID, 6) == 0;
2936 }
2937 
2938 static int retrieve_bss(struct atmel_private *priv)
2939 {
2940 	int i;
2941 	int max_rssi = -128;
2942 	int max_index = -1;
2943 
2944 	if (priv->BSS_list_entries == 0)
2945 		return -1;
2946 
2947 	if (priv->connect_to_any_BSS) {
2948 		/* Select a BSS with the max-RSSI but of the same type and of
2949 		   the same WEP mode and that it is not marked as 'bad' (i.e.
2950 		   we had previously failed to connect to this BSS with the
2951 		   settings that we currently use) */
2952 		priv->current_BSS = 0;
2953 		for (i = 0; i < priv->BSS_list_entries; i++) {
2954 			if (priv->operating_mode == priv->BSSinfo[i].BSStype &&
2955 			    ((!priv->wep_is_on && !priv->BSSinfo[i].UsingWEP) ||
2956 			     (priv->wep_is_on && priv->BSSinfo[i].UsingWEP)) &&
2957 			    !(priv->BSSinfo[i].channel & 0x80)) {
2958 				max_rssi = priv->BSSinfo[i].RSSI;
2959 				priv->current_BSS = max_index = i;
2960 			}
2961 		}
2962 		return max_index;
2963 	}
2964 
2965 	for (i = 0; i < priv->BSS_list_entries; i++) {
2966 		if (priv->SSID_size == priv->BSSinfo[i].SSIDsize &&
2967 		    memcmp(priv->SSID, priv->BSSinfo[i].SSID, priv->SSID_size) == 0 &&
2968 		    priv->operating_mode == priv->BSSinfo[i].BSStype &&
2969 		    atmel_validate_channel(priv, priv->BSSinfo[i].channel) == 0) {
2970 			if (priv->BSSinfo[i].RSSI >= max_rssi) {
2971 				max_rssi = priv->BSSinfo[i].RSSI;
2972 				max_index = i;
2973 			}
2974 		}
2975 	}
2976 	return max_index;
2977 }
2978 
2979 static void store_bss_info(struct atmel_private *priv,
2980 			   struct ieee80211_hdr *header, u16 capability,
2981 			   u16 beacon_period, u8 channel, u8 rssi, u8 ssid_len,
2982 			   u8 *ssid, int is_beacon)
2983 {
2984 	u8 *bss = capability & WLAN_CAPABILITY_ESS ? header->addr2 : header->addr3;
2985 	int i, index;
2986 
2987 	for (index = -1, i = 0; i < priv->BSS_list_entries; i++)
2988 		if (memcmp(bss, priv->BSSinfo[i].BSSID, ETH_ALEN) == 0)
2989 			index = i;
2990 
2991 	/* If we process a probe and an entry from this BSS exists
2992 	   we will update the BSS entry with the info from this BSS.
2993 	   If we process a beacon we will only update RSSI */
2994 
2995 	if (index == -1) {
2996 		if (priv->BSS_list_entries == MAX_BSS_ENTRIES)
2997 			return;
2998 		index = priv->BSS_list_entries++;
2999 		memcpy(priv->BSSinfo[index].BSSID, bss, ETH_ALEN);
3000 		priv->BSSinfo[index].RSSI = rssi;
3001 	} else {
3002 		if (rssi > priv->BSSinfo[index].RSSI)
3003 			priv->BSSinfo[index].RSSI = rssi;
3004 		if (is_beacon)
3005 			return;
3006 	}
3007 
3008 	priv->BSSinfo[index].channel = channel;
3009 	priv->BSSinfo[index].beacon_period = beacon_period;
3010 	priv->BSSinfo[index].UsingWEP = capability & WLAN_CAPABILITY_PRIVACY;
3011 	memcpy(priv->BSSinfo[index].SSID, ssid, ssid_len);
3012 	priv->BSSinfo[index].SSIDsize = ssid_len;
3013 
3014 	if (capability & WLAN_CAPABILITY_IBSS)
3015 		priv->BSSinfo[index].BSStype = IW_MODE_ADHOC;
3016 	else if (capability & WLAN_CAPABILITY_ESS)
3017 		priv->BSSinfo[index].BSStype = IW_MODE_INFRA;
3018 
3019 	priv->BSSinfo[index].preamble = capability & WLAN_CAPABILITY_SHORT_PREAMBLE ?
3020 		SHORT_PREAMBLE : LONG_PREAMBLE;
3021 }
3022 
3023 static void authenticate(struct atmel_private *priv, u16 frame_len)
3024 {
3025 	struct auth_body *auth = (struct auth_body *)priv->rx_buf;
3026 	u16 status = le16_to_cpu(auth->status);
3027 	u16 trans_seq_no = le16_to_cpu(auth->trans_seq);
3028 	u16 system = le16_to_cpu(auth->alg);
3029 
3030 	if (status == WLAN_STATUS_SUCCESS && !priv->wep_is_on) {
3031 		/* no WEP */
3032 		if (priv->station_was_associated) {
3033 			atmel_enter_state(priv, STATION_STATE_REASSOCIATING);
3034 			send_association_request(priv, 1);
3035 			return;
3036 		} else {
3037 			atmel_enter_state(priv, STATION_STATE_ASSOCIATING);
3038 			send_association_request(priv, 0);
3039 			return;
3040 		}
3041 	}
3042 
3043 	if (status == WLAN_STATUS_SUCCESS && priv->wep_is_on) {
3044 		int should_associate = 0;
3045 		/* WEP */
3046 		if (trans_seq_no != priv->ExpectedAuthentTransactionSeqNum)
3047 			return;
3048 
3049 		if (system == WLAN_AUTH_OPEN) {
3050 			if (trans_seq_no == 0x0002) {
3051 				should_associate = 1;
3052 			}
3053 		} else if (system == WLAN_AUTH_SHARED_KEY) {
3054 			if (trans_seq_no == 0x0002 &&
3055 			    auth->el_id == WLAN_EID_CHALLENGE) {
3056 				send_authentication_request(priv, system, auth->chall_text, auth->chall_text_len);
3057 				return;
3058 			} else if (trans_seq_no == 0x0004) {
3059 				should_associate = 1;
3060 			}
3061 		}
3062 
3063 		if (should_associate) {
3064 			if (priv->station_was_associated) {
3065 				atmel_enter_state(priv, STATION_STATE_REASSOCIATING);
3066 				send_association_request(priv, 1);
3067 				return;
3068 			} else {
3069 				atmel_enter_state(priv, STATION_STATE_ASSOCIATING);
3070 				send_association_request(priv, 0);
3071 				return;
3072 			}
3073 		}
3074 	}
3075 
3076 	if (status == WLAN_STATUS_NOT_SUPPORTED_AUTH_ALG) {
3077 		/* Flip back and forth between WEP auth modes until the max
3078 		 * authentication tries has been exceeded.
3079 		 */
3080 		if (system == WLAN_AUTH_OPEN) {
3081 			priv->CurrentAuthentTransactionSeqNum = 0x001;
3082 			priv->exclude_unencrypted = 1;
3083 			send_authentication_request(priv, WLAN_AUTH_SHARED_KEY, NULL, 0);
3084 			return;
3085 		} else if (system == WLAN_AUTH_SHARED_KEY
3086 			   && priv->wep_is_on) {
3087 			priv->CurrentAuthentTransactionSeqNum = 0x001;
3088 			priv->exclude_unencrypted = 0;
3089 			send_authentication_request(priv, WLAN_AUTH_OPEN, NULL, 0);
3090 			return;
3091 		} else if (priv->connect_to_any_BSS) {
3092 			int bss_index;
3093 
3094 			priv->BSSinfo[(int)(priv->current_BSS)].channel |= 0x80;
3095 
3096 			if ((bss_index  = retrieve_bss(priv)) != -1) {
3097 				atmel_join_bss(priv, bss_index);
3098 				return;
3099 			}
3100 		}
3101 	}
3102 
3103 	priv->AuthenticationRequestRetryCnt = 0;
3104 	atmel_enter_state(priv,  STATION_STATE_MGMT_ERROR);
3105 	priv->station_is_associated = 0;
3106 }
3107 
3108 static void associate(struct atmel_private *priv, u16 frame_len, u16 subtype)
3109 {
3110 	struct ass_resp_format {
3111 		__le16 capability;
3112 		__le16 status;
3113 		__le16 ass_id;
3114 		u8 el_id;
3115 		u8 length;
3116 		u8 rates[4];
3117 	} *ass_resp = (struct ass_resp_format *)priv->rx_buf;
3118 
3119 	u16 status = le16_to_cpu(ass_resp->status);
3120 	u16 ass_id = le16_to_cpu(ass_resp->ass_id);
3121 	u16 rates_len = ass_resp->length > 4 ? 4 : ass_resp->length;
3122 
3123 	union iwreq_data wrqu;
3124 
3125 	if (frame_len < 8 + rates_len)
3126 		return;
3127 
3128 	if (status == WLAN_STATUS_SUCCESS) {
3129 		if (subtype == IEEE80211_STYPE_ASSOC_RESP)
3130 			priv->AssociationRequestRetryCnt = 0;
3131 		else
3132 			priv->ReAssociationRequestRetryCnt = 0;
3133 
3134 		atmel_set_mib16(priv, Mac_Mgmt_Mib_Type,
3135 				MAC_MGMT_MIB_STATION_ID_POS, ass_id & 0x3fff);
3136 		atmel_set_mib(priv, Phy_Mib_Type,
3137 			      PHY_MIB_RATE_SET_POS, ass_resp->rates, rates_len);
3138 		if (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 		} else {
3145 			priv->listen_interval = 2;
3146 			atmel_set_mib8(priv, Mac_Mgmt_Mib_Type,
3147 				       MAC_MGMT_MIB_PS_MODE_POS,  PS_MODE);
3148 			atmel_set_mib16(priv, Mac_Mgmt_Mib_Type,
3149 					MAC_MGMT_MIB_LISTEN_INTERVAL_POS, 2);
3150 		}
3151 
3152 		priv->station_is_associated = 1;
3153 		priv->station_was_associated = 1;
3154 		atmel_enter_state(priv, STATION_STATE_READY);
3155 
3156 		/* Send association event to userspace */
3157 		wrqu.data.length = 0;
3158 		wrqu.data.flags = 0;
3159 		memcpy(wrqu.ap_addr.sa_data, priv->CurrentBSSID, ETH_ALEN);
3160 		wrqu.ap_addr.sa_family = ARPHRD_ETHER;
3161 		wireless_send_event(priv->dev, SIOCGIWAP, &wrqu, NULL);
3162 
3163 		return;
3164 	}
3165 
3166 	if (subtype == IEEE80211_STYPE_ASSOC_RESP &&
3167 	    status != WLAN_STATUS_ASSOC_DENIED_RATES &&
3168 	    status != WLAN_STATUS_CAPS_UNSUPPORTED &&
3169 	    priv->AssociationRequestRetryCnt < MAX_ASSOCIATION_RETRIES) {
3170 		mod_timer(&priv->management_timer, jiffies + MGMT_JIFFIES);
3171 		priv->AssociationRequestRetryCnt++;
3172 		send_association_request(priv, 0);
3173 		return;
3174 	}
3175 
3176 	if (subtype == IEEE80211_STYPE_REASSOC_RESP &&
3177 	    status != WLAN_STATUS_ASSOC_DENIED_RATES &&
3178 	    status != WLAN_STATUS_CAPS_UNSUPPORTED &&
3179 	    priv->ReAssociationRequestRetryCnt < MAX_ASSOCIATION_RETRIES) {
3180 		mod_timer(&priv->management_timer, jiffies + MGMT_JIFFIES);
3181 		priv->ReAssociationRequestRetryCnt++;
3182 		send_association_request(priv, 1);
3183 		return;
3184 	}
3185 
3186 	atmel_enter_state(priv,  STATION_STATE_MGMT_ERROR);
3187 	priv->station_is_associated = 0;
3188 
3189 	if (priv->connect_to_any_BSS) {
3190 		int bss_index;
3191 		priv->BSSinfo[(int)(priv->current_BSS)].channel |= 0x80;
3192 
3193 		if ((bss_index = retrieve_bss(priv)) != -1)
3194 			atmel_join_bss(priv, bss_index);
3195 	}
3196 }
3197 
3198 static void atmel_join_bss(struct atmel_private *priv, int bss_index)
3199 {
3200 	struct bss_info *bss =  &priv->BSSinfo[bss_index];
3201 
3202 	memcpy(priv->CurrentBSSID, bss->BSSID, ETH_ALEN);
3203 	memcpy(priv->SSID, bss->SSID, priv->SSID_size = bss->SSIDsize);
3204 
3205 	/* The WPA stuff cares about the current AP address */
3206 	if (priv->use_wpa)
3207 		build_wpa_mib(priv);
3208 
3209 	/* When switching to AdHoc turn OFF Power Save if needed */
3210 
3211 	if (bss->BSStype == IW_MODE_ADHOC &&
3212 	    priv->operating_mode != IW_MODE_ADHOC &&
3213 	    priv->power_mode) {
3214 		priv->power_mode = 0;
3215 		priv->listen_interval = 1;
3216 		atmel_set_mib8(priv, Mac_Mgmt_Mib_Type,
3217 			       MAC_MGMT_MIB_PS_MODE_POS,  ACTIVE_MODE);
3218 		atmel_set_mib16(priv, Mac_Mgmt_Mib_Type,
3219 				MAC_MGMT_MIB_LISTEN_INTERVAL_POS, 1);
3220 	}
3221 
3222 	priv->operating_mode = bss->BSStype;
3223 	priv->channel = bss->channel & 0x7f;
3224 	priv->beacon_period = bss->beacon_period;
3225 
3226 	if (priv->preamble != bss->preamble) {
3227 		priv->preamble = bss->preamble;
3228 		atmel_set_mib8(priv, Local_Mib_Type,
3229 			       LOCAL_MIB_PREAMBLE_TYPE, bss->preamble);
3230 	}
3231 
3232 	if (!priv->wep_is_on && bss->UsingWEP) {
3233 		atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
3234 		priv->station_is_associated = 0;
3235 		return;
3236 	}
3237 
3238 	if (priv->wep_is_on && !bss->UsingWEP) {
3239 		atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
3240 		priv->station_is_associated = 0;
3241 		return;
3242 	}
3243 
3244 	atmel_enter_state(priv, STATION_STATE_JOINNING);
3245 
3246 	if (priv->operating_mode == IW_MODE_INFRA)
3247 		join(priv, BSS_TYPE_INFRASTRUCTURE);
3248 	else
3249 		join(priv, BSS_TYPE_AD_HOC);
3250 }
3251 
3252 static void restart_search(struct atmel_private *priv)
3253 {
3254 	int bss_index;
3255 
3256 	if (!priv->connect_to_any_BSS) {
3257 		atmel_scan(priv, 1);
3258 	} else {
3259 		priv->BSSinfo[(int)(priv->current_BSS)].channel |= 0x80;
3260 
3261 		if ((bss_index = retrieve_bss(priv)) != -1)
3262 			atmel_join_bss(priv, bss_index);
3263 		else
3264 			atmel_scan(priv, 0);
3265 	}
3266 }
3267 
3268 static void smooth_rssi(struct atmel_private *priv, u8 rssi)
3269 {
3270 	u8 old = priv->wstats.qual.level;
3271 	u8 max_rssi = 42; /* 502-rmfd-revd max by experiment, default for now */
3272 
3273 	switch (priv->firmware_type) {
3274 	case ATMEL_FW_TYPE_502E:
3275 		max_rssi = 63; /* 502-rmfd-reve max by experiment */
3276 		break;
3277 	default:
3278 		break;
3279 	}
3280 
3281 	rssi = rssi * 100 / max_rssi;
3282 	if ((rssi + old) % 2)
3283 		priv->wstats.qual.level = (rssi + old) / 2 + 1;
3284 	else
3285 		priv->wstats.qual.level = (rssi + old) / 2;
3286 	priv->wstats.qual.updated |= IW_QUAL_LEVEL_UPDATED;
3287 	priv->wstats.qual.updated &= ~IW_QUAL_LEVEL_INVALID;
3288 }
3289 
3290 static void atmel_smooth_qual(struct atmel_private *priv)
3291 {
3292 	unsigned long time_diff = (jiffies - priv->last_qual) / HZ;
3293 	while (time_diff--) {
3294 		priv->last_qual += HZ;
3295 		priv->wstats.qual.qual = priv->wstats.qual.qual / 2;
3296 		priv->wstats.qual.qual +=
3297 			priv->beacons_this_sec * priv->beacon_period * (priv->wstats.qual.level + 100) / 4000;
3298 		priv->beacons_this_sec = 0;
3299 	}
3300 	priv->wstats.qual.updated |= IW_QUAL_QUAL_UPDATED;
3301 	priv->wstats.qual.updated &= ~IW_QUAL_QUAL_INVALID;
3302 }
3303 
3304 /* deals with incoming management frames. */
3305 static void atmel_management_frame(struct atmel_private *priv,
3306 				   struct ieee80211_hdr *header,
3307 				   u16 frame_len, u8 rssi)
3308 {
3309 	u16 subtype;
3310 
3311 	subtype = le16_to_cpu(header->frame_control) & IEEE80211_FCTL_STYPE;
3312 	switch (subtype) {
3313 	case IEEE80211_STYPE_BEACON:
3314 	case IEEE80211_STYPE_PROBE_RESP:
3315 
3316 		/* beacon frame has multiple variable-length fields -
3317 		   never let an engineer loose with a data structure design. */
3318 		{
3319 			struct beacon_format {
3320 				__le64 timestamp;
3321 				__le16 interval;
3322 				__le16 capability;
3323 				u8 ssid_el_id;
3324 				u8 ssid_length;
3325 				/* ssid here */
3326 				u8 rates_el_id;
3327 				u8 rates_length;
3328 				/* rates here */
3329 				u8 ds_el_id;
3330 				u8 ds_length;
3331 				/* ds here */
3332 			} *beacon = (struct beacon_format *)priv->rx_buf;
3333 
3334 			u8 channel, rates_length, ssid_length;
3335 			u64 timestamp = le64_to_cpu(beacon->timestamp);
3336 			u16 beacon_interval = le16_to_cpu(beacon->interval);
3337 			u16 capability = le16_to_cpu(beacon->capability);
3338 			u8 *beaconp = priv->rx_buf;
3339 			ssid_length = beacon->ssid_length;
3340 			/* this blows chunks. */
3341 			if (frame_len < 14 || frame_len < ssid_length + 15)
3342 				return;
3343 			rates_length = beaconp[beacon->ssid_length + 15];
3344 			if (frame_len < ssid_length + rates_length + 18)
3345 				return;
3346 			if (ssid_length >  MAX_SSID_LENGTH)
3347 				return;
3348 			channel = beaconp[ssid_length + rates_length + 18];
3349 
3350 			if (priv->station_state == STATION_STATE_READY) {
3351 				smooth_rssi(priv, rssi);
3352 				if (is_frame_from_current_bss(priv, header)) {
3353 					priv->beacons_this_sec++;
3354 					atmel_smooth_qual(priv);
3355 					if (priv->last_beacon_timestamp) {
3356 						/* Note truncate this to 32 bits - kernel can't divide a long long */
3357 						u32 beacon_delay = timestamp - priv->last_beacon_timestamp;
3358 						int beacons = beacon_delay / (beacon_interval * 1000);
3359 						if (beacons > 1)
3360 							priv->wstats.miss.beacon += beacons - 1;
3361 					}
3362 					priv->last_beacon_timestamp = timestamp;
3363 					handle_beacon_probe(priv, capability, channel);
3364 				}
3365 			}
3366 
3367 			if (priv->station_state == STATION_STATE_SCANNING)
3368 				store_bss_info(priv, header, capability,
3369 					       beacon_interval, channel, rssi,
3370 					       ssid_length,
3371 					       &beacon->rates_el_id,
3372 					       subtype == IEEE80211_STYPE_BEACON);
3373 		}
3374 		break;
3375 
3376 	case IEEE80211_STYPE_AUTH:
3377 
3378 		if (priv->station_state == STATION_STATE_AUTHENTICATING)
3379 			authenticate(priv, frame_len);
3380 
3381 		break;
3382 
3383 	case IEEE80211_STYPE_ASSOC_RESP:
3384 	case IEEE80211_STYPE_REASSOC_RESP:
3385 
3386 		if (priv->station_state == STATION_STATE_ASSOCIATING ||
3387 		    priv->station_state == STATION_STATE_REASSOCIATING)
3388 			associate(priv, frame_len, subtype);
3389 
3390 		break;
3391 
3392 	case IEEE80211_STYPE_DISASSOC:
3393 		if (priv->station_is_associated &&
3394 		    priv->operating_mode == IW_MODE_INFRA &&
3395 		    is_frame_from_current_bss(priv, header)) {
3396 			priv->station_was_associated = 0;
3397 			priv->station_is_associated = 0;
3398 
3399 			atmel_enter_state(priv, STATION_STATE_JOINNING);
3400 			join(priv, BSS_TYPE_INFRASTRUCTURE);
3401 		}
3402 
3403 		break;
3404 
3405 	case IEEE80211_STYPE_DEAUTH:
3406 		if (priv->operating_mode == IW_MODE_INFRA &&
3407 		    is_frame_from_current_bss(priv, header)) {
3408 			priv->station_was_associated = 0;
3409 
3410 			atmel_enter_state(priv, STATION_STATE_JOINNING);
3411 			join(priv, BSS_TYPE_INFRASTRUCTURE);
3412 		}
3413 
3414 		break;
3415 	}
3416 }
3417 
3418 /* run when timer expires */
3419 static void atmel_management_timer(struct timer_list *t)
3420 {
3421 	struct atmel_private *priv = from_timer(priv, t, management_timer);
3422 	unsigned long flags;
3423 
3424 	/* Check if the card has been yanked. */
3425 	if (priv->card && priv->present_callback &&
3426 		!(*priv->present_callback)(priv->card))
3427 		return;
3428 
3429 	spin_lock_irqsave(&priv->irqlock, flags);
3430 
3431 	switch (priv->station_state) {
3432 
3433 	case STATION_STATE_AUTHENTICATING:
3434 		if (priv->AuthenticationRequestRetryCnt >= MAX_AUTHENTICATION_RETRIES) {
3435 			atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
3436 			priv->station_is_associated = 0;
3437 			priv->AuthenticationRequestRetryCnt = 0;
3438 			restart_search(priv);
3439 		} else {
3440 			int auth = WLAN_AUTH_OPEN;
3441 			priv->AuthenticationRequestRetryCnt++;
3442 			priv->CurrentAuthentTransactionSeqNum = 0x0001;
3443 			mod_timer(&priv->management_timer, jiffies + MGMT_JIFFIES);
3444 			if (priv->wep_is_on && priv->exclude_unencrypted)
3445 				auth = WLAN_AUTH_SHARED_KEY;
3446 			send_authentication_request(priv, auth, NULL, 0);
3447 	  }
3448 	  break;
3449 
3450 	case STATION_STATE_ASSOCIATING:
3451 		if (priv->AssociationRequestRetryCnt == MAX_ASSOCIATION_RETRIES) {
3452 			atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
3453 			priv->station_is_associated = 0;
3454 			priv->AssociationRequestRetryCnt = 0;
3455 			restart_search(priv);
3456 		} else {
3457 			priv->AssociationRequestRetryCnt++;
3458 			mod_timer(&priv->management_timer, jiffies + MGMT_JIFFIES);
3459 			send_association_request(priv, 0);
3460 		}
3461 	  break;
3462 
3463 	case STATION_STATE_REASSOCIATING:
3464 		if (priv->ReAssociationRequestRetryCnt == MAX_ASSOCIATION_RETRIES) {
3465 			atmel_enter_state(priv, STATION_STATE_MGMT_ERROR);
3466 			priv->station_is_associated = 0;
3467 			priv->ReAssociationRequestRetryCnt = 0;
3468 			restart_search(priv);
3469 		} else {
3470 			priv->ReAssociationRequestRetryCnt++;
3471 			mod_timer(&priv->management_timer, jiffies + MGMT_JIFFIES);
3472 			send_association_request(priv, 1);
3473 		}
3474 		break;
3475 
3476 	default:
3477 		break;
3478 	}
3479 
3480 	spin_unlock_irqrestore(&priv->irqlock, flags);
3481 }
3482 
3483 static void atmel_command_irq(struct atmel_private *priv)
3484 {
3485 	u8 status = atmel_rmem8(priv, atmel_co(priv, CMD_BLOCK_STATUS_OFFSET));
3486 	u8 command = atmel_rmem8(priv, atmel_co(priv, CMD_BLOCK_COMMAND_OFFSET));
3487 	int fast_scan;
3488 	union iwreq_data wrqu;
3489 
3490 	if (status == CMD_STATUS_IDLE ||
3491 	    status == CMD_STATUS_IN_PROGRESS)
3492 		return;
3493 
3494 	switch (command) {
3495 	case CMD_Start:
3496 		if (status == CMD_STATUS_COMPLETE) {
3497 			priv->station_was_associated = priv->station_is_associated;
3498 			atmel_get_mib(priv, Mac_Mgmt_Mib_Type, MAC_MGMT_MIB_CUR_BSSID_POS,
3499 				      (u8 *)priv->CurrentBSSID, 6);
3500 			atmel_enter_state(priv, STATION_STATE_READY);
3501 		}
3502 		break;
3503 
3504 	case CMD_Scan:
3505 		fast_scan = priv->fast_scan;
3506 		priv->fast_scan = 0;
3507 
3508 		if (status != CMD_STATUS_COMPLETE) {
3509 			atmel_scan(priv, 1);
3510 		} else {
3511 			int bss_index = retrieve_bss(priv);
3512 			int notify_scan_complete = 1;
3513 			if (bss_index != -1) {
3514 				atmel_join_bss(priv, bss_index);
3515 			} else if (priv->operating_mode == IW_MODE_ADHOC &&
3516 				   priv->SSID_size != 0) {
3517 				start(priv, BSS_TYPE_AD_HOC);
3518 			} else {
3519 				priv->fast_scan = !fast_scan;
3520 				atmel_scan(priv, 1);
3521 				notify_scan_complete = 0;
3522 			}
3523 			priv->site_survey_state = SITE_SURVEY_COMPLETED;
3524 			if (notify_scan_complete) {
3525 				wrqu.data.length = 0;
3526 				wrqu.data.flags = 0;
3527 				wireless_send_event(priv->dev, SIOCGIWSCAN, &wrqu, NULL);
3528 			}
3529 		}
3530 		break;
3531 
3532 	case CMD_SiteSurvey:
3533 		priv->fast_scan = 0;
3534 
3535 		if (status != CMD_STATUS_COMPLETE)
3536 			return;
3537 
3538 		priv->site_survey_state = SITE_SURVEY_COMPLETED;
3539 		if (priv->station_is_associated) {
3540 			atmel_enter_state(priv, STATION_STATE_READY);
3541 			wrqu.data.length = 0;
3542 			wrqu.data.flags = 0;
3543 			wireless_send_event(priv->dev, SIOCGIWSCAN, &wrqu, NULL);
3544 		} else {
3545 			atmel_scan(priv, 1);
3546 		}
3547 		break;
3548 
3549 	case CMD_Join:
3550 		if (status == CMD_STATUS_COMPLETE) {
3551 			if (priv->operating_mode == IW_MODE_ADHOC) {
3552 				priv->station_was_associated = priv->station_is_associated;
3553 				atmel_enter_state(priv, STATION_STATE_READY);
3554 			} else {
3555 				int auth = WLAN_AUTH_OPEN;
3556 				priv->AuthenticationRequestRetryCnt = 0;
3557 				atmel_enter_state(priv, STATION_STATE_AUTHENTICATING);
3558 
3559 				mod_timer(&priv->management_timer, jiffies + MGMT_JIFFIES);
3560 				priv->CurrentAuthentTransactionSeqNum = 0x0001;
3561 				if (priv->wep_is_on && priv->exclude_unencrypted)
3562 					auth = WLAN_AUTH_SHARED_KEY;
3563 				send_authentication_request(priv, auth, NULL, 0);
3564 			}
3565 			return;
3566 		}
3567 
3568 		atmel_scan(priv, 1);
3569 	}
3570 }
3571 
3572 static int atmel_wakeup_firmware(struct atmel_private *priv)
3573 {
3574 	struct host_info_struct *iface = &priv->host_info;
3575 	u16 mr1, mr3;
3576 	int i;
3577 
3578 	if (priv->card_type == CARD_TYPE_SPI_FLASH)
3579 		atmel_set_gcr(priv->dev, GCR_REMAP);
3580 
3581 	/* wake up on-board processor */
3582 	atmel_clear_gcr(priv->dev, 0x0040);
3583 	atmel_write16(priv->dev, BSR, BSS_SRAM);
3584 
3585 	if (priv->card_type == CARD_TYPE_SPI_FLASH)
3586 		mdelay(100);
3587 
3588 	/* and wait for it */
3589 	for (i = LOOP_RETRY_LIMIT; i; i--) {
3590 		mr1 = atmel_read16(priv->dev, MR1);
3591 		mr3 = atmel_read16(priv->dev, MR3);
3592 
3593 		if (mr3 & MAC_BOOT_COMPLETE)
3594 			break;
3595 		if (mr1 & MAC_BOOT_COMPLETE &&
3596 		    priv->bus_type == BUS_TYPE_PCCARD)
3597 			break;
3598 	}
3599 
3600 	if (i == 0) {
3601 		printk(KERN_ALERT "%s: MAC failed to boot.\n", priv->dev->name);
3602 		return -EIO;
3603 	}
3604 
3605 	if ((priv->host_info_base = atmel_read16(priv->dev, MR2)) == 0xffff) {
3606 		printk(KERN_ALERT "%s: card missing.\n", priv->dev->name);
3607 		return -ENODEV;
3608 	}
3609 
3610 	/* now check for completion of MAC initialization through
3611 	   the FunCtrl field of the IFACE, poll MR1 to detect completion of
3612 	   MAC initialization, check completion status, set interrupt mask,
3613 	   enables interrupts and calls Tx and Rx initialization functions */
3614 
3615 	atmel_wmem8(priv, atmel_hi(priv, IFACE_FUNC_CTRL_OFFSET), FUNC_CTRL_INIT_COMPLETE);
3616 
3617 	for (i = LOOP_RETRY_LIMIT; i; i--) {
3618 		mr1 = atmel_read16(priv->dev, MR1);
3619 		mr3 = atmel_read16(priv->dev, MR3);
3620 
3621 		if (mr3 & MAC_INIT_COMPLETE)
3622 			break;
3623 		if (mr1 & MAC_INIT_COMPLETE &&
3624 		    priv->bus_type == BUS_TYPE_PCCARD)
3625 			break;
3626 	}
3627 
3628 	if (i == 0) {
3629 		printk(KERN_ALERT "%s: MAC failed to initialise.\n",
3630 				priv->dev->name);
3631 		return -EIO;
3632 	}
3633 
3634 	/* Check for MAC_INIT_OK only on the register that the MAC_INIT_OK was set */
3635 	if ((mr3 & MAC_INIT_COMPLETE) &&
3636 	    !(atmel_read16(priv->dev, MR3) & MAC_INIT_OK)) {
3637 		printk(KERN_ALERT "%s: MAC failed MR3 self-test.\n", priv->dev->name);
3638 		return -EIO;
3639 	}
3640 	if ((mr1 & MAC_INIT_COMPLETE) &&
3641 	    !(atmel_read16(priv->dev, MR1) & MAC_INIT_OK)) {
3642 		printk(KERN_ALERT "%s: MAC failed MR1 self-test.\n", priv->dev->name);
3643 		return -EIO;
3644 	}
3645 
3646 	atmel_copy_to_host(priv->dev, (unsigned char *)iface,
3647 			   priv->host_info_base, sizeof(*iface));
3648 
3649 	iface->tx_buff_pos = le16_to_cpu(iface->tx_buff_pos);
3650 	iface->tx_buff_size = le16_to_cpu(iface->tx_buff_size);
3651 	iface->tx_desc_pos = le16_to_cpu(iface->tx_desc_pos);
3652 	iface->tx_desc_count = le16_to_cpu(iface->tx_desc_count);
3653 	iface->rx_buff_pos = le16_to_cpu(iface->rx_buff_pos);
3654 	iface->rx_buff_size = le16_to_cpu(iface->rx_buff_size);
3655 	iface->rx_desc_pos = le16_to_cpu(iface->rx_desc_pos);
3656 	iface->rx_desc_count = le16_to_cpu(iface->rx_desc_count);
3657 	iface->build_version = le16_to_cpu(iface->build_version);
3658 	iface->command_pos = le16_to_cpu(iface->command_pos);
3659 	iface->major_version = le16_to_cpu(iface->major_version);
3660 	iface->minor_version = le16_to_cpu(iface->minor_version);
3661 	iface->func_ctrl = le16_to_cpu(iface->func_ctrl);
3662 	iface->mac_status = le16_to_cpu(iface->mac_status);
3663 
3664 	return 0;
3665 }
3666 
3667 /* determine type of memory and MAC address */
3668 static int probe_atmel_card(struct net_device *dev)
3669 {
3670 	int rc = 0;
3671 	struct atmel_private *priv = netdev_priv(dev);
3672 
3673 	/* reset pccard */
3674 	if (priv->bus_type == BUS_TYPE_PCCARD)
3675 		atmel_write16(dev, GCR, 0x0060);
3676 
3677 	atmel_write16(dev, GCR, 0x0040);
3678 	mdelay(500);
3679 
3680 	if (atmel_read16(dev, MR2) == 0) {
3681 		/* No stored firmware so load a small stub which just
3682 		   tells us the MAC address */
3683 		int i;
3684 		priv->card_type = CARD_TYPE_EEPROM;
3685 		atmel_write16(dev, BSR, BSS_IRAM);
3686 		atmel_copy_to_card(dev, 0, mac_reader, sizeof(mac_reader));
3687 		atmel_set_gcr(dev, GCR_REMAP);
3688 		atmel_clear_gcr(priv->dev, 0x0040);
3689 		atmel_write16(dev, BSR, BSS_SRAM);
3690 		for (i = LOOP_RETRY_LIMIT; i; i--)
3691 			if (atmel_read16(dev, MR3) & MAC_BOOT_COMPLETE)
3692 				break;
3693 		if (i == 0) {
3694 			printk(KERN_ALERT "%s: MAC failed to boot MAC address reader.\n", dev->name);
3695 		} else {
3696 			atmel_copy_to_host(dev, dev->dev_addr, atmel_read16(dev, MR2), 6);
3697 			/* got address, now squash it again until the network
3698 			   interface is opened */
3699 			if (priv->bus_type == BUS_TYPE_PCCARD)
3700 				atmel_write16(dev, GCR, 0x0060);
3701 			atmel_write16(dev, GCR, 0x0040);
3702 			rc = 1;
3703 		}
3704 	} else if (atmel_read16(dev, MR4) == 0) {
3705 		/* Mac address easy in this case. */
3706 		priv->card_type = CARD_TYPE_PARALLEL_FLASH;
3707 		atmel_write16(dev,  BSR, 1);
3708 		atmel_copy_to_host(dev, dev->dev_addr, 0xc000, 6);
3709 		atmel_write16(dev,  BSR, 0x200);
3710 		rc = 1;
3711 	} else {
3712 		/* Standard firmware in flash, boot it up and ask
3713 		   for the Mac Address */
3714 		priv->card_type = CARD_TYPE_SPI_FLASH;
3715 		if (atmel_wakeup_firmware(priv) == 0) {
3716 			atmel_get_mib(priv, Mac_Address_Mib_Type, 0, dev->dev_addr, 6);
3717 
3718 			/* got address, now squash it again until the network
3719 			   interface is opened */
3720 			if (priv->bus_type == BUS_TYPE_PCCARD)
3721 				atmel_write16(dev, GCR, 0x0060);
3722 			atmel_write16(dev, GCR, 0x0040);
3723 			rc = 1;
3724 		}
3725 	}
3726 
3727 	if (rc) {
3728 		if (dev->dev_addr[0] == 0xFF) {
3729 			static const u8 default_mac[] = {
3730 				0x00, 0x04, 0x25, 0x00, 0x00, 0x00
3731 			};
3732 			printk(KERN_ALERT "%s: *** Invalid MAC address. UPGRADE Firmware ****\n", dev->name);
3733 			memcpy(dev->dev_addr, default_mac, ETH_ALEN);
3734 		}
3735 	}
3736 
3737 	return rc;
3738 }
3739 
3740 /* Move the encyption information on the MIB structure.
3741    This routine is for the pre-WPA firmware: later firmware has
3742    a different format MIB and a different routine. */
3743 static void build_wep_mib(struct atmel_private *priv)
3744 {
3745 	struct { /* NB this is matched to the hardware, don't change. */
3746 		u8 wep_is_on;
3747 		u8 default_key; /* 0..3 */
3748 		u8 reserved;
3749 		u8 exclude_unencrypted;
3750 
3751 		u32 WEPICV_error_count;
3752 		u32 WEP_excluded_count;
3753 
3754 		u8 wep_keys[MAX_ENCRYPTION_KEYS][13];
3755 		u8 encryption_level; /* 0, 1, 2 */
3756 		u8 reserved2[3];
3757 	} mib;
3758 	int i;
3759 
3760 	mib.wep_is_on = priv->wep_is_on;
3761 	if (priv->wep_is_on) {
3762 		if (priv->wep_key_len[priv->default_key] > 5)
3763 			mib.encryption_level = 2;
3764 		else
3765 			mib.encryption_level = 1;
3766 	} else {
3767 		mib.encryption_level = 0;
3768 	}
3769 
3770 	mib.default_key = priv->default_key;
3771 	mib.exclude_unencrypted = priv->exclude_unencrypted;
3772 
3773 	for (i = 0; i < MAX_ENCRYPTION_KEYS; i++)
3774 		memcpy(mib.wep_keys[i], priv->wep_keys[i], 13);
3775 
3776 	atmel_set_mib(priv, Mac_Wep_Mib_Type, 0, (u8 *)&mib, sizeof(mib));
3777 }
3778 
3779 static void build_wpa_mib(struct atmel_private *priv)
3780 {
3781 	/* This is for the later (WPA enabled) firmware. */
3782 
3783 	struct { /* NB this is matched to the hardware, don't change. */
3784 		u8 cipher_default_key_value[MAX_ENCRYPTION_KEYS][MAX_ENCRYPTION_KEY_SIZE];
3785 		u8 receiver_address[ETH_ALEN];
3786 		u8 wep_is_on;
3787 		u8 default_key; /* 0..3 */
3788 		u8 group_key;
3789 		u8 exclude_unencrypted;
3790 		u8 encryption_type;
3791 		u8 reserved;
3792 
3793 		u32 WEPICV_error_count;
3794 		u32 WEP_excluded_count;
3795 
3796 		u8 key_RSC[4][8];
3797 	} mib;
3798 
3799 	int i;
3800 
3801 	mib.wep_is_on = priv->wep_is_on;
3802 	mib.exclude_unencrypted = priv->exclude_unencrypted;
3803 	memcpy(mib.receiver_address, priv->CurrentBSSID, ETH_ALEN);
3804 
3805 	/* zero all the keys before adding in valid ones. */
3806 	memset(mib.cipher_default_key_value, 0, sizeof(mib.cipher_default_key_value));
3807 
3808 	if (priv->wep_is_on) {
3809 		/* There's a comment in the Atmel code to the effect that this
3810 		   is only valid when still using WEP, it may need to be set to
3811 		   something to use WPA */
3812 		memset(mib.key_RSC, 0, sizeof(mib.key_RSC));
3813 
3814 		mib.default_key = mib.group_key = 255;
3815 		for (i = 0; i < MAX_ENCRYPTION_KEYS; i++) {
3816 			if (priv->wep_key_len[i] > 0) {
3817 				memcpy(mib.cipher_default_key_value[i], priv->wep_keys[i], MAX_ENCRYPTION_KEY_SIZE);
3818 				if (i == priv->default_key) {
3819 					mib.default_key = i;
3820 					mib.cipher_default_key_value[i][MAX_ENCRYPTION_KEY_SIZE-1] = 7;
3821 					mib.cipher_default_key_value[i][MAX_ENCRYPTION_KEY_SIZE-2] = priv->pairwise_cipher_suite;
3822 				} else {
3823 					mib.group_key = i;
3824 					priv->group_cipher_suite = priv->pairwise_cipher_suite;
3825 					mib.cipher_default_key_value[i][MAX_ENCRYPTION_KEY_SIZE-1] = 1;
3826 					mib.cipher_default_key_value[i][MAX_ENCRYPTION_KEY_SIZE-2] = priv->group_cipher_suite;
3827 				}
3828 			}
3829 		}
3830 		if (mib.default_key == 255)
3831 			mib.default_key = mib.group_key != 255 ? mib.group_key : 0;
3832 		if (mib.group_key == 255)
3833 			mib.group_key = mib.default_key;
3834 
3835 	}
3836 
3837 	atmel_set_mib(priv, Mac_Wep_Mib_Type, 0, (u8 *)&mib, sizeof(mib));
3838 }
3839 
3840 static int reset_atmel_card(struct net_device *dev)
3841 {
3842 	/* do everything necessary to wake up the hardware, including
3843 	   waiting for the lightning strike and throwing the knife switch....
3844 
3845 	   set all the Mib values which matter in the card to match
3846 	   their settings in the atmel_private structure. Some of these
3847 	   can be altered on the fly, but many (WEP, infrastructure or ad-hoc)
3848 	   can only be changed by tearing down the world and coming back through
3849 	   here.
3850 
3851 	   This routine is also responsible for initialising some
3852 	   hardware-specific fields in the atmel_private structure,
3853 	   including a copy of the firmware's hostinfo structure
3854 	   which is the route into the rest of the firmware datastructures. */
3855 
3856 	struct atmel_private *priv = netdev_priv(dev);
3857 	u8 configuration;
3858 	int old_state = priv->station_state;
3859 	int err = 0;
3860 
3861 	/* data to add to the firmware names, in priority order
3862 	   this implemenents firmware versioning */
3863 
3864 	static char *firmware_modifier[] = {
3865 		"-wpa",
3866 		"",
3867 		NULL
3868 	};
3869 
3870 	/* reset pccard */
3871 	if (priv->bus_type == BUS_TYPE_PCCARD)
3872 		atmel_write16(priv->dev, GCR, 0x0060);
3873 
3874 	/* stop card , disable interrupts */
3875 	atmel_write16(priv->dev, GCR, 0x0040);
3876 
3877 	if (priv->card_type == CARD_TYPE_EEPROM) {
3878 		/* copy in firmware if needed */
3879 		const struct firmware *fw_entry = NULL;
3880 		const unsigned char *fw;
3881 		int len = priv->firmware_length;
3882 		if (!(fw = priv->firmware)) {
3883 			if (priv->firmware_type == ATMEL_FW_TYPE_NONE) {
3884 				if (strlen(priv->firmware_id) == 0) {
3885 					printk(KERN_INFO
3886 					       "%s: card type is unknown: assuming at76c502 firmware is OK.\n",
3887 					       dev->name);
3888 					printk(KERN_INFO
3889 					       "%s: if not, use the firmware= module parameter.\n",
3890 					       dev->name);
3891 					strcpy(priv->firmware_id, "atmel_at76c502.bin");
3892 				}
3893 				err = request_firmware(&fw_entry, priv->firmware_id, priv->sys_dev);
3894 				if (err != 0) {
3895 					printk(KERN_ALERT
3896 					       "%s: firmware %s is missing, cannot continue.\n",
3897 					       dev->name, priv->firmware_id);
3898 					return err;
3899 				}
3900 			} else {
3901 				int fw_index = 0;
3902 				int success = 0;
3903 
3904 				/* get firmware filename entry based on firmware type ID */
3905 				while (fw_table[fw_index].fw_type != priv->firmware_type
3906 						&& fw_table[fw_index].fw_type != ATMEL_FW_TYPE_NONE)
3907 					fw_index++;
3908 
3909 				/* construct the actual firmware file name */
3910 				if (fw_table[fw_index].fw_type != ATMEL_FW_TYPE_NONE) {
3911 					int i;
3912 					for (i = 0; firmware_modifier[i]; i++) {
3913 						snprintf(priv->firmware_id, 32, "%s%s.%s", fw_table[fw_index].fw_file,
3914 							firmware_modifier[i], fw_table[fw_index].fw_file_ext);
3915 						priv->firmware_id[31] = '\0';
3916 						if (request_firmware(&fw_entry, priv->firmware_id, priv->sys_dev) == 0) {
3917 							success = 1;
3918 							break;
3919 						}
3920 					}
3921 				}
3922 				if (!success) {
3923 					printk(KERN_ALERT
3924 					       "%s: firmware %s is missing, cannot start.\n",
3925 					       dev->name, priv->firmware_id);
3926 					priv->firmware_id[0] = '\0';
3927 					return -ENOENT;
3928 				}
3929 			}
3930 
3931 			fw = fw_entry->data;
3932 			len = fw_entry->size;
3933 		}
3934 
3935 		if (len <= 0x6000) {
3936 			atmel_write16(priv->dev, BSR, BSS_IRAM);
3937 			atmel_copy_to_card(priv->dev, 0, fw, len);
3938 			atmel_set_gcr(priv->dev, GCR_REMAP);
3939 		} else {
3940 			/* Remap */
3941 			atmel_set_gcr(priv->dev, GCR_REMAP);
3942 			atmel_write16(priv->dev, BSR, BSS_IRAM);
3943 			atmel_copy_to_card(priv->dev, 0, fw, 0x6000);
3944 			atmel_write16(priv->dev, BSR, 0x2ff);
3945 			atmel_copy_to_card(priv->dev, 0x8000, &fw[0x6000], len - 0x6000);
3946 		}
3947 
3948 		release_firmware(fw_entry);
3949 	}
3950 
3951 	err = atmel_wakeup_firmware(priv);
3952 	if (err != 0)
3953 		return err;
3954 
3955 	/* Check the version and set the correct flag for wpa stuff,
3956 	   old and new firmware is incompatible.
3957 	   The pre-wpa 3com firmware reports major version 5,
3958 	   the wpa 3com firmware is major version 4 and doesn't need
3959 	   the 3com broken-ness filter. */
3960 	priv->use_wpa = (priv->host_info.major_version == 4);
3961 	priv->radio_on_broken = (priv->host_info.major_version == 5);
3962 
3963 	/* unmask all irq sources */
3964 	atmel_wmem8(priv, atmel_hi(priv, IFACE_INT_MASK_OFFSET), 0xff);
3965 
3966 	/* int Tx system and enable Tx */
3967 	atmel_wmem8(priv, atmel_tx(priv, TX_DESC_FLAGS_OFFSET, 0), 0);
3968 	atmel_wmem32(priv, atmel_tx(priv, TX_DESC_NEXT_OFFSET, 0), 0x80000000L);
3969 	atmel_wmem16(priv, atmel_tx(priv, TX_DESC_POS_OFFSET, 0), 0);
3970 	atmel_wmem16(priv, atmel_tx(priv, TX_DESC_SIZE_OFFSET, 0), 0);
3971 
3972 	priv->tx_desc_free = priv->host_info.tx_desc_count;
3973 	priv->tx_desc_head = 0;
3974 	priv->tx_desc_tail = 0;
3975 	priv->tx_desc_previous = 0;
3976 	priv->tx_free_mem = priv->host_info.tx_buff_size;
3977 	priv->tx_buff_head = 0;
3978 	priv->tx_buff_tail = 0;
3979 
3980 	configuration = atmel_rmem8(priv, atmel_hi(priv, IFACE_FUNC_CTRL_OFFSET));
3981 	atmel_wmem8(priv, atmel_hi(priv, IFACE_FUNC_CTRL_OFFSET),
3982 				   configuration | FUNC_CTRL_TxENABLE);
3983 
3984 	/* init Rx system and enable */
3985 	priv->rx_desc_head = 0;
3986 
3987 	configuration = atmel_rmem8(priv, atmel_hi(priv, IFACE_FUNC_CTRL_OFFSET));
3988 	atmel_wmem8(priv, atmel_hi(priv, IFACE_FUNC_CTRL_OFFSET),
3989 				   configuration | FUNC_CTRL_RxENABLE);
3990 
3991 	if (!priv->radio_on_broken) {
3992 		if (atmel_send_command_wait(priv, CMD_EnableRadio, NULL, 0) ==
3993 		    CMD_STATUS_REJECTED_RADIO_OFF) {
3994 			printk(KERN_INFO "%s: cannot turn the radio on.\n",
3995 			       dev->name);
3996 			return -EIO;
3997 		}
3998 	}
3999 
4000 	/* set up enough MIB values to run. */
4001 	atmel_set_mib8(priv, Local_Mib_Type, LOCAL_MIB_AUTO_TX_RATE_POS, priv->auto_tx_rate);
4002 	atmel_set_mib8(priv, Local_Mib_Type,  LOCAL_MIB_TX_PROMISCUOUS_POS,  PROM_MODE_OFF);
4003 	atmel_set_mib16(priv, Mac_Mib_Type, MAC_MIB_RTS_THRESHOLD_POS, priv->rts_threshold);
4004 	atmel_set_mib16(priv, Mac_Mib_Type, MAC_MIB_FRAG_THRESHOLD_POS, priv->frag_threshold);
4005 	atmel_set_mib8(priv, Mac_Mib_Type, MAC_MIB_SHORT_RETRY_POS, priv->short_retry);
4006 	atmel_set_mib8(priv, Mac_Mib_Type, MAC_MIB_LONG_RETRY_POS, priv->long_retry);
4007 	atmel_set_mib8(priv, Local_Mib_Type, LOCAL_MIB_PREAMBLE_TYPE, priv->preamble);
4008 	atmel_set_mib(priv, Mac_Address_Mib_Type, MAC_ADDR_MIB_MAC_ADDR_POS,
4009 		      priv->dev->dev_addr, 6);
4010 	atmel_set_mib8(priv, Mac_Mgmt_Mib_Type, MAC_MGMT_MIB_PS_MODE_POS, ACTIVE_MODE);
4011 	atmel_set_mib16(priv, Mac_Mgmt_Mib_Type, MAC_MGMT_MIB_LISTEN_INTERVAL_POS, 1);
4012 	atmel_set_mib16(priv, Mac_Mgmt_Mib_Type, MAC_MGMT_MIB_BEACON_PER_POS, priv->default_beacon_period);
4013 	atmel_set_mib(priv, Phy_Mib_Type, PHY_MIB_RATE_SET_POS, atmel_basic_rates, 4);
4014 	atmel_set_mib8(priv, Mac_Mgmt_Mib_Type, MAC_MGMT_MIB_CUR_PRIVACY_POS, priv->wep_is_on);
4015 	if (priv->use_wpa)
4016 		build_wpa_mib(priv);
4017 	else
4018 		build_wep_mib(priv);
4019 
4020 	if (old_state == STATION_STATE_READY) {
4021 		union iwreq_data wrqu;
4022 
4023 		wrqu.data.length = 0;
4024 		wrqu.data.flags = 0;
4025 		wrqu.ap_addr.sa_family = ARPHRD_ETHER;
4026 		eth_zero_addr(wrqu.ap_addr.sa_data);
4027 		wireless_send_event(priv->dev, SIOCGIWAP, &wrqu, NULL);
4028 	}
4029 
4030 	return 0;
4031 }
4032 
4033 static void atmel_send_command(struct atmel_private *priv, int command,
4034 			       void *cmd, int cmd_size)
4035 {
4036 	if (cmd)
4037 		atmel_copy_to_card(priv->dev, atmel_co(priv, CMD_BLOCK_PARAMETERS_OFFSET),
4038 				   cmd, cmd_size);
4039 
4040 	atmel_wmem8(priv, atmel_co(priv, CMD_BLOCK_COMMAND_OFFSET), command);
4041 	atmel_wmem8(priv, atmel_co(priv, CMD_BLOCK_STATUS_OFFSET), 0);
4042 }
4043 
4044 static int atmel_send_command_wait(struct atmel_private *priv, int command,
4045 				   void *cmd, int cmd_size)
4046 {
4047 	int i, status;
4048 
4049 	atmel_send_command(priv, command, cmd, cmd_size);
4050 
4051 	for (i = 5000; i; i--) {
4052 		status = atmel_rmem8(priv, atmel_co(priv, CMD_BLOCK_STATUS_OFFSET));
4053 		if (status != CMD_STATUS_IDLE &&
4054 		    status != CMD_STATUS_IN_PROGRESS)
4055 			break;
4056 		udelay(20);
4057 	}
4058 
4059 	if (i == 0) {
4060 		printk(KERN_ALERT "%s: failed to contact MAC.\n", priv->dev->name);
4061 		status =  CMD_STATUS_HOST_ERROR;
4062 	} else {
4063 		if (command != CMD_EnableRadio)
4064 			status = CMD_STATUS_COMPLETE;
4065 	}
4066 
4067 	return status;
4068 }
4069 
4070 static u8 atmel_get_mib8(struct atmel_private *priv, u8 type, u8 index)
4071 {
4072 	struct get_set_mib m;
4073 	m.type = type;
4074 	m.size = 1;
4075 	m.index = index;
4076 
4077 	atmel_send_command_wait(priv, CMD_Get_MIB_Vars, &m, MIB_HEADER_SIZE + 1);
4078 	return atmel_rmem8(priv, atmel_co(priv, CMD_BLOCK_PARAMETERS_OFFSET + MIB_HEADER_SIZE));
4079 }
4080 
4081 static void atmel_set_mib8(struct atmel_private *priv, u8 type, u8 index, u8 data)
4082 {
4083 	struct get_set_mib m;
4084 	m.type = type;
4085 	m.size = 1;
4086 	m.index = index;
4087 	m.data[0] = data;
4088 
4089 	atmel_send_command_wait(priv, CMD_Set_MIB_Vars, &m, MIB_HEADER_SIZE + 1);
4090 }
4091 
4092 static void atmel_set_mib16(struct atmel_private *priv, u8 type, u8 index,
4093 			    u16 data)
4094 {
4095 	struct get_set_mib m;
4096 	m.type = type;
4097 	m.size = 2;
4098 	m.index = index;
4099 	m.data[0] = data;
4100 	m.data[1] = data >> 8;
4101 
4102 	atmel_send_command_wait(priv, CMD_Set_MIB_Vars, &m, MIB_HEADER_SIZE + 2);
4103 }
4104 
4105 static void atmel_set_mib(struct atmel_private *priv, u8 type, u8 index,
4106 			  u8 *data, int data_len)
4107 {
4108 	struct get_set_mib m;
4109 	m.type = type;
4110 	m.size = data_len;
4111 	m.index = index;
4112 
4113 	if (data_len > MIB_MAX_DATA_BYTES)
4114 		printk(KERN_ALERT "%s: MIB buffer too small.\n", priv->dev->name);
4115 
4116 	memcpy(m.data, data, data_len);
4117 	atmel_send_command_wait(priv, CMD_Set_MIB_Vars, &m, MIB_HEADER_SIZE + data_len);
4118 }
4119 
4120 static void atmel_get_mib(struct atmel_private *priv, u8 type, u8 index,
4121 			  u8 *data, int data_len)
4122 {
4123 	struct get_set_mib m;
4124 	m.type = type;
4125 	m.size = data_len;
4126 	m.index = index;
4127 
4128 	if (data_len > MIB_MAX_DATA_BYTES)
4129 		printk(KERN_ALERT "%s: MIB buffer too small.\n", priv->dev->name);
4130 
4131 	atmel_send_command_wait(priv, CMD_Get_MIB_Vars, &m, MIB_HEADER_SIZE + data_len);
4132 	atmel_copy_to_host(priv->dev, data,
4133 			   atmel_co(priv, CMD_BLOCK_PARAMETERS_OFFSET + MIB_HEADER_SIZE), data_len);
4134 }
4135 
4136 static void atmel_writeAR(struct net_device *dev, u16 data)
4137 {
4138 	int i;
4139 	outw(data, dev->base_addr + AR);
4140 	/* Address register appears to need some convincing..... */
4141 	for (i = 0; data != inw(dev->base_addr + AR) && i < 10; i++)
4142 		outw(data, dev->base_addr + AR);
4143 }
4144 
4145 static void atmel_copy_to_card(struct net_device *dev, u16 dest,
4146 			       const unsigned char *src, u16 len)
4147 {
4148 	int i;
4149 	atmel_writeAR(dev, dest);
4150 	if (dest % 2) {
4151 		atmel_write8(dev, DR, *src);
4152 		src++; len--;
4153 	}
4154 	for (i = len; i > 1 ; i -= 2) {
4155 		u8 lb = *src++;
4156 		u8 hb = *src++;
4157 		atmel_write16(dev, DR, lb | (hb << 8));
4158 	}
4159 	if (i)
4160 		atmel_write8(dev, DR, *src);
4161 }
4162 
4163 static void atmel_copy_to_host(struct net_device *dev, unsigned char *dest,
4164 			       u16 src, u16 len)
4165 {
4166 	int i;
4167 	atmel_writeAR(dev, src);
4168 	if (src % 2) {
4169 		*dest = atmel_read8(dev, DR);
4170 		dest++; len--;
4171 	}
4172 	for (i = len; i > 1 ; i -= 2) {
4173 		u16 hw = atmel_read16(dev, DR);
4174 		*dest++ = hw;
4175 		*dest++ = hw >> 8;
4176 	}
4177 	if (i)
4178 		*dest = atmel_read8(dev, DR);
4179 }
4180 
4181 static void atmel_set_gcr(struct net_device *dev, u16 mask)
4182 {
4183 	outw(inw(dev->base_addr + GCR) | mask, dev->base_addr + GCR);
4184 }
4185 
4186 static void atmel_clear_gcr(struct net_device *dev, u16 mask)
4187 {
4188 	outw(inw(dev->base_addr + GCR) & ~mask, dev->base_addr + GCR);
4189 }
4190 
4191 static int atmel_lock_mac(struct atmel_private *priv)
4192 {
4193 	int i, j = 20;
4194  retry:
4195 	for (i = 5000; i; i--) {
4196 		if (!atmel_rmem8(priv, atmel_hi(priv, IFACE_LOCKOUT_HOST_OFFSET)))
4197 			break;
4198 		udelay(20);
4199 	}
4200 
4201 	if (!i)
4202 		return 0; /* timed out */
4203 
4204 	atmel_wmem8(priv, atmel_hi(priv, IFACE_LOCKOUT_MAC_OFFSET), 1);
4205 	if (atmel_rmem8(priv, atmel_hi(priv, IFACE_LOCKOUT_HOST_OFFSET))) {
4206 		atmel_wmem8(priv, atmel_hi(priv, IFACE_LOCKOUT_MAC_OFFSET), 0);
4207 		if (!j--)
4208 			return 0; /* timed out */
4209 		goto retry;
4210 	}
4211 
4212 	return 1;
4213 }
4214 
4215 static void atmel_wmem32(struct atmel_private *priv, u16 pos, u32 data)
4216 {
4217 	atmel_writeAR(priv->dev, pos);
4218 	atmel_write16(priv->dev, DR, data); /* card is little-endian */
4219 	atmel_write16(priv->dev, DR, data >> 16);
4220 }
4221 
4222 /***************************************************************************/
4223 /* There follows the source form of the MAC address reading firmware       */
4224 /***************************************************************************/
4225 #if 0
4226 
4227 /* Copyright 2003 Matthew T. Russotto                                      */
4228 /* But derived from the Atmel 76C502 firmware written by Atmel and         */
4229 /* included in "atmel wireless lan drivers" package                        */
4230 /**
4231     This file is part of net.russotto.AtmelMACFW, hereto referred to
4232     as AtmelMACFW
4233 
4234     AtmelMACFW is free software; you can redistribute it and/or modify
4235     it under the terms of the GNU General Public License version 2
4236     as published by the Free Software Foundation.
4237 
4238     AtmelMACFW is distributed in the hope that it will be useful,
4239     but WITHOUT ANY WARRANTY; without even the implied warranty of
4240     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
4241     GNU General Public License for more details.
4242 
4243     You should have received a copy of the GNU General Public License
4244     along with AtmelMACFW; if not, see <http://www.gnu.org/licenses/>.
4245 
4246 ****************************************************************************/
4247 /* This firmware should work on the 76C502 RFMD, RFMD_D, and RFMD_E        */
4248 /* It will probably work on the 76C504 and 76C502 RFMD_3COM                */
4249 /* It only works on SPI EEPROM versions of the card.                       */
4250 
4251 /* This firmware initializes the SPI controller and clock, reads the MAC   */
4252 /* address from the EEPROM into SRAM, and puts the SRAM offset of the MAC  */
4253 /* address in MR2, and sets MR3 to 0x10 to indicate it is done             */
4254 /* It also puts a complete copy of the EEPROM in SRAM with the offset in   */
4255 /* MR4, for investigational purposes (maybe we can determine chip type     */
4256 /* from that?)                                                             */
4257 
4258 	.org 0
4259     .set MRBASE, 0x8000000
4260 	.set CPSR_INITIAL, 0xD3 /* IRQ/FIQ disabled, ARM mode, Supervisor state */
4261 	.set CPSR_USER, 0xD1 /* IRQ/FIQ disabled, ARM mode, USER state */
4262 	.set SRAM_BASE,  0x02000000
4263 	.set SP_BASE,    0x0F300000
4264 	.set UNK_BASE,   0x0F000000 /* Some internal device, but which one? */
4265 	.set SPI_CGEN_BASE,  0x0E000000 /* Some internal device, but which one? */
4266 	.set UNK3_BASE,  0x02014000 /* Some internal device, but which one? */
4267 	.set STACK_BASE, 0x5600
4268 	.set SP_SR, 0x10
4269 	.set SP_TDRE, 2 /* status register bit -- TDR empty */
4270 	.set SP_RDRF, 1 /* status register bit -- RDR full */
4271 	.set SP_SWRST, 0x80
4272 	.set SP_SPIEN, 0x1
4273 	.set SP_CR, 0   /* control register */
4274 	.set SP_MR, 4   /* mode register */
4275 	.set SP_RDR, 0x08 /* Read Data Register */
4276 	.set SP_TDR, 0x0C /* Transmit Data Register */
4277 	.set SP_CSR0, 0x30 /* chip select registers */
4278 	.set SP_CSR1, 0x34
4279 	.set SP_CSR2, 0x38
4280 	.set SP_CSR3, 0x3C
4281 	.set NVRAM_CMD_RDSR, 5 /* read status register */
4282 	.set NVRAM_CMD_READ, 3 /* read data */
4283 	.set NVRAM_SR_RDY, 1 /* RDY bit.  This bit is inverted */
4284 	.set SPI_8CLOCKS, 0xFF /* Writing this to the TDR doesn't do anything to the
4285 				  serial output, since SO is normally high.  But it
4286 				  does cause 8 clock cycles and thus 8 bits to be
4287 				  clocked in to the chip.  See Atmel's SPI
4288 				  controller (e.g. AT91M55800) timing and 4K
4289 				  SPI EEPROM manuals */
4290 
4291 	.set NVRAM_SCRATCH, 0x02000100  /* arbitrary area for scratchpad memory */
4292 	.set NVRAM_IMAGE, 0x02000200
4293 	.set NVRAM_LENGTH, 0x0200
4294 	.set MAC_ADDRESS_MIB, SRAM_BASE
4295 	.set MAC_ADDRESS_LENGTH, 6
4296 	.set MAC_BOOT_FLAG, 0x10
4297 	.set MR1, 0
4298 	.set MR2, 4
4299 	.set MR3, 8
4300 	.set MR4, 0xC
4301 RESET_VECTOR:
4302 	b RESET_HANDLER
4303 UNDEF_VECTOR:
4304 	b HALT1
4305 SWI_VECTOR:
4306 	b HALT1
4307 IABORT_VECTOR:
4308 	b HALT1
4309 DABORT_VECTOR:
4310 RESERVED_VECTOR:
4311 	b HALT1
4312 IRQ_VECTOR:
4313 	b HALT1
4314 FIQ_VECTOR:
4315 	b HALT1
4316 HALT1:	b HALT1
4317 RESET_HANDLER:
4318 	mov     r0, #CPSR_INITIAL
4319 	msr	CPSR_c, r0	/* This is probably unnecessary */
4320 
4321 /* I'm guessing this is initializing clock generator electronics for SPI */
4322 	ldr	r0, =SPI_CGEN_BASE
4323 	mov	r1, #0
4324 	mov	r1, r1, lsl #3
4325 	orr	r1, r1, #0
4326 	str	r1, [r0]
4327 	ldr	r1, [r0, #28]
4328 	bic	r1, r1, #16
4329 	str	r1, [r0, #28]
4330 	mov	r1, #1
4331 	str	r1, [r0, #8]
4332 
4333 	ldr	r0, =MRBASE
4334 	mov	r1, #0
4335 	strh	r1, [r0, #MR1]
4336 	strh	r1, [r0, #MR2]
4337 	strh	r1, [r0, #MR3]
4338 	strh	r1, [r0, #MR4]
4339 
4340 	mov	sp, #STACK_BASE
4341 	bl	SP_INIT
4342 	mov	r0, #10
4343 	bl	DELAY9
4344 	bl	GET_MAC_ADDR
4345 	bl	GET_WHOLE_NVRAM
4346 	ldr	r0, =MRBASE
4347 	ldr	r1, =MAC_ADDRESS_MIB
4348 	strh	r1, [r0, #MR2]
4349 	ldr	r1, =NVRAM_IMAGE
4350 	strh	r1, [r0, #MR4]
4351 	mov	r1, #MAC_BOOT_FLAG
4352 	strh	r1, [r0, #MR3]
4353 HALT2:	b HALT2
4354 .func Get_Whole_NVRAM, GET_WHOLE_NVRAM
4355 GET_WHOLE_NVRAM:
4356 	stmdb	sp!, {lr}
4357 	mov	r2, #0 /* 0th bytes of NVRAM */
4358 	mov	r3, #NVRAM_LENGTH
4359 	mov	r1, #0		/* not used in routine */
4360 	ldr	r0, =NVRAM_IMAGE
4361 	bl	NVRAM_XFER
4362 	ldmia	sp!, {lr}
4363 	bx	lr
4364 .endfunc
4365 
4366 .func Get_MAC_Addr, GET_MAC_ADDR
4367 GET_MAC_ADDR:
4368 	stmdb	sp!, {lr}
4369 	mov	r2, #0x120	/* address of MAC Address within NVRAM */
4370 	mov	r3, #MAC_ADDRESS_LENGTH
4371 	mov	r1, #0		/* not used in routine */
4372 	ldr	r0, =MAC_ADDRESS_MIB
4373 	bl	NVRAM_XFER
4374 	ldmia	sp!, {lr}
4375 	bx	lr
4376 .endfunc
4377 .ltorg
4378 .func Delay9, DELAY9
4379 DELAY9:
4380 	adds	r0, r0, r0, LSL #3   /* r0 = r0 * 9 */
4381 DELAYLOOP:
4382 	beq	DELAY9_done
4383 	subs	r0, r0, #1
4384 	b	DELAYLOOP
4385 DELAY9_done:
4386 	bx	lr
4387 .endfunc
4388 
4389 .func SP_Init, SP_INIT
4390 SP_INIT:
4391 	mov	r1, #SP_SWRST
4392 	ldr	r0, =SP_BASE
4393 	str	r1, [r0, #SP_CR] /* reset the SPI */
4394 	mov	r1, #0
4395 	str	r1, [r0, #SP_CR] /* release SPI from reset state */
4396 	mov	r1, #SP_SPIEN
4397 	str	r1, [r0, #SP_MR] /* set the SPI to MASTER mode*/
4398 	str	r1, [r0, #SP_CR] /* enable the SPI */
4399 
4400 /*  My guess would be this turns on the SPI clock */
4401 	ldr	r3, =SPI_CGEN_BASE
4402 	ldr	r1, [r3, #28]
4403 	orr	r1, r1, #0x2000
4404 	str	r1, [r3, #28]
4405 
4406 	ldr	r1, =0x2000c01
4407 	str	r1, [r0, #SP_CSR0]
4408 	ldr	r1, =0x2000201
4409 	str	r1, [r0, #SP_CSR1]
4410 	str	r1, [r0, #SP_CSR2]
4411 	str	r1, [r0, #SP_CSR3]
4412 	ldr	r1, [r0, #SP_SR]
4413 	ldr	r0, [r0, #SP_RDR]
4414 	bx	lr
4415 .endfunc
4416 .func NVRAM_Init, NVRAM_INIT
4417 NVRAM_INIT:
4418 	ldr	r1, =SP_BASE
4419 	ldr	r0, [r1, #SP_RDR]
4420 	mov	r0, #NVRAM_CMD_RDSR
4421 	str	r0, [r1, #SP_TDR]
4422 SP_loop1:
4423 	ldr	r0, [r1, #SP_SR]
4424 	tst	r0, #SP_TDRE
4425 	beq	SP_loop1
4426 
4427 	mov	r0, #SPI_8CLOCKS
4428 	str	r0, [r1, #SP_TDR]
4429 SP_loop2:
4430 	ldr	r0, [r1, #SP_SR]
4431 	tst	r0, #SP_TDRE
4432 	beq	SP_loop2
4433 
4434 	ldr	r0, [r1, #SP_RDR]
4435 SP_loop3:
4436 	ldr	r0, [r1, #SP_SR]
4437 	tst	r0, #SP_RDRF
4438 	beq	SP_loop3
4439 
4440 	ldr	r0, [r1, #SP_RDR]
4441 	and	r0, r0, #255
4442 	bx	lr
4443 .endfunc
4444 
4445 .func NVRAM_Xfer, NVRAM_XFER
4446 	/* r0 = dest address */
4447 	/* r1 = not used */
4448 	/* r2 = src address within NVRAM */
4449 	/* r3 = length */
4450 NVRAM_XFER:
4451 	stmdb	sp!, {r4, r5, lr}
4452 	mov	r5, r0		/* save r0 (dest address) */
4453 	mov	r4, r3		/* save r3 (length) */
4454 	mov	r0, r2, LSR #5 /*  SPI memories put A8 in the command field */
4455 	and	r0, r0, #8
4456 	add	r0, r0, #NVRAM_CMD_READ
4457 	ldr	r1, =NVRAM_SCRATCH
4458 	strb	r0, [r1, #0]	/* save command in NVRAM_SCRATCH[0] */
4459 	strb	r2, [r1, #1]    /* save low byte of source address in NVRAM_SCRATCH[1] */
4460 _local1:
4461 	bl	NVRAM_INIT
4462 	tst	r0, #NVRAM_SR_RDY
4463 	bne	_local1
4464 	mov	r0, #20
4465 	bl	DELAY9
4466 	mov	r2, r4		/* length */
4467 	mov	r1, r5		/* dest address */
4468 	mov	r0, #2		/* bytes to transfer in command */
4469 	bl	NVRAM_XFER2
4470 	ldmia	sp!, {r4, r5, lr}
4471 	bx	lr
4472 .endfunc
4473 
4474 .func NVRAM_Xfer2, NVRAM_XFER2
4475 NVRAM_XFER2:
4476 	stmdb	sp!, {r4, r5, r6, lr}
4477 	ldr	r4, =SP_BASE
4478 	mov	r3, #0
4479 	cmp	r0, #0
4480 	bls	_local2
4481 	ldr	r5, =NVRAM_SCRATCH
4482 _local4:
4483 	ldrb	r6, [r5, r3]
4484 	str	r6, [r4, #SP_TDR]
4485 _local3:
4486 	ldr	r6, [r4, #SP_SR]
4487 	tst	r6, #SP_TDRE
4488 	beq	_local3
4489 	add	r3, r3, #1
4490 	cmp	r3, r0 /* r0 is # of bytes to send out (command+addr) */
4491 	blo	_local4
4492 _local2:
4493 	mov	r3, #SPI_8CLOCKS
4494 	str	r3, [r4, #SP_TDR]
4495 	ldr	r0, [r4, #SP_RDR]
4496 _local5:
4497 	ldr	r0, [r4, #SP_SR]
4498 	tst	r0, #SP_RDRF
4499 	beq	_local5
4500 	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 */
4501 	mov	r0, #0
4502 	cmp	r2, #0  /* r2 is # of bytes to copy in */
4503 	bls	_local6
4504 _local7:
4505 	ldr	r5, [r4, #SP_SR]
4506 	tst	r5, #SP_TDRE
4507 	beq	_local7
4508 	str	r3, [r4, #SP_TDR]  /* r3 has SPI_8CLOCKS */
4509 _local8:
4510 	ldr	r5, [r4, #SP_SR]
4511 	tst	r5, #SP_RDRF
4512 	beq	_local8
4513 	ldr	r5, [r4, #SP_RDR] /* but didn't we read this byte above? */
4514 	strb	r5, [r1], #1 /* postindexed */
4515 	add	r0, r0, #1
4516 	cmp	r0, r2
4517 	blo	_local7 /* since we don't send another address, the NVRAM must be capable of sequential reads */
4518 _local6:
4519 	mov	r0, #200
4520 	bl	DELAY9
4521 	ldmia	sp!, {r4, r5, r6, lr}
4522 	bx	lr
4523 #endif
4524