1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33#include <linux/sched.h>
34#include <linux/slab.h>
35#include <net/cfg80211-wext.h>
36#include "ipw2200.h"
37
38
39#ifndef KBUILD_EXTMOD
40#define VK "k"
41#else
42#define VK
43#endif
44
45#ifdef CONFIG_IPW2200_DEBUG
46#define VD "d"
47#else
48#define VD
49#endif
50
51#ifdef CONFIG_IPW2200_MONITOR
52#define VM "m"
53#else
54#define VM
55#endif
56
57#ifdef CONFIG_IPW2200_PROMISCUOUS
58#define VP "p"
59#else
60#define VP
61#endif
62
63#ifdef CONFIG_IPW2200_RADIOTAP
64#define VR "r"
65#else
66#define VR
67#endif
68
69#ifdef CONFIG_IPW2200_QOS
70#define VQ "q"
71#else
72#define VQ
73#endif
74
75#define IPW2200_VERSION "1.2.2" VK VD VM VP VR VQ
76#define DRV_DESCRIPTION "Intel(R) PRO/Wireless 2200/2915 Network Driver"
77#define DRV_COPYRIGHT "Copyright(c) 2003-2006 Intel Corporation"
78#define DRV_VERSION IPW2200_VERSION
79
80#define ETH_P_80211_STATS (ETH_P_80211_RAW + 1)
81
82MODULE_DESCRIPTION(DRV_DESCRIPTION);
83MODULE_VERSION(DRV_VERSION);
84MODULE_AUTHOR(DRV_COPYRIGHT);
85MODULE_LICENSE("GPL");
86MODULE_FIRMWARE("ipw2200-ibss.fw");
87#ifdef CONFIG_IPW2200_MONITOR
88MODULE_FIRMWARE("ipw2200-sniffer.fw");
89#endif
90MODULE_FIRMWARE("ipw2200-bss.fw");
91
92static int cmdlog = 0;
93static int debug = 0;
94static int default_channel = 0;
95static int network_mode = 0;
96
97static u32 ipw_debug_level;
98static int associate;
99static int auto_create = 1;
100static int led_support = 1;
101static int disable = 0;
102static int bt_coexist = 0;
103static int hwcrypto = 0;
104static int roaming = 1;
105static const char ipw_modes[] = {
106 'a', 'b', 'g', '?'
107};
108static int antenna = CFG_SYS_ANTENNA_BOTH;
109
110#ifdef CONFIG_IPW2200_PROMISCUOUS
111static int rtap_iface = 0;
112#endif
113
114static struct ieee80211_rate ipw2200_rates[] = {
115 { .bitrate = 10 },
116 { .bitrate = 20, .flags = IEEE80211_RATE_SHORT_PREAMBLE },
117 { .bitrate = 55, .flags = IEEE80211_RATE_SHORT_PREAMBLE },
118 { .bitrate = 110, .flags = IEEE80211_RATE_SHORT_PREAMBLE },
119 { .bitrate = 60 },
120 { .bitrate = 90 },
121 { .bitrate = 120 },
122 { .bitrate = 180 },
123 { .bitrate = 240 },
124 { .bitrate = 360 },
125 { .bitrate = 480 },
126 { .bitrate = 540 }
127};
128
129#define ipw2200_a_rates (ipw2200_rates + 4)
130#define ipw2200_num_a_rates 8
131#define ipw2200_bg_rates (ipw2200_rates + 0)
132#define ipw2200_num_bg_rates 12
133
134#ifdef CONFIG_IPW2200_QOS
135static int qos_enable = 0;
136static int qos_burst_enable = 0;
137static int qos_no_ack_mask = 0;
138static int burst_duration_CCK = 0;
139static int burst_duration_OFDM = 0;
140
141static struct libipw_qos_parameters def_qos_parameters_OFDM = {
142 {QOS_TX0_CW_MIN_OFDM, QOS_TX1_CW_MIN_OFDM, QOS_TX2_CW_MIN_OFDM,
143 QOS_TX3_CW_MIN_OFDM},
144 {QOS_TX0_CW_MAX_OFDM, QOS_TX1_CW_MAX_OFDM, QOS_TX2_CW_MAX_OFDM,
145 QOS_TX3_CW_MAX_OFDM},
146 {QOS_TX0_AIFS, QOS_TX1_AIFS, QOS_TX2_AIFS, QOS_TX3_AIFS},
147 {QOS_TX0_ACM, QOS_TX1_ACM, QOS_TX2_ACM, QOS_TX3_ACM},
148 {QOS_TX0_TXOP_LIMIT_OFDM, QOS_TX1_TXOP_LIMIT_OFDM,
149 QOS_TX2_TXOP_LIMIT_OFDM, QOS_TX3_TXOP_LIMIT_OFDM}
150};
151
152static struct libipw_qos_parameters def_qos_parameters_CCK = {
153 {QOS_TX0_CW_MIN_CCK, QOS_TX1_CW_MIN_CCK, QOS_TX2_CW_MIN_CCK,
154 QOS_TX3_CW_MIN_CCK},
155 {QOS_TX0_CW_MAX_CCK, QOS_TX1_CW_MAX_CCK, QOS_TX2_CW_MAX_CCK,
156 QOS_TX3_CW_MAX_CCK},
157 {QOS_TX0_AIFS, QOS_TX1_AIFS, QOS_TX2_AIFS, QOS_TX3_AIFS},
158 {QOS_TX0_ACM, QOS_TX1_ACM, QOS_TX2_ACM, QOS_TX3_ACM},
159 {QOS_TX0_TXOP_LIMIT_CCK, QOS_TX1_TXOP_LIMIT_CCK, QOS_TX2_TXOP_LIMIT_CCK,
160 QOS_TX3_TXOP_LIMIT_CCK}
161};
162
163static struct libipw_qos_parameters def_parameters_OFDM = {
164 {DEF_TX0_CW_MIN_OFDM, DEF_TX1_CW_MIN_OFDM, DEF_TX2_CW_MIN_OFDM,
165 DEF_TX3_CW_MIN_OFDM},
166 {DEF_TX0_CW_MAX_OFDM, DEF_TX1_CW_MAX_OFDM, DEF_TX2_CW_MAX_OFDM,
167 DEF_TX3_CW_MAX_OFDM},
168 {DEF_TX0_AIFS, DEF_TX1_AIFS, DEF_TX2_AIFS, DEF_TX3_AIFS},
169 {DEF_TX0_ACM, DEF_TX1_ACM, DEF_TX2_ACM, DEF_TX3_ACM},
170 {DEF_TX0_TXOP_LIMIT_OFDM, DEF_TX1_TXOP_LIMIT_OFDM,
171 DEF_TX2_TXOP_LIMIT_OFDM, DEF_TX3_TXOP_LIMIT_OFDM}
172};
173
174static struct libipw_qos_parameters def_parameters_CCK = {
175 {DEF_TX0_CW_MIN_CCK, DEF_TX1_CW_MIN_CCK, DEF_TX2_CW_MIN_CCK,
176 DEF_TX3_CW_MIN_CCK},
177 {DEF_TX0_CW_MAX_CCK, DEF_TX1_CW_MAX_CCK, DEF_TX2_CW_MAX_CCK,
178 DEF_TX3_CW_MAX_CCK},
179 {DEF_TX0_AIFS, DEF_TX1_AIFS, DEF_TX2_AIFS, DEF_TX3_AIFS},
180 {DEF_TX0_ACM, DEF_TX1_ACM, DEF_TX2_ACM, DEF_TX3_ACM},
181 {DEF_TX0_TXOP_LIMIT_CCK, DEF_TX1_TXOP_LIMIT_CCK, DEF_TX2_TXOP_LIMIT_CCK,
182 DEF_TX3_TXOP_LIMIT_CCK}
183};
184
185static u8 qos_oui[QOS_OUI_LEN] = { 0x00, 0x50, 0xF2 };
186
187static int from_priority_to_tx_queue[] = {
188 IPW_TX_QUEUE_1, IPW_TX_QUEUE_2, IPW_TX_QUEUE_2, IPW_TX_QUEUE_1,
189 IPW_TX_QUEUE_3, IPW_TX_QUEUE_3, IPW_TX_QUEUE_4, IPW_TX_QUEUE_4
190};
191
192static u32 ipw_qos_get_burst_duration(struct ipw_priv *priv);
193
194static int ipw_send_qos_params_command(struct ipw_priv *priv, struct libipw_qos_parameters
195 *qos_param);
196static int ipw_send_qos_info_command(struct ipw_priv *priv, struct libipw_qos_information_element
197 *qos_param);
198#endif
199
200static struct iw_statistics *ipw_get_wireless_stats(struct net_device *dev);
201static void ipw_remove_current_network(struct ipw_priv *priv);
202static void ipw_rx(struct ipw_priv *priv);
203static int ipw_queue_tx_reclaim(struct ipw_priv *priv,
204 struct clx2_tx_queue *txq, int qindex);
205static int ipw_queue_reset(struct ipw_priv *priv);
206
207static int ipw_queue_tx_hcmd(struct ipw_priv *priv, int hcmd, void *buf,
208 int len, int sync);
209
210static void ipw_tx_queue_free(struct ipw_priv *);
211
212static struct ipw_rx_queue *ipw_rx_queue_alloc(struct ipw_priv *);
213static void ipw_rx_queue_free(struct ipw_priv *, struct ipw_rx_queue *);
214static void ipw_rx_queue_replenish(void *);
215static int ipw_up(struct ipw_priv *);
216static void ipw_bg_up(struct work_struct *work);
217static void ipw_down(struct ipw_priv *);
218static void ipw_bg_down(struct work_struct *work);
219static int ipw_config(struct ipw_priv *);
220static int init_supported_rates(struct ipw_priv *priv,
221 struct ipw_supported_rates *prates);
222static void ipw_set_hwcrypto_keys(struct ipw_priv *);
223static void ipw_send_wep_keys(struct ipw_priv *, int);
224
225static int snprint_line(char *buf, size_t count,
226 const u8 * data, u32 len, u32 ofs)
227{
228 int out, i, j, l;
229 char c;
230
231 out = snprintf(buf, count, "%08X", ofs);
232
233 for (l = 0, i = 0; i < 2; i++) {
234 out += snprintf(buf + out, count - out, " ");
235 for (j = 0; j < 8 && l < len; j++, l++)
236 out += snprintf(buf + out, count - out, "%02X ",
237 data[(i * 8 + j)]);
238 for (; j < 8; j++)
239 out += snprintf(buf + out, count - out, " ");
240 }
241
242 out += snprintf(buf + out, count - out, " ");
243 for (l = 0, i = 0; i < 2; i++) {
244 out += snprintf(buf + out, count - out, " ");
245 for (j = 0; j < 8 && l < len; j++, l++) {
246 c = data[(i * 8 + j)];
247 if (!isascii(c) || !isprint(c))
248 c = '.';
249
250 out += snprintf(buf + out, count - out, "%c", c);
251 }
252
253 for (; j < 8; j++)
254 out += snprintf(buf + out, count - out, " ");
255 }
256
257 return out;
258}
259
260static void printk_buf(int level, const u8 * data, u32 len)
261{
262 char line[81];
263 u32 ofs = 0;
264 if (!(ipw_debug_level & level))
265 return;
266
267 while (len) {
268 snprint_line(line, sizeof(line), &data[ofs],
269 min(len, 16U), ofs);
270 printk(KERN_DEBUG "%s\n", line);
271 ofs += 16;
272 len -= min(len, 16U);
273 }
274}
275
276static int snprintk_buf(u8 * output, size_t size, const u8 * data, size_t len)
277{
278 size_t out = size;
279 u32 ofs = 0;
280 int total = 0;
281
282 while (size && len) {
283 out = snprint_line(output, size, &data[ofs],
284 min_t(size_t, len, 16U), ofs);
285
286 ofs += 16;
287 output += out;
288 size -= out;
289 len -= min_t(size_t, len, 16U);
290 total += out;
291 }
292 return total;
293}
294
295
296static u32 _ipw_read_reg32(struct ipw_priv *priv, u32 reg);
297#define ipw_read_reg32(a, b) _ipw_read_reg32(a, b)
298
299
300static u8 _ipw_read_reg8(struct ipw_priv *ipw, u32 reg);
301#define ipw_read_reg8(a, b) _ipw_read_reg8(a, b)
302
303
304static void _ipw_write_reg8(struct ipw_priv *priv, u32 reg, u8 value);
305static inline void ipw_write_reg8(struct ipw_priv *a, u32 b, u8 c)
306{
307 IPW_DEBUG_IO("%s %d: write_indirect8(0x%08X, 0x%08X)\n", __FILE__,
308 __LINE__, (u32) (b), (u32) (c));
309 _ipw_write_reg8(a, b, c);
310}
311
312
313static void _ipw_write_reg16(struct ipw_priv *priv, u32 reg, u16 value);
314static inline void ipw_write_reg16(struct ipw_priv *a, u32 b, u16 c)
315{
316 IPW_DEBUG_IO("%s %d: write_indirect16(0x%08X, 0x%08X)\n", __FILE__,
317 __LINE__, (u32) (b), (u32) (c));
318 _ipw_write_reg16(a, b, c);
319}
320
321
322static void _ipw_write_reg32(struct ipw_priv *priv, u32 reg, u32 value);
323static inline void ipw_write_reg32(struct ipw_priv *a, u32 b, u32 c)
324{
325 IPW_DEBUG_IO("%s %d: write_indirect32(0x%08X, 0x%08X)\n", __FILE__,
326 __LINE__, (u32) (b), (u32) (c));
327 _ipw_write_reg32(a, b, c);
328}
329
330
331static inline void _ipw_write8(struct ipw_priv *ipw, unsigned long ofs,
332 u8 val)
333{
334 writeb(val, ipw->hw_base + ofs);
335}
336
337
338#define ipw_write8(ipw, ofs, val) do { \
339 IPW_DEBUG_IO("%s %d: write_direct8(0x%08X, 0x%08X)\n", __FILE__, \
340 __LINE__, (u32)(ofs), (u32)(val)); \
341 _ipw_write8(ipw, ofs, val); \
342} while (0)
343
344
345static inline void _ipw_write16(struct ipw_priv *ipw, unsigned long ofs,
346 u16 val)
347{
348 writew(val, ipw->hw_base + ofs);
349}
350
351
352#define ipw_write16(ipw, ofs, val) do { \
353 IPW_DEBUG_IO("%s %d: write_direct16(0x%08X, 0x%08X)\n", __FILE__, \
354 __LINE__, (u32)(ofs), (u32)(val)); \
355 _ipw_write16(ipw, ofs, val); \
356} while (0)
357
358
359static inline void _ipw_write32(struct ipw_priv *ipw, unsigned long ofs,
360 u32 val)
361{
362 writel(val, ipw->hw_base + ofs);
363}
364
365
366#define ipw_write32(ipw, ofs, val) do { \
367 IPW_DEBUG_IO("%s %d: write_direct32(0x%08X, 0x%08X)\n", __FILE__, \
368 __LINE__, (u32)(ofs), (u32)(val)); \
369 _ipw_write32(ipw, ofs, val); \
370} while (0)
371
372
373static inline u8 _ipw_read8(struct ipw_priv *ipw, unsigned long ofs)
374{
375 return readb(ipw->hw_base + ofs);
376}
377
378
379#define ipw_read8(ipw, ofs) ({ \
380 IPW_DEBUG_IO("%s %d: read_direct8(0x%08X)\n", __FILE__, __LINE__, \
381 (u32)(ofs)); \
382 _ipw_read8(ipw, ofs); \
383})
384
385
386static inline u16 _ipw_read16(struct ipw_priv *ipw, unsigned long ofs)
387{
388 return readw(ipw->hw_base + ofs);
389}
390
391
392#define ipw_read16(ipw, ofs) ({ \
393 IPW_DEBUG_IO("%s %d: read_direct16(0x%08X)\n", __FILE__, __LINE__, \
394 (u32)(ofs)); \
395 _ipw_read16(ipw, ofs); \
396})
397
398
399static inline u32 _ipw_read32(struct ipw_priv *ipw, unsigned long ofs)
400{
401 return readl(ipw->hw_base + ofs);
402}
403
404
405#define ipw_read32(ipw, ofs) ({ \
406 IPW_DEBUG_IO("%s %d: read_direct32(0x%08X)\n", __FILE__, __LINE__, \
407 (u32)(ofs)); \
408 _ipw_read32(ipw, ofs); \
409})
410
411static void _ipw_read_indirect(struct ipw_priv *, u32, u8 *, int);
412
413#define ipw_read_indirect(a, b, c, d) ({ \
414 IPW_DEBUG_IO("%s %d: read_indirect(0x%08X) %u bytes\n", __FILE__, \
415 __LINE__, (u32)(b), (u32)(d)); \
416 _ipw_read_indirect(a, b, c, d); \
417})
418
419
420static void _ipw_write_indirect(struct ipw_priv *priv, u32 addr, u8 * data,
421 int num);
422#define ipw_write_indirect(a, b, c, d) do { \
423 IPW_DEBUG_IO("%s %d: write_indirect(0x%08X) %u bytes\n", __FILE__, \
424 __LINE__, (u32)(b), (u32)(d)); \
425 _ipw_write_indirect(a, b, c, d); \
426} while (0)
427
428
429static void _ipw_write_reg32(struct ipw_priv *priv, u32 reg, u32 value)
430{
431 IPW_DEBUG_IO(" %p : reg = 0x%8X : value = 0x%8X\n", priv, reg, value);
432 _ipw_write32(priv, IPW_INDIRECT_ADDR, reg);
433 _ipw_write32(priv, IPW_INDIRECT_DATA, value);
434}
435
436
437static void _ipw_write_reg8(struct ipw_priv *priv, u32 reg, u8 value)
438{
439 u32 aligned_addr = reg & IPW_INDIRECT_ADDR_MASK;
440 u32 dif_len = reg - aligned_addr;
441
442 IPW_DEBUG_IO(" reg = 0x%8X : value = 0x%8X\n", reg, value);
443 _ipw_write32(priv, IPW_INDIRECT_ADDR, aligned_addr);
444 _ipw_write8(priv, IPW_INDIRECT_DATA + dif_len, value);
445}
446
447
448static void _ipw_write_reg16(struct ipw_priv *priv, u32 reg, u16 value)
449{
450 u32 aligned_addr = reg & IPW_INDIRECT_ADDR_MASK;
451 u32 dif_len = (reg - aligned_addr) & (~0x1ul);
452
453 IPW_DEBUG_IO(" reg = 0x%8X : value = 0x%8X\n", reg, value);
454 _ipw_write32(priv, IPW_INDIRECT_ADDR, aligned_addr);
455 _ipw_write16(priv, IPW_INDIRECT_DATA + dif_len, value);
456}
457
458
459static u8 _ipw_read_reg8(struct ipw_priv *priv, u32 reg)
460{
461 u32 word;
462 _ipw_write32(priv, IPW_INDIRECT_ADDR, reg & IPW_INDIRECT_ADDR_MASK);
463 IPW_DEBUG_IO(" reg = 0x%8X :\n", reg);
464 word = _ipw_read32(priv, IPW_INDIRECT_DATA);
465 return (word >> ((reg & 0x3) * 8)) & 0xff;
466}
467
468
469static u32 _ipw_read_reg32(struct ipw_priv *priv, u32 reg)
470{
471 u32 value;
472
473 IPW_DEBUG_IO("%p : reg = 0x%08x\n", priv, reg);
474
475 _ipw_write32(priv, IPW_INDIRECT_ADDR, reg);
476 value = _ipw_read32(priv, IPW_INDIRECT_DATA);
477 IPW_DEBUG_IO(" reg = 0x%4X : value = 0x%4x\n", reg, value);
478 return value;
479}
480
481
482
483static void _ipw_read_indirect(struct ipw_priv *priv, u32 addr, u8 * buf,
484 int num)
485{
486 u32 aligned_addr = addr & IPW_INDIRECT_ADDR_MASK;
487 u32 dif_len = addr - aligned_addr;
488 u32 i;
489
490 IPW_DEBUG_IO("addr = %i, buf = %p, num = %i\n", addr, buf, num);
491
492 if (num <= 0) {
493 return;
494 }
495
496
497 if (unlikely(dif_len)) {
498 _ipw_write32(priv, IPW_INDIRECT_ADDR, aligned_addr);
499
500 for (i = dif_len; ((i < 4) && (num > 0)); i++, num--)
501 *buf++ = _ipw_read8(priv, IPW_INDIRECT_DATA + i);
502 aligned_addr += 4;
503 }
504
505
506 _ipw_write32(priv, IPW_AUTOINC_ADDR, aligned_addr);
507 for (; num >= 4; buf += 4, aligned_addr += 4, num -= 4)
508 *(u32 *) buf = _ipw_read32(priv, IPW_AUTOINC_DATA);
509
510
511 if (unlikely(num)) {
512 _ipw_write32(priv, IPW_INDIRECT_ADDR, aligned_addr);
513 for (i = 0; num > 0; i++, num--)
514 *buf++ = ipw_read8(priv, IPW_INDIRECT_DATA + i);
515 }
516}
517
518
519
520static void _ipw_write_indirect(struct ipw_priv *priv, u32 addr, u8 * buf,
521 int num)
522{
523 u32 aligned_addr = addr & IPW_INDIRECT_ADDR_MASK;
524 u32 dif_len = addr - aligned_addr;
525 u32 i;
526
527 IPW_DEBUG_IO("addr = %i, buf = %p, num = %i\n", addr, buf, num);
528
529 if (num <= 0) {
530 return;
531 }
532
533
534 if (unlikely(dif_len)) {
535 _ipw_write32(priv, IPW_INDIRECT_ADDR, aligned_addr);
536
537 for (i = dif_len; ((i < 4) && (num > 0)); i++, num--, buf++)
538 _ipw_write8(priv, IPW_INDIRECT_DATA + i, *buf);
539 aligned_addr += 4;
540 }
541
542
543 _ipw_write32(priv, IPW_AUTOINC_ADDR, aligned_addr);
544 for (; num >= 4; buf += 4, aligned_addr += 4, num -= 4)
545 _ipw_write32(priv, IPW_AUTOINC_DATA, *(u32 *) buf);
546
547
548 if (unlikely(num)) {
549 _ipw_write32(priv, IPW_INDIRECT_ADDR, aligned_addr);
550 for (i = 0; num > 0; i++, num--, buf++)
551 _ipw_write8(priv, IPW_INDIRECT_DATA + i, *buf);
552 }
553}
554
555
556
557static void ipw_write_direct(struct ipw_priv *priv, u32 addr, void *buf,
558 int num)
559{
560 memcpy_toio((priv->hw_base + addr), buf, num);
561}
562
563
564static inline void ipw_set_bit(struct ipw_priv *priv, u32 reg, u32 mask)
565{
566 ipw_write32(priv, reg, ipw_read32(priv, reg) | mask);
567}
568
569
570static inline void ipw_clear_bit(struct ipw_priv *priv, u32 reg, u32 mask)
571{
572 ipw_write32(priv, reg, ipw_read32(priv, reg) & ~mask);
573}
574
575static inline void __ipw_enable_interrupts(struct ipw_priv *priv)
576{
577 if (priv->status & STATUS_INT_ENABLED)
578 return;
579 priv->status |= STATUS_INT_ENABLED;
580 ipw_write32(priv, IPW_INTA_MASK_R, IPW_INTA_MASK_ALL);
581}
582
583static inline void __ipw_disable_interrupts(struct ipw_priv *priv)
584{
585 if (!(priv->status & STATUS_INT_ENABLED))
586 return;
587 priv->status &= ~STATUS_INT_ENABLED;
588 ipw_write32(priv, IPW_INTA_MASK_R, ~IPW_INTA_MASK_ALL);
589}
590
591static inline void ipw_enable_interrupts(struct ipw_priv *priv)
592{
593 unsigned long flags;
594
595 spin_lock_irqsave(&priv->irq_lock, flags);
596 __ipw_enable_interrupts(priv);
597 spin_unlock_irqrestore(&priv->irq_lock, flags);
598}
599
600static inline void ipw_disable_interrupts(struct ipw_priv *priv)
601{
602 unsigned long flags;
603
604 spin_lock_irqsave(&priv->irq_lock, flags);
605 __ipw_disable_interrupts(priv);
606 spin_unlock_irqrestore(&priv->irq_lock, flags);
607}
608
609static char *ipw_error_desc(u32 val)
610{
611 switch (val) {
612 case IPW_FW_ERROR_OK:
613 return "ERROR_OK";
614 case IPW_FW_ERROR_FAIL:
615 return "ERROR_FAIL";
616 case IPW_FW_ERROR_MEMORY_UNDERFLOW:
617 return "MEMORY_UNDERFLOW";
618 case IPW_FW_ERROR_MEMORY_OVERFLOW:
619 return "MEMORY_OVERFLOW";
620 case IPW_FW_ERROR_BAD_PARAM:
621 return "BAD_PARAM";
622 case IPW_FW_ERROR_BAD_CHECKSUM:
623 return "BAD_CHECKSUM";
624 case IPW_FW_ERROR_NMI_INTERRUPT:
625 return "NMI_INTERRUPT";
626 case IPW_FW_ERROR_BAD_DATABASE:
627 return "BAD_DATABASE";
628 case IPW_FW_ERROR_ALLOC_FAIL:
629 return "ALLOC_FAIL";
630 case IPW_FW_ERROR_DMA_UNDERRUN:
631 return "DMA_UNDERRUN";
632 case IPW_FW_ERROR_DMA_STATUS:
633 return "DMA_STATUS";
634 case IPW_FW_ERROR_DINO_ERROR:
635 return "DINO_ERROR";
636 case IPW_FW_ERROR_EEPROM_ERROR:
637 return "EEPROM_ERROR";
638 case IPW_FW_ERROR_SYSASSERT:
639 return "SYSASSERT";
640 case IPW_FW_ERROR_FATAL_ERROR:
641 return "FATAL_ERROR";
642 default:
643 return "UNKNOWN_ERROR";
644 }
645}
646
647static void ipw_dump_error_log(struct ipw_priv *priv,
648 struct ipw_fw_error *error)
649{
650 u32 i;
651
652 if (!error) {
653 IPW_ERROR("Error allocating and capturing error log. "
654 "Nothing to dump.\n");
655 return;
656 }
657
658 IPW_ERROR("Start IPW Error Log Dump:\n");
659 IPW_ERROR("Status: 0x%08X, Config: %08X\n",
660 error->status, error->config);
661
662 for (i = 0; i < error->elem_len; i++)
663 IPW_ERROR("%s %i 0x%08x 0x%08x 0x%08x 0x%08x 0x%08x\n",
664 ipw_error_desc(error->elem[i].desc),
665 error->elem[i].time,
666 error->elem[i].blink1,
667 error->elem[i].blink2,
668 error->elem[i].link1,
669 error->elem[i].link2, error->elem[i].data);
670 for (i = 0; i < error->log_len; i++)
671 IPW_ERROR("%i\t0x%08x\t%i\n",
672 error->log[i].time,
673 error->log[i].data, error->log[i].event);
674}
675
676static inline int ipw_is_init(struct ipw_priv *priv)
677{
678 return (priv->status & STATUS_INIT) ? 1 : 0;
679}
680
681static int ipw_get_ordinal(struct ipw_priv *priv, u32 ord, void *val, u32 * len)
682{
683 u32 addr, field_info, field_len, field_count, total_len;
684
685 IPW_DEBUG_ORD("ordinal = %i\n", ord);
686
687 if (!priv || !val || !len) {
688 IPW_DEBUG_ORD("Invalid argument\n");
689 return -EINVAL;
690 }
691
692
693 if (!priv->table0_addr || !priv->table1_addr || !priv->table2_addr) {
694 IPW_DEBUG_ORD("Access ordinals before initialization\n");
695 return -EINVAL;
696 }
697
698 switch (IPW_ORD_TABLE_ID_MASK & ord) {
699 case IPW_ORD_TABLE_0_MASK:
700
701
702
703
704
705
706
707
708 ord &= IPW_ORD_TABLE_VALUE_MASK;
709
710
711 if (ord > priv->table0_len) {
712 IPW_DEBUG_ORD("ordinal value (%i) longer then "
713 "max (%i)\n", ord, priv->table0_len);
714 return -EINVAL;
715 }
716
717
718 if (*len < sizeof(u32)) {
719 IPW_DEBUG_ORD("ordinal buffer length too small, "
720 "need %zd\n", sizeof(u32));
721 return -EINVAL;
722 }
723
724 IPW_DEBUG_ORD("Reading TABLE0[%i] from offset 0x%08x\n",
725 ord, priv->table0_addr + (ord << 2));
726
727 *len = sizeof(u32);
728 ord <<= 2;
729 *((u32 *) val) = ipw_read32(priv, priv->table0_addr + ord);
730 break;
731
732 case IPW_ORD_TABLE_1_MASK:
733
734
735
736
737
738
739
740
741
742 ord &= IPW_ORD_TABLE_VALUE_MASK;
743
744
745 if (ord > priv->table1_len) {
746 IPW_DEBUG_ORD("ordinal value too long\n");
747 return -EINVAL;
748 }
749
750
751 if (*len < sizeof(u32)) {
752 IPW_DEBUG_ORD("ordinal buffer length too small, "
753 "need %zd\n", sizeof(u32));
754 return -EINVAL;
755 }
756
757 *((u32 *) val) =
758 ipw_read_reg32(priv, (priv->table1_addr + (ord << 2)));
759 *len = sizeof(u32);
760 break;
761
762 case IPW_ORD_TABLE_2_MASK:
763
764
765
766
767
768
769
770
771
772
773 ord &= IPW_ORD_TABLE_VALUE_MASK;
774
775
776 if (ord > priv->table2_len) {
777 IPW_DEBUG_ORD("ordinal value too long\n");
778 return -EINVAL;
779 }
780
781
782 addr = ipw_read_reg32(priv, priv->table2_addr + (ord << 3));
783
784
785
786 field_info =
787 ipw_read_reg32(priv,
788 priv->table2_addr + (ord << 3) +
789 sizeof(u32));
790
791
792 field_len = *((u16 *) & field_info);
793
794
795 field_count = *(((u16 *) & field_info) + 1);
796
797
798 total_len = field_len * field_count;
799 if (total_len > *len) {
800 *len = total_len;
801 return -EINVAL;
802 }
803
804 *len = total_len;
805 if (!total_len)
806 return 0;
807
808 IPW_DEBUG_ORD("addr = 0x%08x, total_len = %i, "
809 "field_info = 0x%08x\n",
810 addr, total_len, field_info);
811 ipw_read_indirect(priv, addr, val, total_len);
812 break;
813
814 default:
815 IPW_DEBUG_ORD("Invalid ordinal!\n");
816 return -EINVAL;
817
818 }
819
820 return 0;
821}
822
823static void ipw_init_ordinals(struct ipw_priv *priv)
824{
825 priv->table0_addr = IPW_ORDINALS_TABLE_LOWER;
826 priv->table0_len = ipw_read32(priv, priv->table0_addr);
827
828 IPW_DEBUG_ORD("table 0 offset at 0x%08x, len = %i\n",
829 priv->table0_addr, priv->table0_len);
830
831 priv->table1_addr = ipw_read32(priv, IPW_ORDINALS_TABLE_1);
832 priv->table1_len = ipw_read_reg32(priv, priv->table1_addr);
833
834 IPW_DEBUG_ORD("table 1 offset at 0x%08x, len = %i\n",
835 priv->table1_addr, priv->table1_len);
836
837 priv->table2_addr = ipw_read32(priv, IPW_ORDINALS_TABLE_2);
838 priv->table2_len = ipw_read_reg32(priv, priv->table2_addr);
839 priv->table2_len &= 0x0000ffff;
840
841 IPW_DEBUG_ORD("table 2 offset at 0x%08x, len = %i\n",
842 priv->table2_addr, priv->table2_len);
843
844}
845
846static u32 ipw_register_toggle(u32 reg)
847{
848 reg &= ~IPW_START_STANDBY;
849 if (reg & IPW_GATE_ODMA)
850 reg &= ~IPW_GATE_ODMA;
851 if (reg & IPW_GATE_IDMA)
852 reg &= ~IPW_GATE_IDMA;
853 if (reg & IPW_GATE_ADMA)
854 reg &= ~IPW_GATE_ADMA;
855 return reg;
856}
857
858
859
860
861
862
863
864
865
866
867#define LD_TIME_LINK_ON msecs_to_jiffies(300)
868#define LD_TIME_LINK_OFF msecs_to_jiffies(2700)
869#define LD_TIME_ACT_ON msecs_to_jiffies(250)
870
871static void ipw_led_link_on(struct ipw_priv *priv)
872{
873 unsigned long flags;
874 u32 led;
875
876
877
878 if (priv->config & CFG_NO_LED || priv->nic_type == EEPROM_NIC_TYPE_1)
879 return;
880
881 spin_lock_irqsave(&priv->lock, flags);
882
883 if (!(priv->status & STATUS_RF_KILL_MASK) &&
884 !(priv->status & STATUS_LED_LINK_ON)) {
885 IPW_DEBUG_LED("Link LED On\n");
886 led = ipw_read_reg32(priv, IPW_EVENT_REG);
887 led |= priv->led_association_on;
888
889 led = ipw_register_toggle(led);
890
891 IPW_DEBUG_LED("Reg: 0x%08X\n", led);
892 ipw_write_reg32(priv, IPW_EVENT_REG, led);
893
894 priv->status |= STATUS_LED_LINK_ON;
895
896
897 if (!(priv->status & STATUS_ASSOCIATED))
898 schedule_delayed_work(&priv->led_link_off,
899 LD_TIME_LINK_ON);
900 }
901
902 spin_unlock_irqrestore(&priv->lock, flags);
903}
904
905static void ipw_bg_led_link_on(struct work_struct *work)
906{
907 struct ipw_priv *priv =
908 container_of(work, struct ipw_priv, led_link_on.work);
909 mutex_lock(&priv->mutex);
910 ipw_led_link_on(priv);
911 mutex_unlock(&priv->mutex);
912}
913
914static void ipw_led_link_off(struct ipw_priv *priv)
915{
916 unsigned long flags;
917 u32 led;
918
919
920
921 if (priv->config & CFG_NO_LED || priv->nic_type == EEPROM_NIC_TYPE_1)
922 return;
923
924 spin_lock_irqsave(&priv->lock, flags);
925
926 if (priv->status & STATUS_LED_LINK_ON) {
927 led = ipw_read_reg32(priv, IPW_EVENT_REG);
928 led &= priv->led_association_off;
929 led = ipw_register_toggle(led);
930
931 IPW_DEBUG_LED("Reg: 0x%08X\n", led);
932 ipw_write_reg32(priv, IPW_EVENT_REG, led);
933
934 IPW_DEBUG_LED("Link LED Off\n");
935
936 priv->status &= ~STATUS_LED_LINK_ON;
937
938
939
940 if (!(priv->status & STATUS_RF_KILL_MASK) &&
941 !(priv->status & STATUS_ASSOCIATED))
942 schedule_delayed_work(&priv->led_link_on,
943 LD_TIME_LINK_OFF);
944
945 }
946
947 spin_unlock_irqrestore(&priv->lock, flags);
948}
949
950static void ipw_bg_led_link_off(struct work_struct *work)
951{
952 struct ipw_priv *priv =
953 container_of(work, struct ipw_priv, led_link_off.work);
954 mutex_lock(&priv->mutex);
955 ipw_led_link_off(priv);
956 mutex_unlock(&priv->mutex);
957}
958
959static void __ipw_led_activity_on(struct ipw_priv *priv)
960{
961 u32 led;
962
963 if (priv->config & CFG_NO_LED)
964 return;
965
966 if (priv->status & STATUS_RF_KILL_MASK)
967 return;
968
969 if (!(priv->status & STATUS_LED_ACT_ON)) {
970 led = ipw_read_reg32(priv, IPW_EVENT_REG);
971 led |= priv->led_activity_on;
972
973 led = ipw_register_toggle(led);
974
975 IPW_DEBUG_LED("Reg: 0x%08X\n", led);
976 ipw_write_reg32(priv, IPW_EVENT_REG, led);
977
978 IPW_DEBUG_LED("Activity LED On\n");
979
980 priv->status |= STATUS_LED_ACT_ON;
981
982 cancel_delayed_work(&priv->led_act_off);
983 schedule_delayed_work(&priv->led_act_off, LD_TIME_ACT_ON);
984 } else {
985
986 cancel_delayed_work(&priv->led_act_off);
987 schedule_delayed_work(&priv->led_act_off, LD_TIME_ACT_ON);
988 }
989}
990
991#if 0
992void ipw_led_activity_on(struct ipw_priv *priv)
993{
994 unsigned long flags;
995 spin_lock_irqsave(&priv->lock, flags);
996 __ipw_led_activity_on(priv);
997 spin_unlock_irqrestore(&priv->lock, flags);
998}
999#endif
1000
1001static void ipw_led_activity_off(struct ipw_priv *priv)
1002{
1003 unsigned long flags;
1004 u32 led;
1005
1006 if (priv->config & CFG_NO_LED)
1007 return;
1008
1009 spin_lock_irqsave(&priv->lock, flags);
1010
1011 if (priv->status & STATUS_LED_ACT_ON) {
1012 led = ipw_read_reg32(priv, IPW_EVENT_REG);
1013 led &= priv->led_activity_off;
1014
1015 led = ipw_register_toggle(led);
1016
1017 IPW_DEBUG_LED("Reg: 0x%08X\n", led);
1018 ipw_write_reg32(priv, IPW_EVENT_REG, led);
1019
1020 IPW_DEBUG_LED("Activity LED Off\n");
1021
1022 priv->status &= ~STATUS_LED_ACT_ON;
1023 }
1024
1025 spin_unlock_irqrestore(&priv->lock, flags);
1026}
1027
1028static void ipw_bg_led_activity_off(struct work_struct *work)
1029{
1030 struct ipw_priv *priv =
1031 container_of(work, struct ipw_priv, led_act_off.work);
1032 mutex_lock(&priv->mutex);
1033 ipw_led_activity_off(priv);
1034 mutex_unlock(&priv->mutex);
1035}
1036
1037static void ipw_led_band_on(struct ipw_priv *priv)
1038{
1039 unsigned long flags;
1040 u32 led;
1041
1042
1043 if (priv->config & CFG_NO_LED ||
1044 priv->nic_type != EEPROM_NIC_TYPE_1 || !priv->assoc_network)
1045 return;
1046
1047 spin_lock_irqsave(&priv->lock, flags);
1048
1049 led = ipw_read_reg32(priv, IPW_EVENT_REG);
1050 if (priv->assoc_network->mode == IEEE_A) {
1051 led |= priv->led_ofdm_on;
1052 led &= priv->led_association_off;
1053 IPW_DEBUG_LED("Mode LED On: 802.11a\n");
1054 } else if (priv->assoc_network->mode == IEEE_G) {
1055 led |= priv->led_ofdm_on;
1056 led |= priv->led_association_on;
1057 IPW_DEBUG_LED("Mode LED On: 802.11g\n");
1058 } else {
1059 led &= priv->led_ofdm_off;
1060 led |= priv->led_association_on;
1061 IPW_DEBUG_LED("Mode LED On: 802.11b\n");
1062 }
1063
1064 led = ipw_register_toggle(led);
1065
1066 IPW_DEBUG_LED("Reg: 0x%08X\n", led);
1067 ipw_write_reg32(priv, IPW_EVENT_REG, led);
1068
1069 spin_unlock_irqrestore(&priv->lock, flags);
1070}
1071
1072static void ipw_led_band_off(struct ipw_priv *priv)
1073{
1074 unsigned long flags;
1075 u32 led;
1076
1077
1078 if (priv->config & CFG_NO_LED || priv->nic_type != EEPROM_NIC_TYPE_1)
1079 return;
1080
1081 spin_lock_irqsave(&priv->lock, flags);
1082
1083 led = ipw_read_reg32(priv, IPW_EVENT_REG);
1084 led &= priv->led_ofdm_off;
1085 led &= priv->led_association_off;
1086
1087 led = ipw_register_toggle(led);
1088
1089 IPW_DEBUG_LED("Reg: 0x%08X\n", led);
1090 ipw_write_reg32(priv, IPW_EVENT_REG, led);
1091
1092 spin_unlock_irqrestore(&priv->lock, flags);
1093}
1094
1095static void ipw_led_radio_on(struct ipw_priv *priv)
1096{
1097 ipw_led_link_on(priv);
1098}
1099
1100static void ipw_led_radio_off(struct ipw_priv *priv)
1101{
1102 ipw_led_activity_off(priv);
1103 ipw_led_link_off(priv);
1104}
1105
1106static void ipw_led_link_up(struct ipw_priv *priv)
1107{
1108
1109 ipw_led_link_on(priv);
1110}
1111
1112static void ipw_led_link_down(struct ipw_priv *priv)
1113{
1114 ipw_led_activity_off(priv);
1115 ipw_led_link_off(priv);
1116
1117 if (priv->status & STATUS_RF_KILL_MASK)
1118 ipw_led_radio_off(priv);
1119}
1120
1121static void ipw_led_init(struct ipw_priv *priv)
1122{
1123 priv->nic_type = priv->eeprom[EEPROM_NIC_TYPE];
1124
1125
1126 priv->led_activity_on = IPW_ACTIVITY_LED;
1127 priv->led_activity_off = ~(IPW_ACTIVITY_LED);
1128
1129 priv->led_association_on = IPW_ASSOCIATED_LED;
1130 priv->led_association_off = ~(IPW_ASSOCIATED_LED);
1131
1132
1133 priv->led_ofdm_on = IPW_OFDM_LED;
1134 priv->led_ofdm_off = ~(IPW_OFDM_LED);
1135
1136 switch (priv->nic_type) {
1137 case EEPROM_NIC_TYPE_1:
1138
1139 priv->led_activity_on = IPW_ASSOCIATED_LED;
1140 priv->led_activity_off = ~(IPW_ASSOCIATED_LED);
1141 priv->led_association_on = IPW_ACTIVITY_LED;
1142 priv->led_association_off = ~(IPW_ACTIVITY_LED);
1143
1144 if (!(priv->config & CFG_NO_LED))
1145 ipw_led_band_on(priv);
1146
1147
1148
1149 return;
1150
1151 case EEPROM_NIC_TYPE_3:
1152 case EEPROM_NIC_TYPE_2:
1153 case EEPROM_NIC_TYPE_4:
1154 case EEPROM_NIC_TYPE_0:
1155 break;
1156
1157 default:
1158 IPW_DEBUG_INFO("Unknown NIC type from EEPROM: %d\n",
1159 priv->nic_type);
1160 priv->nic_type = EEPROM_NIC_TYPE_0;
1161 break;
1162 }
1163
1164 if (!(priv->config & CFG_NO_LED)) {
1165 if (priv->status & STATUS_ASSOCIATED)
1166 ipw_led_link_on(priv);
1167 else
1168 ipw_led_link_off(priv);
1169 }
1170}
1171
1172static void ipw_led_shutdown(struct ipw_priv *priv)
1173{
1174 ipw_led_activity_off(priv);
1175 ipw_led_link_off(priv);
1176 ipw_led_band_off(priv);
1177 cancel_delayed_work(&priv->led_link_on);
1178 cancel_delayed_work(&priv->led_link_off);
1179 cancel_delayed_work(&priv->led_act_off);
1180}
1181
1182
1183
1184
1185
1186
1187
1188
1189static ssize_t show_debug_level(struct device_driver *d, char *buf)
1190{
1191 return sprintf(buf, "0x%08X\n", ipw_debug_level);
1192}
1193
1194static ssize_t store_debug_level(struct device_driver *d, const char *buf,
1195 size_t count)
1196{
1197 char *p = (char *)buf;
1198 u32 val;
1199
1200 if (p[1] == 'x' || p[1] == 'X' || p[0] == 'x' || p[0] == 'X') {
1201 p++;
1202 if (p[0] == 'x' || p[0] == 'X')
1203 p++;
1204 val = simple_strtoul(p, &p, 16);
1205 } else
1206 val = simple_strtoul(p, &p, 10);
1207 if (p == buf)
1208 printk(KERN_INFO DRV_NAME
1209 ": %s is not in hex or decimal form.\n", buf);
1210 else
1211 ipw_debug_level = val;
1212
1213 return strnlen(buf, count);
1214}
1215
1216static DRIVER_ATTR(debug_level, S_IWUSR | S_IRUGO,
1217 show_debug_level, store_debug_level);
1218
1219static inline u32 ipw_get_event_log_len(struct ipw_priv *priv)
1220{
1221
1222 return ipw_read_reg32(priv, ipw_read32(priv, IPW_EVENT_LOG));
1223}
1224
1225static void ipw_capture_event_log(struct ipw_priv *priv,
1226 u32 log_len, struct ipw_event *log)
1227{
1228 u32 base;
1229
1230 if (log_len) {
1231 base = ipw_read32(priv, IPW_EVENT_LOG);
1232 ipw_read_indirect(priv, base + sizeof(base) + sizeof(u32),
1233 (u8 *) log, sizeof(*log) * log_len);
1234 }
1235}
1236
1237static struct ipw_fw_error *ipw_alloc_error_log(struct ipw_priv *priv)
1238{
1239 struct ipw_fw_error *error;
1240 u32 log_len = ipw_get_event_log_len(priv);
1241 u32 base = ipw_read32(priv, IPW_ERROR_LOG);
1242 u32 elem_len = ipw_read_reg32(priv, base);
1243
1244 error = kmalloc(sizeof(*error) +
1245 sizeof(*error->elem) * elem_len +
1246 sizeof(*error->log) * log_len, GFP_ATOMIC);
1247 if (!error) {
1248 IPW_ERROR("Memory allocation for firmware error log "
1249 "failed.\n");
1250 return NULL;
1251 }
1252 error->jiffies = jiffies;
1253 error->status = priv->status;
1254 error->config = priv->config;
1255 error->elem_len = elem_len;
1256 error->log_len = log_len;
1257 error->elem = (struct ipw_error_elem *)error->payload;
1258 error->log = (struct ipw_event *)(error->elem + elem_len);
1259
1260 ipw_capture_event_log(priv, log_len, error->log);
1261
1262 if (elem_len)
1263 ipw_read_indirect(priv, base + sizeof(base), (u8 *) error->elem,
1264 sizeof(*error->elem) * elem_len);
1265
1266 return error;
1267}
1268
1269static ssize_t show_event_log(struct device *d,
1270 struct device_attribute *attr, char *buf)
1271{
1272 struct ipw_priv *priv = dev_get_drvdata(d);
1273 u32 log_len = ipw_get_event_log_len(priv);
1274 u32 log_size;
1275 struct ipw_event *log;
1276 u32 len = 0, i;
1277
1278
1279 log_size = PAGE_SIZE / sizeof(*log) > log_len ?
1280 sizeof(*log) * log_len : PAGE_SIZE;
1281 log = kzalloc(log_size, GFP_KERNEL);
1282 if (!log) {
1283 IPW_ERROR("Unable to allocate memory for log\n");
1284 return 0;
1285 }
1286 log_len = log_size / sizeof(*log);
1287 ipw_capture_event_log(priv, log_len, log);
1288
1289 len += snprintf(buf + len, PAGE_SIZE - len, "%08X", log_len);
1290 for (i = 0; i < log_len; i++)
1291 len += snprintf(buf + len, PAGE_SIZE - len,
1292 "\n%08X%08X%08X",
1293 log[i].time, log[i].event, log[i].data);
1294 len += snprintf(buf + len, PAGE_SIZE - len, "\n");
1295 kfree(log);
1296 return len;
1297}
1298
1299static DEVICE_ATTR(event_log, S_IRUGO, show_event_log, NULL);
1300
1301static ssize_t show_error(struct device *d,
1302 struct device_attribute *attr, char *buf)
1303{
1304 struct ipw_priv *priv = dev_get_drvdata(d);
1305 u32 len = 0, i;
1306 if (!priv->error)
1307 return 0;
1308 len += snprintf(buf + len, PAGE_SIZE - len,
1309 "%08lX%08X%08X%08X",
1310 priv->error->jiffies,
1311 priv->error->status,
1312 priv->error->config, priv->error->elem_len);
1313 for (i = 0; i < priv->error->elem_len; i++)
1314 len += snprintf(buf + len, PAGE_SIZE - len,
1315 "\n%08X%08X%08X%08X%08X%08X%08X",
1316 priv->error->elem[i].time,
1317 priv->error->elem[i].desc,
1318 priv->error->elem[i].blink1,
1319 priv->error->elem[i].blink2,
1320 priv->error->elem[i].link1,
1321 priv->error->elem[i].link2,
1322 priv->error->elem[i].data);
1323
1324 len += snprintf(buf + len, PAGE_SIZE - len,
1325 "\n%08X", priv->error->log_len);
1326 for (i = 0; i < priv->error->log_len; i++)
1327 len += snprintf(buf + len, PAGE_SIZE - len,
1328 "\n%08X%08X%08X",
1329 priv->error->log[i].time,
1330 priv->error->log[i].event,
1331 priv->error->log[i].data);
1332 len += snprintf(buf + len, PAGE_SIZE - len, "\n");
1333 return len;
1334}
1335
1336static ssize_t clear_error(struct device *d,
1337 struct device_attribute *attr,
1338 const char *buf, size_t count)
1339{
1340 struct ipw_priv *priv = dev_get_drvdata(d);
1341
1342 kfree(priv->error);
1343 priv->error = NULL;
1344 return count;
1345}
1346
1347static DEVICE_ATTR(error, S_IRUGO | S_IWUSR, show_error, clear_error);
1348
1349static ssize_t show_cmd_log(struct device *d,
1350 struct device_attribute *attr, char *buf)
1351{
1352 struct ipw_priv *priv = dev_get_drvdata(d);
1353 u32 len = 0, i;
1354 if (!priv->cmdlog)
1355 return 0;
1356 for (i = (priv->cmdlog_pos + 1) % priv->cmdlog_len;
1357 (i != priv->cmdlog_pos) && (PAGE_SIZE - len);
1358 i = (i + 1) % priv->cmdlog_len) {
1359 len +=
1360 snprintf(buf + len, PAGE_SIZE - len,
1361 "\n%08lX%08X%08X%08X\n", priv->cmdlog[i].jiffies,
1362 priv->cmdlog[i].retcode, priv->cmdlog[i].cmd.cmd,
1363 priv->cmdlog[i].cmd.len);
1364 len +=
1365 snprintk_buf(buf + len, PAGE_SIZE - len,
1366 (u8 *) priv->cmdlog[i].cmd.param,
1367 priv->cmdlog[i].cmd.len);
1368 len += snprintf(buf + len, PAGE_SIZE - len, "\n");
1369 }
1370 len += snprintf(buf + len, PAGE_SIZE - len, "\n");
1371 return len;
1372}
1373
1374static DEVICE_ATTR(cmd_log, S_IRUGO, show_cmd_log, NULL);
1375
1376#ifdef CONFIG_IPW2200_PROMISCUOUS
1377static void ipw_prom_free(struct ipw_priv *priv);
1378static int ipw_prom_alloc(struct ipw_priv *priv);
1379static ssize_t store_rtap_iface(struct device *d,
1380 struct device_attribute *attr,
1381 const char *buf, size_t count)
1382{
1383 struct ipw_priv *priv = dev_get_drvdata(d);
1384 int rc = 0;
1385
1386 if (count < 1)
1387 return -EINVAL;
1388
1389 switch (buf[0]) {
1390 case '0':
1391 if (!rtap_iface)
1392 return count;
1393
1394 if (netif_running(priv->prom_net_dev)) {
1395 IPW_WARNING("Interface is up. Cannot unregister.\n");
1396 return count;
1397 }
1398
1399 ipw_prom_free(priv);
1400 rtap_iface = 0;
1401 break;
1402
1403 case '1':
1404 if (rtap_iface)
1405 return count;
1406
1407 rc = ipw_prom_alloc(priv);
1408 if (!rc)
1409 rtap_iface = 1;
1410 break;
1411
1412 default:
1413 return -EINVAL;
1414 }
1415
1416 if (rc) {
1417 IPW_ERROR("Failed to register promiscuous network "
1418 "device (error %d).\n", rc);
1419 }
1420
1421 return count;
1422}
1423
1424static ssize_t show_rtap_iface(struct device *d,
1425 struct device_attribute *attr,
1426 char *buf)
1427{
1428 struct ipw_priv *priv = dev_get_drvdata(d);
1429 if (rtap_iface)
1430 return sprintf(buf, "%s", priv->prom_net_dev->name);
1431 else {
1432 buf[0] = '-';
1433 buf[1] = '1';
1434 buf[2] = '\0';
1435 return 3;
1436 }
1437}
1438
1439static DEVICE_ATTR(rtap_iface, S_IWUSR | S_IRUSR, show_rtap_iface,
1440 store_rtap_iface);
1441
1442static ssize_t store_rtap_filter(struct device *d,
1443 struct device_attribute *attr,
1444 const char *buf, size_t count)
1445{
1446 struct ipw_priv *priv = dev_get_drvdata(d);
1447
1448 if (!priv->prom_priv) {
1449 IPW_ERROR("Attempting to set filter without "
1450 "rtap_iface enabled.\n");
1451 return -EPERM;
1452 }
1453
1454 priv->prom_priv->filter = simple_strtol(buf, NULL, 0);
1455
1456 IPW_DEBUG_INFO("Setting rtap filter to " BIT_FMT16 "\n",
1457 BIT_ARG16(priv->prom_priv->filter));
1458
1459 return count;
1460}
1461
1462static ssize_t show_rtap_filter(struct device *d,
1463 struct device_attribute *attr,
1464 char *buf)
1465{
1466 struct ipw_priv *priv = dev_get_drvdata(d);
1467 return sprintf(buf, "0x%04X",
1468 priv->prom_priv ? priv->prom_priv->filter : 0);
1469}
1470
1471static DEVICE_ATTR(rtap_filter, S_IWUSR | S_IRUSR, show_rtap_filter,
1472 store_rtap_filter);
1473#endif
1474
1475static ssize_t show_scan_age(struct device *d, struct device_attribute *attr,
1476 char *buf)
1477{
1478 struct ipw_priv *priv = dev_get_drvdata(d);
1479 return sprintf(buf, "%d\n", priv->ieee->scan_age);
1480}
1481
1482static ssize_t store_scan_age(struct device *d, struct device_attribute *attr,
1483 const char *buf, size_t count)
1484{
1485 struct ipw_priv *priv = dev_get_drvdata(d);
1486 struct net_device *dev = priv->net_dev;
1487 char buffer[] = "00000000";
1488 unsigned long len =
1489 (sizeof(buffer) - 1) > count ? count : sizeof(buffer) - 1;
1490 unsigned long val;
1491 char *p = buffer;
1492
1493 IPW_DEBUG_INFO("enter\n");
1494
1495 strncpy(buffer, buf, len);
1496 buffer[len] = 0;
1497
1498 if (p[1] == 'x' || p[1] == 'X' || p[0] == 'x' || p[0] == 'X') {
1499 p++;
1500 if (p[0] == 'x' || p[0] == 'X')
1501 p++;
1502 val = simple_strtoul(p, &p, 16);
1503 } else
1504 val = simple_strtoul(p, &p, 10);
1505 if (p == buffer) {
1506 IPW_DEBUG_INFO("%s: user supplied invalid value.\n", dev->name);
1507 } else {
1508 priv->ieee->scan_age = val;
1509 IPW_DEBUG_INFO("set scan_age = %u\n", priv->ieee->scan_age);
1510 }
1511
1512 IPW_DEBUG_INFO("exit\n");
1513 return len;
1514}
1515
1516static DEVICE_ATTR(scan_age, S_IWUSR | S_IRUGO, show_scan_age, store_scan_age);
1517
1518static ssize_t show_led(struct device *d, struct device_attribute *attr,
1519 char *buf)
1520{
1521 struct ipw_priv *priv = dev_get_drvdata(d);
1522 return sprintf(buf, "%d\n", (priv->config & CFG_NO_LED) ? 0 : 1);
1523}
1524
1525static ssize_t store_led(struct device *d, struct device_attribute *attr,
1526 const char *buf, size_t count)
1527{
1528 struct ipw_priv *priv = dev_get_drvdata(d);
1529
1530 IPW_DEBUG_INFO("enter\n");
1531
1532 if (count == 0)
1533 return 0;
1534
1535 if (*buf == 0) {
1536 IPW_DEBUG_LED("Disabling LED control.\n");
1537 priv->config |= CFG_NO_LED;
1538 ipw_led_shutdown(priv);
1539 } else {
1540 IPW_DEBUG_LED("Enabling LED control.\n");
1541 priv->config &= ~CFG_NO_LED;
1542 ipw_led_init(priv);
1543 }
1544
1545 IPW_DEBUG_INFO("exit\n");
1546 return count;
1547}
1548
1549static DEVICE_ATTR(led, S_IWUSR | S_IRUGO, show_led, store_led);
1550
1551static ssize_t show_status(struct device *d,
1552 struct device_attribute *attr, char *buf)
1553{
1554 struct ipw_priv *p = dev_get_drvdata(d);
1555 return sprintf(buf, "0x%08x\n", (int)p->status);
1556}
1557
1558static DEVICE_ATTR(status, S_IRUGO, show_status, NULL);
1559
1560static ssize_t show_cfg(struct device *d, struct device_attribute *attr,
1561 char *buf)
1562{
1563 struct ipw_priv *p = dev_get_drvdata(d);
1564 return sprintf(buf, "0x%08x\n", (int)p->config);
1565}
1566
1567static DEVICE_ATTR(cfg, S_IRUGO, show_cfg, NULL);
1568
1569static ssize_t show_nic_type(struct device *d,
1570 struct device_attribute *attr, char *buf)
1571{
1572 struct ipw_priv *priv = dev_get_drvdata(d);
1573 return sprintf(buf, "TYPE: %d\n", priv->nic_type);
1574}
1575
1576static DEVICE_ATTR(nic_type, S_IRUGO, show_nic_type, NULL);
1577
1578static ssize_t show_ucode_version(struct device *d,
1579 struct device_attribute *attr, char *buf)
1580{
1581 u32 len = sizeof(u32), tmp = 0;
1582 struct ipw_priv *p = dev_get_drvdata(d);
1583
1584 if (ipw_get_ordinal(p, IPW_ORD_STAT_UCODE_VERSION, &tmp, &len))
1585 return 0;
1586
1587 return sprintf(buf, "0x%08x\n", tmp);
1588}
1589
1590static DEVICE_ATTR(ucode_version, S_IWUSR | S_IRUGO, show_ucode_version, NULL);
1591
1592static ssize_t show_rtc(struct device *d, struct device_attribute *attr,
1593 char *buf)
1594{
1595 u32 len = sizeof(u32), tmp = 0;
1596 struct ipw_priv *p = dev_get_drvdata(d);
1597
1598 if (ipw_get_ordinal(p, IPW_ORD_STAT_RTC, &tmp, &len))
1599 return 0;
1600
1601 return sprintf(buf, "0x%08x\n", tmp);
1602}
1603
1604static DEVICE_ATTR(rtc, S_IWUSR | S_IRUGO, show_rtc, NULL);
1605
1606
1607
1608
1609
1610static ssize_t show_eeprom_delay(struct device *d,
1611 struct device_attribute *attr, char *buf)
1612{
1613 struct ipw_priv *p = dev_get_drvdata(d);
1614 int n = p->eeprom_delay;
1615 return sprintf(buf, "%i\n", n);
1616}
1617static ssize_t store_eeprom_delay(struct device *d,
1618 struct device_attribute *attr,
1619 const char *buf, size_t count)
1620{
1621 struct ipw_priv *p = dev_get_drvdata(d);
1622 sscanf(buf, "%i", &p->eeprom_delay);
1623 return strnlen(buf, count);
1624}
1625
1626static DEVICE_ATTR(eeprom_delay, S_IWUSR | S_IRUGO,
1627 show_eeprom_delay, store_eeprom_delay);
1628
1629static ssize_t show_command_event_reg(struct device *d,
1630 struct device_attribute *attr, char *buf)
1631{
1632 u32 reg = 0;
1633 struct ipw_priv *p = dev_get_drvdata(d);
1634
1635 reg = ipw_read_reg32(p, IPW_INTERNAL_CMD_EVENT);
1636 return sprintf(buf, "0x%08x\n", reg);
1637}
1638static ssize_t store_command_event_reg(struct device *d,
1639 struct device_attribute *attr,
1640 const char *buf, size_t count)
1641{
1642 u32 reg;
1643 struct ipw_priv *p = dev_get_drvdata(d);
1644
1645 sscanf(buf, "%x", ®);
1646 ipw_write_reg32(p, IPW_INTERNAL_CMD_EVENT, reg);
1647 return strnlen(buf, count);
1648}
1649
1650static DEVICE_ATTR(command_event_reg, S_IWUSR | S_IRUGO,
1651 show_command_event_reg, store_command_event_reg);
1652
1653static ssize_t show_mem_gpio_reg(struct device *d,
1654 struct device_attribute *attr, char *buf)
1655{
1656 u32 reg = 0;
1657 struct ipw_priv *p = dev_get_drvdata(d);
1658
1659 reg = ipw_read_reg32(p, 0x301100);
1660 return sprintf(buf, "0x%08x\n", reg);
1661}
1662static ssize_t store_mem_gpio_reg(struct device *d,
1663 struct device_attribute *attr,
1664 const char *buf, size_t count)
1665{
1666 u32 reg;
1667 struct ipw_priv *p = dev_get_drvdata(d);
1668
1669 sscanf(buf, "%x", ®);
1670 ipw_write_reg32(p, 0x301100, reg);
1671 return strnlen(buf, count);
1672}
1673
1674static DEVICE_ATTR(mem_gpio_reg, S_IWUSR | S_IRUGO,
1675 show_mem_gpio_reg, store_mem_gpio_reg);
1676
1677static ssize_t show_indirect_dword(struct device *d,
1678 struct device_attribute *attr, char *buf)
1679{
1680 u32 reg = 0;
1681 struct ipw_priv *priv = dev_get_drvdata(d);
1682
1683 if (priv->status & STATUS_INDIRECT_DWORD)
1684 reg = ipw_read_reg32(priv, priv->indirect_dword);
1685 else
1686 reg = 0;
1687
1688 return sprintf(buf, "0x%08x\n", reg);
1689}
1690static ssize_t store_indirect_dword(struct device *d,
1691 struct device_attribute *attr,
1692 const char *buf, size_t count)
1693{
1694 struct ipw_priv *priv = dev_get_drvdata(d);
1695
1696 sscanf(buf, "%x", &priv->indirect_dword);
1697 priv->status |= STATUS_INDIRECT_DWORD;
1698 return strnlen(buf, count);
1699}
1700
1701static DEVICE_ATTR(indirect_dword, S_IWUSR | S_IRUGO,
1702 show_indirect_dword, store_indirect_dword);
1703
1704static ssize_t show_indirect_byte(struct device *d,
1705 struct device_attribute *attr, char *buf)
1706{
1707 u8 reg = 0;
1708 struct ipw_priv *priv = dev_get_drvdata(d);
1709
1710 if (priv->status & STATUS_INDIRECT_BYTE)
1711 reg = ipw_read_reg8(priv, priv->indirect_byte);
1712 else
1713 reg = 0;
1714
1715 return sprintf(buf, "0x%02x\n", reg);
1716}
1717static ssize_t store_indirect_byte(struct device *d,
1718 struct device_attribute *attr,
1719 const char *buf, size_t count)
1720{
1721 struct ipw_priv *priv = dev_get_drvdata(d);
1722
1723 sscanf(buf, "%x", &priv->indirect_byte);
1724 priv->status |= STATUS_INDIRECT_BYTE;
1725 return strnlen(buf, count);
1726}
1727
1728static DEVICE_ATTR(indirect_byte, S_IWUSR | S_IRUGO,
1729 show_indirect_byte, store_indirect_byte);
1730
1731static ssize_t show_direct_dword(struct device *d,
1732 struct device_attribute *attr, char *buf)
1733{
1734 u32 reg = 0;
1735 struct ipw_priv *priv = dev_get_drvdata(d);
1736
1737 if (priv->status & STATUS_DIRECT_DWORD)
1738 reg = ipw_read32(priv, priv->direct_dword);
1739 else
1740 reg = 0;
1741
1742 return sprintf(buf, "0x%08x\n", reg);
1743}
1744static ssize_t store_direct_dword(struct device *d,
1745 struct device_attribute *attr,
1746 const char *buf, size_t count)
1747{
1748 struct ipw_priv *priv = dev_get_drvdata(d);
1749
1750 sscanf(buf, "%x", &priv->direct_dword);
1751 priv->status |= STATUS_DIRECT_DWORD;
1752 return strnlen(buf, count);
1753}
1754
1755static DEVICE_ATTR(direct_dword, S_IWUSR | S_IRUGO,
1756 show_direct_dword, store_direct_dword);
1757
1758static int rf_kill_active(struct ipw_priv *priv)
1759{
1760 if (0 == (ipw_read32(priv, 0x30) & 0x10000)) {
1761 priv->status |= STATUS_RF_KILL_HW;
1762 wiphy_rfkill_set_hw_state(priv->ieee->wdev.wiphy, true);
1763 } else {
1764 priv->status &= ~STATUS_RF_KILL_HW;
1765 wiphy_rfkill_set_hw_state(priv->ieee->wdev.wiphy, false);
1766 }
1767
1768 return (priv->status & STATUS_RF_KILL_HW) ? 1 : 0;
1769}
1770
1771static ssize_t show_rf_kill(struct device *d, struct device_attribute *attr,
1772 char *buf)
1773{
1774
1775
1776
1777
1778 struct ipw_priv *priv = dev_get_drvdata(d);
1779 int val = ((priv->status & STATUS_RF_KILL_SW) ? 0x1 : 0x0) |
1780 (rf_kill_active(priv) ? 0x2 : 0x0);
1781 return sprintf(buf, "%i\n", val);
1782}
1783
1784static int ipw_radio_kill_sw(struct ipw_priv *priv, int disable_radio)
1785{
1786 if ((disable_radio ? 1 : 0) ==
1787 ((priv->status & STATUS_RF_KILL_SW) ? 1 : 0))
1788 return 0;
1789
1790 IPW_DEBUG_RF_KILL("Manual SW RF Kill set to: RADIO %s\n",
1791 disable_radio ? "OFF" : "ON");
1792
1793 if (disable_radio) {
1794 priv->status |= STATUS_RF_KILL_SW;
1795
1796 cancel_delayed_work(&priv->request_scan);
1797 cancel_delayed_work(&priv->request_direct_scan);
1798 cancel_delayed_work(&priv->request_passive_scan);
1799 cancel_delayed_work(&priv->scan_event);
1800 schedule_work(&priv->down);
1801 } else {
1802 priv->status &= ~STATUS_RF_KILL_SW;
1803 if (rf_kill_active(priv)) {
1804 IPW_DEBUG_RF_KILL("Can not turn radio back on - "
1805 "disabled by HW switch\n");
1806
1807 cancel_delayed_work(&priv->rf_kill);
1808 schedule_delayed_work(&priv->rf_kill,
1809 round_jiffies_relative(2 * HZ));
1810 } else
1811 schedule_work(&priv->up);
1812 }
1813
1814 return 1;
1815}
1816
1817static ssize_t store_rf_kill(struct device *d, struct device_attribute *attr,
1818 const char *buf, size_t count)
1819{
1820 struct ipw_priv *priv = dev_get_drvdata(d);
1821
1822 ipw_radio_kill_sw(priv, buf[0] == '1');
1823
1824 return count;
1825}
1826
1827static DEVICE_ATTR(rf_kill, S_IWUSR | S_IRUGO, show_rf_kill, store_rf_kill);
1828
1829static ssize_t show_speed_scan(struct device *d, struct device_attribute *attr,
1830 char *buf)
1831{
1832 struct ipw_priv *priv = dev_get_drvdata(d);
1833 int pos = 0, len = 0;
1834 if (priv->config & CFG_SPEED_SCAN) {
1835 while (priv->speed_scan[pos] != 0)
1836 len += sprintf(&buf[len], "%d ",
1837 priv->speed_scan[pos++]);
1838 return len + sprintf(&buf[len], "\n");
1839 }
1840
1841 return sprintf(buf, "0\n");
1842}
1843
1844static ssize_t store_speed_scan(struct device *d, struct device_attribute *attr,
1845 const char *buf, size_t count)
1846{
1847 struct ipw_priv *priv = dev_get_drvdata(d);
1848 int channel, pos = 0;
1849 const char *p = buf;
1850
1851
1852 while ((channel = simple_strtol(p, NULL, 0))) {
1853 if (pos == MAX_SPEED_SCAN - 1) {
1854 priv->speed_scan[pos] = 0;
1855 break;
1856 }
1857
1858 if (libipw_is_valid_channel(priv->ieee, channel))
1859 priv->speed_scan[pos++] = channel;
1860 else
1861 IPW_WARNING("Skipping invalid channel request: %d\n",
1862 channel);
1863 p = strchr(p, ' ');
1864 if (!p)
1865 break;
1866 while (*p == ' ' || *p == '\t')
1867 p++;
1868 }
1869
1870 if (pos == 0)
1871 priv->config &= ~CFG_SPEED_SCAN;
1872 else {
1873 priv->speed_scan_pos = 0;
1874 priv->config |= CFG_SPEED_SCAN;
1875 }
1876
1877 return count;
1878}
1879
1880static DEVICE_ATTR(speed_scan, S_IWUSR | S_IRUGO, show_speed_scan,
1881 store_speed_scan);
1882
1883static ssize_t show_net_stats(struct device *d, struct device_attribute *attr,
1884 char *buf)
1885{
1886 struct ipw_priv *priv = dev_get_drvdata(d);
1887 return sprintf(buf, "%c\n", (priv->config & CFG_NET_STATS) ? '1' : '0');
1888}
1889
1890static ssize_t store_net_stats(struct device *d, struct device_attribute *attr,
1891 const char *buf, size_t count)
1892{
1893 struct ipw_priv *priv = dev_get_drvdata(d);
1894 if (buf[0] == '1')
1895 priv->config |= CFG_NET_STATS;
1896 else
1897 priv->config &= ~CFG_NET_STATS;
1898
1899 return count;
1900}
1901
1902static DEVICE_ATTR(net_stats, S_IWUSR | S_IRUGO,
1903 show_net_stats, store_net_stats);
1904
1905static ssize_t show_channels(struct device *d,
1906 struct device_attribute *attr,
1907 char *buf)
1908{
1909 struct ipw_priv *priv = dev_get_drvdata(d);
1910 const struct libipw_geo *geo = libipw_get_geo(priv->ieee);
1911 int len = 0, i;
1912
1913 len = sprintf(&buf[len],
1914 "Displaying %d channels in 2.4Ghz band "
1915 "(802.11bg):\n", geo->bg_channels);
1916
1917 for (i = 0; i < geo->bg_channels; i++) {
1918 len += sprintf(&buf[len], "%d: BSS%s%s, %s, Band %s.\n",
1919 geo->bg[i].channel,
1920 geo->bg[i].flags & LIBIPW_CH_RADAR_DETECT ?
1921 " (radar spectrum)" : "",
1922 ((geo->bg[i].flags & LIBIPW_CH_NO_IBSS) ||
1923 (geo->bg[i].flags & LIBIPW_CH_RADAR_DETECT))
1924 ? "" : ", IBSS",
1925 geo->bg[i].flags & LIBIPW_CH_PASSIVE_ONLY ?
1926 "passive only" : "active/passive",
1927 geo->bg[i].flags & LIBIPW_CH_B_ONLY ?
1928 "B" : "B/G");
1929 }
1930
1931 len += sprintf(&buf[len],
1932 "Displaying %d channels in 5.2Ghz band "
1933 "(802.11a):\n", geo->a_channels);
1934 for (i = 0; i < geo->a_channels; i++) {
1935 len += sprintf(&buf[len], "%d: BSS%s%s, %s.\n",
1936 geo->a[i].channel,
1937 geo->a[i].flags & LIBIPW_CH_RADAR_DETECT ?
1938 " (radar spectrum)" : "",
1939 ((geo->a[i].flags & LIBIPW_CH_NO_IBSS) ||
1940 (geo->a[i].flags & LIBIPW_CH_RADAR_DETECT))
1941 ? "" : ", IBSS",
1942 geo->a[i].flags & LIBIPW_CH_PASSIVE_ONLY ?
1943 "passive only" : "active/passive");
1944 }
1945
1946 return len;
1947}
1948
1949static DEVICE_ATTR(channels, S_IRUSR, show_channels, NULL);
1950
1951static void notify_wx_assoc_event(struct ipw_priv *priv)
1952{
1953 union iwreq_data wrqu;
1954 wrqu.ap_addr.sa_family = ARPHRD_ETHER;
1955 if (priv->status & STATUS_ASSOCIATED)
1956 memcpy(wrqu.ap_addr.sa_data, priv->bssid, ETH_ALEN);
1957 else
1958 memset(wrqu.ap_addr.sa_data, 0, ETH_ALEN);
1959 wireless_send_event(priv->net_dev, SIOCGIWAP, &wrqu, NULL);
1960}
1961
1962static void ipw_irq_tasklet(struct ipw_priv *priv)
1963{
1964 u32 inta, inta_mask, handled = 0;
1965 unsigned long flags;
1966 int rc = 0;
1967
1968 spin_lock_irqsave(&priv->irq_lock, flags);
1969
1970 inta = ipw_read32(priv, IPW_INTA_RW);
1971 inta_mask = ipw_read32(priv, IPW_INTA_MASK_R);
1972
1973 if (inta == 0xFFFFFFFF) {
1974
1975 IPW_WARNING("TASKLET INTA == 0xFFFFFFFF\n");
1976
1977 inta = 0;
1978 }
1979 inta &= (IPW_INTA_MASK_ALL & inta_mask);
1980
1981
1982 inta |= priv->isr_inta;
1983
1984 spin_unlock_irqrestore(&priv->irq_lock, flags);
1985
1986 spin_lock_irqsave(&priv->lock, flags);
1987
1988
1989 if (inta & IPW_INTA_BIT_RX_TRANSFER) {
1990 ipw_rx(priv);
1991 handled |= IPW_INTA_BIT_RX_TRANSFER;
1992 }
1993
1994 if (inta & IPW_INTA_BIT_TX_CMD_QUEUE) {
1995 IPW_DEBUG_HC("Command completed.\n");
1996 rc = ipw_queue_tx_reclaim(priv, &priv->txq_cmd, -1);
1997 priv->status &= ~STATUS_HCMD_ACTIVE;
1998 wake_up_interruptible(&priv->wait_command_queue);
1999 handled |= IPW_INTA_BIT_TX_CMD_QUEUE;
2000 }
2001
2002 if (inta & IPW_INTA_BIT_TX_QUEUE_1) {
2003 IPW_DEBUG_TX("TX_QUEUE_1\n");
2004 rc = ipw_queue_tx_reclaim(priv, &priv->txq[0], 0);
2005 handled |= IPW_INTA_BIT_TX_QUEUE_1;
2006 }
2007
2008 if (inta & IPW_INTA_BIT_TX_QUEUE_2) {
2009 IPW_DEBUG_TX("TX_QUEUE_2\n");
2010 rc = ipw_queue_tx_reclaim(priv, &priv->txq[1], 1);
2011 handled |= IPW_INTA_BIT_TX_QUEUE_2;
2012 }
2013
2014 if (inta & IPW_INTA_BIT_TX_QUEUE_3) {
2015 IPW_DEBUG_TX("TX_QUEUE_3\n");
2016 rc = ipw_queue_tx_reclaim(priv, &priv->txq[2], 2);
2017 handled |= IPW_INTA_BIT_TX_QUEUE_3;
2018 }
2019
2020 if (inta & IPW_INTA_BIT_TX_QUEUE_4) {
2021 IPW_DEBUG_TX("TX_QUEUE_4\n");
2022 rc = ipw_queue_tx_reclaim(priv, &priv->txq[3], 3);
2023 handled |= IPW_INTA_BIT_TX_QUEUE_4;
2024 }
2025
2026 if (inta & IPW_INTA_BIT_STATUS_CHANGE) {
2027 IPW_WARNING("STATUS_CHANGE\n");
2028 handled |= IPW_INTA_BIT_STATUS_CHANGE;
2029 }
2030
2031 if (inta & IPW_INTA_BIT_BEACON_PERIOD_EXPIRED) {
2032 IPW_WARNING("TX_PERIOD_EXPIRED\n");
2033 handled |= IPW_INTA_BIT_BEACON_PERIOD_EXPIRED;
2034 }
2035
2036 if (inta & IPW_INTA_BIT_SLAVE_MODE_HOST_CMD_DONE) {
2037 IPW_WARNING("HOST_CMD_DONE\n");
2038 handled |= IPW_INTA_BIT_SLAVE_MODE_HOST_CMD_DONE;
2039 }
2040
2041 if (inta & IPW_INTA_BIT_FW_INITIALIZATION_DONE) {
2042 IPW_WARNING("FW_INITIALIZATION_DONE\n");
2043 handled |= IPW_INTA_BIT_FW_INITIALIZATION_DONE;
2044 }
2045
2046 if (inta & IPW_INTA_BIT_FW_CARD_DISABLE_PHY_OFF_DONE) {
2047 IPW_WARNING("PHY_OFF_DONE\n");
2048 handled |= IPW_INTA_BIT_FW_CARD_DISABLE_PHY_OFF_DONE;
2049 }
2050
2051 if (inta & IPW_INTA_BIT_RF_KILL_DONE) {
2052 IPW_DEBUG_RF_KILL("RF_KILL_DONE\n");
2053 priv->status |= STATUS_RF_KILL_HW;
2054 wiphy_rfkill_set_hw_state(priv->ieee->wdev.wiphy, true);
2055 wake_up_interruptible(&priv->wait_command_queue);
2056 priv->status &= ~(STATUS_ASSOCIATED | STATUS_ASSOCIATING);
2057 cancel_delayed_work(&priv->request_scan);
2058 cancel_delayed_work(&priv->request_direct_scan);
2059 cancel_delayed_work(&priv->request_passive_scan);
2060 cancel_delayed_work(&priv->scan_event);
2061 schedule_work(&priv->link_down);
2062 schedule_delayed_work(&priv->rf_kill, 2 * HZ);
2063 handled |= IPW_INTA_BIT_RF_KILL_DONE;
2064 }
2065
2066 if (inta & IPW_INTA_BIT_FATAL_ERROR) {
2067 IPW_WARNING("Firmware error detected. Restarting.\n");
2068 if (priv->error) {
2069 IPW_DEBUG_FW("Sysfs 'error' log already exists.\n");
2070 if (ipw_debug_level & IPW_DL_FW_ERRORS) {
2071 struct ipw_fw_error *error =
2072 ipw_alloc_error_log(priv);
2073 ipw_dump_error_log(priv, error);
2074 kfree(error);
2075 }
2076 } else {
2077 priv->error = ipw_alloc_error_log(priv);
2078 if (priv->error)
2079 IPW_DEBUG_FW("Sysfs 'error' log captured.\n");
2080 else
2081 IPW_DEBUG_FW("Error allocating sysfs 'error' "
2082 "log.\n");
2083 if (ipw_debug_level & IPW_DL_FW_ERRORS)
2084 ipw_dump_error_log(priv, priv->error);
2085 }
2086
2087
2088
2089 if (priv->ieee->sec.encrypt) {
2090 priv->status &= ~STATUS_ASSOCIATED;
2091 notify_wx_assoc_event(priv);
2092 }
2093
2094
2095
2096 priv->status &= ~STATUS_INIT;
2097
2098
2099 priv->status &= ~STATUS_HCMD_ACTIVE;
2100 wake_up_interruptible(&priv->wait_command_queue);
2101
2102 schedule_work(&priv->adapter_restart);
2103 handled |= IPW_INTA_BIT_FATAL_ERROR;
2104 }
2105
2106 if (inta & IPW_INTA_BIT_PARITY_ERROR) {
2107 IPW_ERROR("Parity error\n");
2108 handled |= IPW_INTA_BIT_PARITY_ERROR;
2109 }
2110
2111 if (handled != inta) {
2112 IPW_ERROR("Unhandled INTA bits 0x%08x\n", inta & ~handled);
2113 }
2114
2115 spin_unlock_irqrestore(&priv->lock, flags);
2116
2117
2118 ipw_enable_interrupts(priv);
2119}
2120
2121#define IPW_CMD(x) case IPW_CMD_ ## x : return #x
2122static char *get_cmd_string(u8 cmd)
2123{
2124 switch (cmd) {
2125 IPW_CMD(HOST_COMPLETE);
2126 IPW_CMD(POWER_DOWN);
2127 IPW_CMD(SYSTEM_CONFIG);
2128 IPW_CMD(MULTICAST_ADDRESS);
2129 IPW_CMD(SSID);
2130 IPW_CMD(ADAPTER_ADDRESS);
2131 IPW_CMD(PORT_TYPE);
2132 IPW_CMD(RTS_THRESHOLD);
2133 IPW_CMD(FRAG_THRESHOLD);
2134 IPW_CMD(POWER_MODE);
2135 IPW_CMD(WEP_KEY);
2136 IPW_CMD(TGI_TX_KEY);
2137 IPW_CMD(SCAN_REQUEST);
2138 IPW_CMD(SCAN_REQUEST_EXT);
2139 IPW_CMD(ASSOCIATE);
2140 IPW_CMD(SUPPORTED_RATES);
2141 IPW_CMD(SCAN_ABORT);
2142 IPW_CMD(TX_FLUSH);
2143 IPW_CMD(QOS_PARAMETERS);
2144 IPW_CMD(DINO_CONFIG);
2145 IPW_CMD(RSN_CAPABILITIES);
2146 IPW_CMD(RX_KEY);
2147 IPW_CMD(CARD_DISABLE);
2148 IPW_CMD(SEED_NUMBER);
2149 IPW_CMD(TX_POWER);
2150 IPW_CMD(COUNTRY_INFO);
2151 IPW_CMD(AIRONET_INFO);
2152 IPW_CMD(AP_TX_POWER);
2153 IPW_CMD(CCKM_INFO);
2154 IPW_CMD(CCX_VER_INFO);
2155 IPW_CMD(SET_CALIBRATION);
2156 IPW_CMD(SENSITIVITY_CALIB);
2157 IPW_CMD(RETRY_LIMIT);
2158 IPW_CMD(IPW_PRE_POWER_DOWN);
2159 IPW_CMD(VAP_BEACON_TEMPLATE);
2160 IPW_CMD(VAP_DTIM_PERIOD);
2161 IPW_CMD(EXT_SUPPORTED_RATES);
2162 IPW_CMD(VAP_LOCAL_TX_PWR_CONSTRAINT);
2163 IPW_CMD(VAP_QUIET_INTERVALS);
2164 IPW_CMD(VAP_CHANNEL_SWITCH);
2165 IPW_CMD(VAP_MANDATORY_CHANNELS);
2166 IPW_CMD(VAP_CELL_PWR_LIMIT);
2167 IPW_CMD(VAP_CF_PARAM_SET);
2168 IPW_CMD(VAP_SET_BEACONING_STATE);
2169 IPW_CMD(MEASUREMENT);
2170 IPW_CMD(POWER_CAPABILITY);
2171 IPW_CMD(SUPPORTED_CHANNELS);
2172 IPW_CMD(TPC_REPORT);
2173 IPW_CMD(WME_INFO);
2174 IPW_CMD(PRODUCTION_COMMAND);
2175 default:
2176 return "UNKNOWN";
2177 }
2178}
2179
2180#define HOST_COMPLETE_TIMEOUT HZ
2181
2182static int __ipw_send_cmd(struct ipw_priv *priv, struct host_cmd *cmd)
2183{
2184 int rc = 0;
2185 unsigned long flags;
2186
2187 spin_lock_irqsave(&priv->lock, flags);
2188 if (priv->status & STATUS_HCMD_ACTIVE) {
2189 IPW_ERROR("Failed to send %s: Already sending a command.\n",
2190 get_cmd_string(cmd->cmd));
2191 spin_unlock_irqrestore(&priv->lock, flags);
2192 return -EAGAIN;
2193 }
2194
2195 priv->status |= STATUS_HCMD_ACTIVE;
2196
2197 if (priv->cmdlog) {
2198 priv->cmdlog[priv->cmdlog_pos].jiffies = jiffies;
2199 priv->cmdlog[priv->cmdlog_pos].cmd.cmd = cmd->cmd;
2200 priv->cmdlog[priv->cmdlog_pos].cmd.len = cmd->len;
2201 memcpy(priv->cmdlog[priv->cmdlog_pos].cmd.param, cmd->param,
2202 cmd->len);
2203 priv->cmdlog[priv->cmdlog_pos].retcode = -1;
2204 }
2205
2206 IPW_DEBUG_HC("%s command (#%d) %d bytes: 0x%08X\n",
2207 get_cmd_string(cmd->cmd), cmd->cmd, cmd->len,
2208 priv->status);
2209
2210#ifndef DEBUG_CMD_WEP_KEY
2211 if (cmd->cmd == IPW_CMD_WEP_KEY)
2212 IPW_DEBUG_HC("WEP_KEY command masked out for secure.\n");
2213 else
2214#endif
2215 printk_buf(IPW_DL_HOST_COMMAND, (u8 *) cmd->param, cmd->len);
2216
2217 rc = ipw_queue_tx_hcmd(priv, cmd->cmd, cmd->param, cmd->len, 0);
2218 if (rc) {
2219 priv->status &= ~STATUS_HCMD_ACTIVE;
2220 IPW_ERROR("Failed to send %s: Reason %d\n",
2221 get_cmd_string(cmd->cmd), rc);
2222 spin_unlock_irqrestore(&priv->lock, flags);
2223 goto exit;
2224 }
2225 spin_unlock_irqrestore(&priv->lock, flags);
2226
2227 rc = wait_event_interruptible_timeout(priv->wait_command_queue,
2228 !(priv->
2229 status & STATUS_HCMD_ACTIVE),
2230 HOST_COMPLETE_TIMEOUT);
2231 if (rc == 0) {
2232 spin_lock_irqsave(&priv->lock, flags);
2233 if (priv->status & STATUS_HCMD_ACTIVE) {
2234 IPW_ERROR("Failed to send %s: Command timed out.\n",
2235 get_cmd_string(cmd->cmd));
2236 priv->status &= ~STATUS_HCMD_ACTIVE;
2237 spin_unlock_irqrestore(&priv->lock, flags);
2238 rc = -EIO;
2239 goto exit;
2240 }
2241 spin_unlock_irqrestore(&priv->lock, flags);
2242 } else
2243 rc = 0;
2244
2245 if (priv->status & STATUS_RF_KILL_HW) {
2246 IPW_ERROR("Failed to send %s: Aborted due to RF kill switch.\n",
2247 get_cmd_string(cmd->cmd));
2248 rc = -EIO;
2249 goto exit;
2250 }
2251
2252 exit:
2253 if (priv->cmdlog) {
2254 priv->cmdlog[priv->cmdlog_pos++].retcode = rc;
2255 priv->cmdlog_pos %= priv->cmdlog_len;
2256 }
2257 return rc;
2258}
2259
2260static int ipw_send_cmd_simple(struct ipw_priv *priv, u8 command)
2261{
2262 struct host_cmd cmd = {
2263 .cmd = command,
2264 };
2265
2266 return __ipw_send_cmd(priv, &cmd);
2267}
2268
2269static int ipw_send_cmd_pdu(struct ipw_priv *priv, u8 command, u8 len,
2270 void *data)
2271{
2272 struct host_cmd cmd = {
2273 .cmd = command,
2274 .len = len,
2275 .param = data,
2276 };
2277
2278 return __ipw_send_cmd(priv, &cmd);
2279}
2280
2281static int ipw_send_host_complete(struct ipw_priv *priv)
2282{
2283 if (!priv) {
2284 IPW_ERROR("Invalid args\n");
2285 return -1;
2286 }
2287
2288 return ipw_send_cmd_simple(priv, IPW_CMD_HOST_COMPLETE);
2289}
2290
2291static int ipw_send_system_config(struct ipw_priv *priv)
2292{
2293 return ipw_send_cmd_pdu(priv, IPW_CMD_SYSTEM_CONFIG,
2294 sizeof(priv->sys_config),
2295 &priv->sys_config);
2296}
2297
2298static int ipw_send_ssid(struct ipw_priv *priv, u8 * ssid, int len)
2299{
2300 if (!priv || !ssid) {
2301 IPW_ERROR("Invalid args\n");
2302 return -1;
2303 }
2304
2305 return ipw_send_cmd_pdu(priv, IPW_CMD_SSID, min(len, IW_ESSID_MAX_SIZE),
2306 ssid);
2307}
2308
2309static int ipw_send_adapter_address(struct ipw_priv *priv, u8 * mac)
2310{
2311 if (!priv || !mac) {
2312 IPW_ERROR("Invalid args\n");
2313 return -1;
2314 }
2315
2316 IPW_DEBUG_INFO("%s: Setting MAC to %pM\n",
2317 priv->net_dev->name, mac);
2318
2319 return ipw_send_cmd_pdu(priv, IPW_CMD_ADAPTER_ADDRESS, ETH_ALEN, mac);
2320}
2321
2322static void ipw_adapter_restart(void *adapter)
2323{
2324 struct ipw_priv *priv = adapter;
2325
2326 if (priv->status & STATUS_RF_KILL_MASK)
2327 return;
2328
2329 ipw_down(priv);
2330
2331 if (priv->assoc_network &&
2332 (priv->assoc_network->capability & WLAN_CAPABILITY_IBSS))
2333 ipw_remove_current_network(priv);
2334
2335 if (ipw_up(priv)) {
2336 IPW_ERROR("Failed to up device\n");
2337 return;
2338 }
2339}
2340
2341static void ipw_bg_adapter_restart(struct work_struct *work)
2342{
2343 struct ipw_priv *priv =
2344 container_of(work, struct ipw_priv, adapter_restart);
2345 mutex_lock(&priv->mutex);
2346 ipw_adapter_restart(priv);
2347 mutex_unlock(&priv->mutex);
2348}
2349
2350static void ipw_abort_scan(struct ipw_priv *priv);
2351
2352#define IPW_SCAN_CHECK_WATCHDOG (5 * HZ)
2353
2354static void ipw_scan_check(void *data)
2355{
2356 struct ipw_priv *priv = data;
2357
2358 if (priv->status & STATUS_SCAN_ABORTING) {
2359 IPW_DEBUG_SCAN("Scan completion watchdog resetting "
2360 "adapter after (%dms).\n",
2361 jiffies_to_msecs(IPW_SCAN_CHECK_WATCHDOG));
2362 schedule_work(&priv->adapter_restart);
2363 } else if (priv->status & STATUS_SCANNING) {
2364 IPW_DEBUG_SCAN("Scan completion watchdog aborting scan "
2365 "after (%dms).\n",
2366 jiffies_to_msecs(IPW_SCAN_CHECK_WATCHDOG));
2367 ipw_abort_scan(priv);
2368 schedule_delayed_work(&priv->scan_check, HZ);
2369 }
2370}
2371
2372static void ipw_bg_scan_check(struct work_struct *work)
2373{
2374 struct ipw_priv *priv =
2375 container_of(work, struct ipw_priv, scan_check.work);
2376 mutex_lock(&priv->mutex);
2377 ipw_scan_check(priv);
2378 mutex_unlock(&priv->mutex);
2379}
2380
2381static int ipw_send_scan_request_ext(struct ipw_priv *priv,
2382 struct ipw_scan_request_ext *request)
2383{
2384 return ipw_send_cmd_pdu(priv, IPW_CMD_SCAN_REQUEST_EXT,
2385 sizeof(*request), request);
2386}
2387
2388static int ipw_send_scan_abort(struct ipw_priv *priv)
2389{
2390 if (!priv) {
2391 IPW_ERROR("Invalid args\n");
2392 return -1;
2393 }
2394
2395 return ipw_send_cmd_simple(priv, IPW_CMD_SCAN_ABORT);
2396}
2397
2398static int ipw_set_sensitivity(struct ipw_priv *priv, u16 sens)
2399{
2400 struct ipw_sensitivity_calib calib = {
2401 .beacon_rssi_raw = cpu_to_le16(sens),
2402 };
2403
2404 return ipw_send_cmd_pdu(priv, IPW_CMD_SENSITIVITY_CALIB, sizeof(calib),
2405 &calib);
2406}
2407
2408static int ipw_send_associate(struct ipw_priv *priv,
2409 struct ipw_associate *associate)
2410{
2411 if (!priv || !associate) {
2412 IPW_ERROR("Invalid args\n");
2413 return -1;
2414 }
2415
2416 return ipw_send_cmd_pdu(priv, IPW_CMD_ASSOCIATE, sizeof(*associate),
2417 associate);
2418}
2419
2420static int ipw_send_supported_rates(struct ipw_priv *priv,
2421 struct ipw_supported_rates *rates)
2422{
2423 if (!priv || !rates) {
2424 IPW_ERROR("Invalid args\n");
2425 return -1;
2426 }
2427
2428 return ipw_send_cmd_pdu(priv, IPW_CMD_SUPPORTED_RATES, sizeof(*rates),
2429 rates);
2430}
2431
2432static int ipw_set_random_seed(struct ipw_priv *priv)
2433{
2434 u32 val;
2435
2436 if (!priv) {
2437 IPW_ERROR("Invalid args\n");
2438 return -1;
2439 }
2440
2441 get_random_bytes(&val, sizeof(val));
2442
2443 return ipw_send_cmd_pdu(priv, IPW_CMD_SEED_NUMBER, sizeof(val), &val);
2444}
2445
2446static int ipw_send_card_disable(struct ipw_priv *priv, u32 phy_off)
2447{
2448 __le32 v = cpu_to_le32(phy_off);
2449 if (!priv) {
2450 IPW_ERROR("Invalid args\n");
2451 return -1;
2452 }
2453
2454 return ipw_send_cmd_pdu(priv, IPW_CMD_CARD_DISABLE, sizeof(v), &v);
2455}
2456
2457static int ipw_send_tx_power(struct ipw_priv *priv, struct ipw_tx_power *power)
2458{
2459 if (!priv || !power) {
2460 IPW_ERROR("Invalid args\n");
2461 return -1;
2462 }
2463
2464 return ipw_send_cmd_pdu(priv, IPW_CMD_TX_POWER, sizeof(*power), power);
2465}
2466
2467static int ipw_set_tx_power(struct ipw_priv *priv)
2468{
2469 const struct libipw_geo *geo = libipw_get_geo(priv->ieee);
2470 struct ipw_tx_power tx_power;
2471 s8 max_power;
2472 int i;
2473
2474 memset(&tx_power, 0, sizeof(tx_power));
2475
2476
2477 tx_power.ieee_mode = IPW_G_MODE;
2478 tx_power.num_channels = geo->bg_channels;
2479 for (i = 0; i < geo->bg_channels; i++) {
2480 max_power = geo->bg[i].max_power;
2481 tx_power.channels_tx_power[i].channel_number =
2482 geo->bg[i].channel;
2483 tx_power.channels_tx_power[i].tx_power = max_power ?
2484 min(max_power, priv->tx_power) : priv->tx_power;
2485 }
2486 if (ipw_send_tx_power(priv, &tx_power))
2487 return -EIO;
2488
2489
2490 tx_power.ieee_mode = IPW_B_MODE;
2491 if (ipw_send_tx_power(priv, &tx_power))
2492 return -EIO;
2493
2494
2495 if (priv->ieee->abg_true) {
2496 tx_power.ieee_mode = IPW_A_MODE;
2497 tx_power.num_channels = geo->a_channels;
2498 for (i = 0; i < tx_power.num_channels; i++) {
2499 max_power = geo->a[i].max_power;
2500 tx_power.channels_tx_power[i].channel_number =
2501 geo->a[i].channel;
2502 tx_power.channels_tx_power[i].tx_power = max_power ?
2503 min(max_power, priv->tx_power) : priv->tx_power;
2504 }
2505 if (ipw_send_tx_power(priv, &tx_power))
2506 return -EIO;
2507 }
2508 return 0;
2509}
2510
2511static int ipw_send_rts_threshold(struct ipw_priv *priv, u16 rts)
2512{
2513 struct ipw_rts_threshold rts_threshold = {
2514 .rts_threshold = cpu_to_le16(rts),
2515 };
2516
2517 if (!priv) {
2518 IPW_ERROR("Invalid args\n");
2519 return -1;
2520 }
2521
2522 return ipw_send_cmd_pdu(priv, IPW_CMD_RTS_THRESHOLD,
2523 sizeof(rts_threshold), &rts_threshold);
2524}
2525
2526static int ipw_send_frag_threshold(struct ipw_priv *priv, u16 frag)
2527{
2528 struct ipw_frag_threshold frag_threshold = {
2529 .frag_threshold = cpu_to_le16(frag),
2530 };
2531
2532 if (!priv) {
2533 IPW_ERROR("Invalid args\n");
2534 return -1;
2535 }
2536
2537 return ipw_send_cmd_pdu(priv, IPW_CMD_FRAG_THRESHOLD,
2538 sizeof(frag_threshold), &frag_threshold);
2539}
2540
2541static int ipw_send_power_mode(struct ipw_priv *priv, u32 mode)
2542{
2543 __le32 param;
2544
2545 if (!priv) {
2546 IPW_ERROR("Invalid args\n");
2547 return -1;
2548 }
2549
2550
2551
2552 switch (mode) {
2553 case IPW_POWER_BATTERY:
2554 param = cpu_to_le32(IPW_POWER_INDEX_3);
2555 break;
2556 case IPW_POWER_AC:
2557 param = cpu_to_le32(IPW_POWER_MODE_CAM);
2558 break;
2559 default:
2560 param = cpu_to_le32(mode);
2561 break;
2562 }
2563
2564 return ipw_send_cmd_pdu(priv, IPW_CMD_POWER_MODE, sizeof(param),
2565 ¶m);
2566}
2567
2568static int ipw_send_retry_limit(struct ipw_priv *priv, u8 slimit, u8 llimit)
2569{
2570 struct ipw_retry_limit retry_limit = {
2571 .short_retry_limit = slimit,
2572 .long_retry_limit = llimit
2573 };
2574
2575 if (!priv) {
2576 IPW_ERROR("Invalid args\n");
2577 return -1;
2578 }
2579
2580 return ipw_send_cmd_pdu(priv, IPW_CMD_RETRY_LIMIT, sizeof(retry_limit),
2581 &retry_limit);
2582}
2583
2584
2585
2586
2587
2588
2589
2590
2591
2592
2593
2594
2595
2596
2597
2598
2599
2600
2601
2602static inline void eeprom_write_reg(struct ipw_priv *p, u32 data)
2603{
2604 ipw_write_reg32(p, FW_MEM_REG_EEPROM_ACCESS, data);
2605
2606
2607 udelay(p->eeprom_delay);
2608}
2609
2610
2611static void eeprom_cs(struct ipw_priv *priv)
2612{
2613 eeprom_write_reg(priv, 0);
2614 eeprom_write_reg(priv, EEPROM_BIT_CS);
2615 eeprom_write_reg(priv, EEPROM_BIT_CS | EEPROM_BIT_SK);
2616 eeprom_write_reg(priv, EEPROM_BIT_CS);
2617}
2618
2619
2620static void eeprom_disable_cs(struct ipw_priv *priv)
2621{
2622 eeprom_write_reg(priv, EEPROM_BIT_CS);
2623 eeprom_write_reg(priv, 0);
2624 eeprom_write_reg(priv, EEPROM_BIT_SK);
2625}
2626
2627
2628static inline void eeprom_write_bit(struct ipw_priv *p, u8 bit)
2629{
2630 int d = (bit ? EEPROM_BIT_DI : 0);
2631 eeprom_write_reg(p, EEPROM_BIT_CS | d);
2632 eeprom_write_reg(p, EEPROM_BIT_CS | d | EEPROM_BIT_SK);
2633}
2634
2635
2636static void eeprom_op(struct ipw_priv *priv, u8 op, u8 addr)
2637{
2638 int i;
2639
2640 eeprom_cs(priv);
2641 eeprom_write_bit(priv, 1);
2642 eeprom_write_bit(priv, op & 2);
2643 eeprom_write_bit(priv, op & 1);
2644 for (i = 7; i >= 0; i--) {
2645 eeprom_write_bit(priv, addr & (1 << i));
2646 }
2647}
2648
2649
2650static u16 eeprom_read_u16(struct ipw_priv *priv, u8 addr)
2651{
2652 int i;
2653 u16 r = 0;
2654
2655
2656 eeprom_op(priv, EEPROM_CMD_READ, addr);
2657
2658
2659 eeprom_write_reg(priv, EEPROM_BIT_CS);
2660
2661
2662 for (i = 0; i < 16; i++) {
2663 u32 data = 0;
2664 eeprom_write_reg(priv, EEPROM_BIT_CS | EEPROM_BIT_SK);
2665 eeprom_write_reg(priv, EEPROM_BIT_CS);
2666 data = ipw_read_reg32(priv, FW_MEM_REG_EEPROM_ACCESS);
2667 r = (r << 1) | ((data & EEPROM_BIT_DO) ? 1 : 0);
2668 }
2669
2670
2671 eeprom_write_reg(priv, 0);
2672 eeprom_disable_cs(priv);
2673
2674 return r;
2675}
2676
2677
2678
2679static void eeprom_parse_mac(struct ipw_priv *priv, u8 * mac)
2680{
2681 memcpy(mac, &priv->eeprom[EEPROM_MAC_ADDRESS], 6);
2682}
2683
2684
2685
2686
2687
2688
2689
2690
2691
2692static void ipw_eeprom_init_sram(struct ipw_priv *priv)
2693{
2694 int i;
2695 __le16 *eeprom = (__le16 *) priv->eeprom;
2696
2697 IPW_DEBUG_TRACE(">>\n");
2698
2699
2700 for (i = 0; i < 128; i++)
2701 eeprom[i] = cpu_to_le16(eeprom_read_u16(priv, (u8) i));
2702
2703
2704
2705
2706
2707
2708 if (priv->eeprom[EEPROM_VERSION] != 0) {
2709 IPW_DEBUG_INFO("Writing EEPROM data into SRAM\n");
2710
2711
2712 for (i = 0; i < IPW_EEPROM_IMAGE_SIZE; i++)
2713 ipw_write8(priv, IPW_EEPROM_DATA + i, priv->eeprom[i]);
2714
2715
2716 ipw_write32(priv, IPW_EEPROM_LOAD_DISABLE, 0);
2717 } else {
2718 IPW_DEBUG_INFO("Enabling FW initializationg of SRAM\n");
2719
2720
2721 ipw_write32(priv, IPW_EEPROM_LOAD_DISABLE, 1);
2722 }
2723
2724 IPW_DEBUG_TRACE("<<\n");
2725}
2726
2727static void ipw_zero_memory(struct ipw_priv *priv, u32 start, u32 count)
2728{
2729 count >>= 2;
2730 if (!count)
2731 return;
2732 _ipw_write32(priv, IPW_AUTOINC_ADDR, start);
2733 while (count--)
2734 _ipw_write32(priv, IPW_AUTOINC_DATA, 0);
2735}
2736
2737static inline void ipw_fw_dma_reset_command_blocks(struct ipw_priv *priv)
2738{
2739 ipw_zero_memory(priv, IPW_SHARED_SRAM_DMA_CONTROL,
2740 CB_NUMBER_OF_ELEMENTS_SMALL *
2741 sizeof(struct command_block));
2742}
2743
2744static int ipw_fw_dma_enable(struct ipw_priv *priv)
2745{
2746
2747 IPW_DEBUG_FW(">> :\n");
2748
2749
2750 ipw_fw_dma_reset_command_blocks(priv);
2751
2752
2753 ipw_write_reg32(priv, IPW_DMA_I_CB_BASE, IPW_SHARED_SRAM_DMA_CONTROL);
2754
2755 IPW_DEBUG_FW("<< :\n");
2756 return 0;
2757}
2758
2759static void ipw_fw_dma_abort(struct ipw_priv *priv)
2760{
2761 u32 control = 0;
2762
2763 IPW_DEBUG_FW(">> :\n");
2764
2765
2766 control = DMA_CONTROL_SMALL_CB_CONST_VALUE | DMA_CB_STOP_AND_ABORT;
2767 ipw_write_reg32(priv, IPW_DMA_I_DMA_CONTROL, control);
2768 priv->sram_desc.last_cb_index = 0;
2769
2770 IPW_DEBUG_FW("<<\n");
2771}
2772
2773static int ipw_fw_dma_write_command_block(struct ipw_priv *priv, int index,
2774 struct command_block *cb)
2775{
2776 u32 address =
2777 IPW_SHARED_SRAM_DMA_CONTROL +
2778 (sizeof(struct command_block) * index);
2779 IPW_DEBUG_FW(">> :\n");
2780
2781 ipw_write_indirect(priv, address, (u8 *) cb,
2782 (int)sizeof(struct command_block));
2783
2784 IPW_DEBUG_FW("<< :\n");
2785 return 0;
2786
2787}
2788
2789static int ipw_fw_dma_kick(struct ipw_priv *priv)
2790{
2791 u32 control = 0;
2792 u32 index = 0;
2793
2794 IPW_DEBUG_FW(">> :\n");
2795
2796 for (index = 0; index < priv->sram_desc.last_cb_index; index++)
2797 ipw_fw_dma_write_command_block(priv, index,
2798 &priv->sram_desc.cb_list[index]);
2799
2800
2801 ipw_clear_bit(priv, IPW_RESET_REG,
2802 IPW_RESET_REG_MASTER_DISABLED |
2803 IPW_RESET_REG_STOP_MASTER);
2804
2805
2806 control = DMA_CONTROL_SMALL_CB_CONST_VALUE | DMA_CB_START;
2807 ipw_write_reg32(priv, IPW_DMA_I_DMA_CONTROL, control);
2808
2809 IPW_DEBUG_FW("<< :\n");
2810 return 0;
2811}
2812
2813static void ipw_fw_dma_dump_command_block(struct ipw_priv *priv)
2814{
2815 u32 address;
2816 u32 register_value = 0;
2817 u32 cb_fields_address = 0;
2818
2819 IPW_DEBUG_FW(">> :\n");
2820 address = ipw_read_reg32(priv, IPW_DMA_I_CURRENT_CB);
2821 IPW_DEBUG_FW_INFO("Current CB is 0x%x\n", address);
2822
2823
2824 register_value = ipw_read_reg32(priv, IPW_DMA_I_DMA_CONTROL);
2825 IPW_DEBUG_FW_INFO("IPW_DMA_I_DMA_CONTROL is 0x%x\n", register_value);
2826
2827
2828 cb_fields_address = address;
2829 register_value = ipw_read_reg32(priv, cb_fields_address);
2830 IPW_DEBUG_FW_INFO("Current CB Control Field is 0x%x\n", register_value);
2831
2832 cb_fields_address += sizeof(u32);
2833 register_value = ipw_read_reg32(priv, cb_fields_address);
2834 IPW_DEBUG_FW_INFO("Current CB Source Field is 0x%x\n", register_value);
2835
2836 cb_fields_address += sizeof(u32);
2837 register_value = ipw_read_reg32(priv, cb_fields_address);
2838 IPW_DEBUG_FW_INFO("Current CB Destination Field is 0x%x\n",
2839 register_value);
2840
2841 cb_fields_address += sizeof(u32);
2842 register_value = ipw_read_reg32(priv, cb_fields_address);
2843 IPW_DEBUG_FW_INFO("Current CB Status Field is 0x%x\n", register_value);
2844
2845 IPW_DEBUG_FW(">> :\n");
2846}
2847
2848static int ipw_fw_dma_command_block_index(struct ipw_priv *priv)
2849{
2850 u32 current_cb_address = 0;
2851 u32 current_cb_index = 0;
2852
2853 IPW_DEBUG_FW("<< :\n");
2854 current_cb_address = ipw_read_reg32(priv, IPW_DMA_I_CURRENT_CB);
2855
2856 current_cb_index = (current_cb_address - IPW_SHARED_SRAM_DMA_CONTROL) /
2857 sizeof(struct command_block);
2858
2859 IPW_DEBUG_FW_INFO("Current CB index 0x%x address = 0x%X\n",
2860 current_cb_index, current_cb_address);
2861
2862 IPW_DEBUG_FW(">> :\n");
2863 return current_cb_index;
2864
2865}
2866
2867static int ipw_fw_dma_add_command_block(struct ipw_priv *priv,
2868 u32 src_address,
2869 u32 dest_address,
2870 u32 length,
2871 int interrupt_enabled, int is_last)
2872{
2873
2874 u32 control = CB_VALID | CB_SRC_LE | CB_DEST_LE | CB_SRC_AUTOINC |
2875 CB_SRC_IO_GATED | CB_DEST_AUTOINC | CB_SRC_SIZE_LONG |
2876 CB_DEST_SIZE_LONG;
2877 struct command_block *cb;
2878 u32 last_cb_element = 0;
2879
2880 IPW_DEBUG_FW_INFO("src_address=0x%x dest_address=0x%x length=0x%x\n",
2881 src_address, dest_address, length);
2882
2883 if (priv->sram_desc.last_cb_index >= CB_NUMBER_OF_ELEMENTS_SMALL)
2884 return -1;
2885
2886 last_cb_element = priv->sram_desc.last_cb_index;
2887 cb = &priv->sram_desc.cb_list[last_cb_element];
2888 priv->sram_desc.last_cb_index++;
2889
2890
2891 if (interrupt_enabled)
2892 control |= CB_INT_ENABLED;
2893
2894 if (is_last)
2895 control |= CB_LAST_VALID;
2896
2897 control |= length;
2898
2899
2900 cb->status = control ^ src_address ^ dest_address;
2901
2902
2903 cb->dest_addr = dest_address;
2904 cb->source_addr = src_address;
2905
2906
2907 cb->control = control;
2908
2909 return 0;
2910}
2911
2912static int ipw_fw_dma_add_buffer(struct ipw_priv *priv, dma_addr_t *src_address,
2913 int nr, u32 dest_address, u32 len)
2914{
2915 int ret, i;
2916 u32 size;
2917
2918 IPW_DEBUG_FW(">>\n");
2919 IPW_DEBUG_FW_INFO("nr=%d dest_address=0x%x len=0x%x\n",
2920 nr, dest_address, len);
2921
2922 for (i = 0; i < nr; i++) {
2923 size = min_t(u32, len - i * CB_MAX_LENGTH, CB_MAX_LENGTH);
2924 ret = ipw_fw_dma_add_command_block(priv, src_address[i],
2925 dest_address +
2926 i * CB_MAX_LENGTH, size,
2927 0, 0);
2928 if (ret) {
2929 IPW_DEBUG_FW_INFO(": Failed\n");
2930 return -1;
2931 } else
2932 IPW_DEBUG_FW_INFO(": Added new cb\n");
2933 }
2934
2935 IPW_DEBUG_FW("<<\n");
2936 return 0;
2937}
2938
2939static int ipw_fw_dma_wait(struct ipw_priv *priv)
2940{
2941 u32 current_index = 0, previous_index;
2942 u32 watchdog = 0;
2943
2944 IPW_DEBUG_FW(">> :\n");
2945
2946 current_index = ipw_fw_dma_command_block_index(priv);
2947 IPW_DEBUG_FW_INFO("sram_desc.last_cb_index:0x%08X\n",
2948 (int)priv->sram_desc.last_cb_index);
2949
2950 while (current_index < priv->sram_desc.last_cb_index) {
2951 udelay(50);
2952 previous_index = current_index;
2953 current_index = ipw_fw_dma_command_block_index(priv);
2954
2955 if (previous_index < current_index) {
2956 watchdog = 0;
2957 continue;
2958 }
2959 if (++watchdog > 400) {
2960 IPW_DEBUG_FW_INFO("Timeout\n");
2961 ipw_fw_dma_dump_command_block(priv);
2962 ipw_fw_dma_abort(priv);
2963 return -1;
2964 }
2965 }
2966
2967 ipw_fw_dma_abort(priv);
2968
2969
2970 ipw_set_bit(priv, IPW_RESET_REG,
2971 IPW_RESET_REG_MASTER_DISABLED | IPW_RESET_REG_STOP_MASTER);
2972
2973 IPW_DEBUG_FW("<< dmaWaitSync\n");
2974 return 0;
2975}
2976
2977static void ipw_remove_current_network(struct ipw_priv *priv)
2978{
2979 struct list_head *element, *safe;
2980 struct libipw_network *network = NULL;
2981 unsigned long flags;
2982
2983 spin_lock_irqsave(&priv->ieee->lock, flags);
2984 list_for_each_safe(element, safe, &priv->ieee->network_list) {
2985 network = list_entry(element, struct libipw_network, list);
2986 if (!memcmp(network->bssid, priv->bssid, ETH_ALEN)) {
2987 list_del(element);
2988 list_add_tail(&network->list,
2989 &priv->ieee->network_free_list);
2990 }
2991 }
2992 spin_unlock_irqrestore(&priv->ieee->lock, flags);
2993}
2994
2995
2996
2997
2998
2999
3000
3001
3002
3003
3004static inline int ipw_alive(struct ipw_priv *priv)
3005{
3006 return ipw_read32(priv, 0x90) == 0xd55555d5;
3007}
3008
3009
3010static int ipw_poll_bit(struct ipw_priv *priv, u32 addr, u32 mask,
3011 int timeout)
3012{
3013 int i = 0;
3014
3015 do {
3016 if ((ipw_read32(priv, addr) & mask) == mask)
3017 return i;
3018 mdelay(10);
3019 i += 10;
3020 } while (i < timeout);
3021
3022 return -ETIME;
3023}
3024
3025
3026
3027
3028
3029
3030static int ipw_stop_master(struct ipw_priv *priv)
3031{
3032 int rc;
3033
3034 IPW_DEBUG_TRACE(">>\n");
3035
3036 ipw_set_bit(priv, IPW_RESET_REG, IPW_RESET_REG_STOP_MASTER);
3037
3038
3039 rc = ipw_poll_bit(priv, IPW_RESET_REG,
3040 IPW_RESET_REG_MASTER_DISABLED, 100);
3041 if (rc < 0) {
3042 IPW_ERROR("wait for stop master failed after 100ms\n");
3043 return -1;
3044 }
3045
3046 IPW_DEBUG_INFO("stop master %dms\n", rc);
3047
3048 return rc;
3049}
3050
3051static void ipw_arc_release(struct ipw_priv *priv)
3052{
3053 IPW_DEBUG_TRACE(">>\n");
3054 mdelay(5);
3055
3056 ipw_clear_bit(priv, IPW_RESET_REG, CBD_RESET_REG_PRINCETON_RESET);
3057
3058
3059 mdelay(5);
3060}
3061
3062struct fw_chunk {
3063 __le32 address;
3064 __le32 length;
3065};
3066
3067static int ipw_load_ucode(struct ipw_priv *priv, u8 * data, size_t len)
3068{
3069 int rc = 0, i, addr;
3070 u8 cr = 0;
3071 __le16 *image;
3072
3073 image = (__le16 *) data;
3074
3075 IPW_DEBUG_TRACE(">>\n");
3076
3077 rc = ipw_stop_master(priv);
3078
3079 if (rc < 0)
3080 return rc;
3081
3082 for (addr = IPW_SHARED_LOWER_BOUND;
3083 addr < IPW_REGISTER_DOMAIN1_END; addr += 4) {
3084 ipw_write32(priv, addr, 0);
3085 }
3086
3087
3088 memset(&priv->dino_alive, 0, sizeof(priv->dino_alive));
3089
3090
3091
3092 ipw_write_reg32(priv, IPW_MEM_HALT_AND_RESET, IPW_BIT_HALT_RESET_ON);
3093 ipw_arc_release(priv);
3094 ipw_write_reg32(priv, IPW_MEM_HALT_AND_RESET, IPW_BIT_HALT_RESET_OFF);
3095 mdelay(1);
3096
3097
3098 ipw_write_reg32(priv, IPW_INTERNAL_CMD_EVENT, IPW_BASEBAND_POWER_DOWN);
3099 mdelay(1);
3100
3101 ipw_write_reg32(priv, IPW_INTERNAL_CMD_EVENT, 0);
3102 mdelay(1);
3103
3104
3105 ipw_write_reg8(priv, IPW_BASEBAND_CONTROL_STATUS, 0x0);
3106 ipw_write_reg8(priv, IPW_BASEBAND_CONTROL_STATUS, DINO_ENABLE_CS);
3107 mdelay(1);
3108
3109
3110
3111
3112
3113
3114
3115
3116
3117
3118 for (i = 0; i < len / 2; i++)
3119 ipw_write_reg16(priv, IPW_BASEBAND_CONTROL_STORE,
3120 le16_to_cpu(image[i]));
3121
3122
3123 ipw_write_reg8(priv, IPW_BASEBAND_CONTROL_STATUS, 0);
3124 ipw_write_reg8(priv, IPW_BASEBAND_CONTROL_STATUS, DINO_ENABLE_SYSTEM);
3125
3126
3127
3128
3129 for (i = 0; i < 100; i++) {
3130
3131 cr = ipw_read_reg8(priv, IPW_BASEBAND_CONTROL_STATUS);
3132 if (cr & DINO_RXFIFO_DATA)
3133 break;
3134 mdelay(1);
3135 }
3136
3137 if (cr & DINO_RXFIFO_DATA) {
3138
3139 __le32 response_buffer[(sizeof(priv->dino_alive) + 3) / 4];
3140
3141 for (i = 0; i < ARRAY_SIZE(response_buffer); i++)
3142 response_buffer[i] =
3143 cpu_to_le32(ipw_read_reg32(priv,
3144 IPW_BASEBAND_RX_FIFO_READ));
3145 memcpy(&priv->dino_alive, response_buffer,
3146 sizeof(priv->dino_alive));
3147 if (priv->dino_alive.alive_command == 1
3148 && priv->dino_alive.ucode_valid == 1) {
3149 rc = 0;
3150 IPW_DEBUG_INFO
3151 ("Microcode OK, rev. %d (0x%x) dev. %d (0x%x) "
3152 "of %02d/%02d/%02d %02d:%02d\n",
3153 priv->dino_alive.software_revision,
3154 priv->dino_alive.software_revision,
3155 priv->dino_alive.device_identifier,
3156 priv->dino_alive.device_identifier,
3157 priv->dino_alive.time_stamp[0],
3158 priv->dino_alive.time_stamp[1],
3159 priv->dino_alive.time_stamp[2],
3160 priv->dino_alive.time_stamp[3],
3161 priv->dino_alive.time_stamp[4]);
3162 } else {
3163 IPW_DEBUG_INFO("Microcode is not alive\n");
3164 rc = -EINVAL;
3165 }
3166 } else {
3167 IPW_DEBUG_INFO("No alive response from DINO\n");
3168 rc = -ETIME;
3169 }
3170
3171
3172
3173 ipw_write_reg8(priv, IPW_BASEBAND_CONTROL_STATUS, 0);
3174
3175 return rc;
3176}
3177
3178static int ipw_load_firmware(struct ipw_priv *priv, u8 * data, size_t len)
3179{
3180 int ret = -1;
3181 int offset = 0;
3182 struct fw_chunk *chunk;
3183 int total_nr = 0;
3184 int i;
3185 struct pci_pool *pool;
3186 void **virts;
3187 dma_addr_t *phys;
3188
3189 IPW_DEBUG_TRACE("<< :\n");
3190
3191 virts = kmalloc(sizeof(void *) * CB_NUMBER_OF_ELEMENTS_SMALL,
3192 GFP_KERNEL);
3193 if (!virts)
3194 return -ENOMEM;
3195
3196 phys = kmalloc(sizeof(dma_addr_t) * CB_NUMBER_OF_ELEMENTS_SMALL,
3197 GFP_KERNEL);
3198 if (!phys) {
3199 kfree(virts);
3200 return -ENOMEM;
3201 }
3202 pool = pci_pool_create("ipw2200", priv->pci_dev, CB_MAX_LENGTH, 0, 0);
3203 if (!pool) {
3204 IPW_ERROR("pci_pool_create failed\n");
3205 kfree(phys);
3206 kfree(virts);
3207 return -ENOMEM;
3208 }
3209
3210
3211 ret = ipw_fw_dma_enable(priv);
3212
3213
3214 BUG_ON(priv->sram_desc.last_cb_index > 0);
3215
3216 do {
3217 u32 chunk_len;
3218 u8 *start;
3219 int size;
3220 int nr = 0;
3221
3222 chunk = (struct fw_chunk *)(data + offset);
3223 offset += sizeof(struct fw_chunk);
3224 chunk_len = le32_to_cpu(chunk->length);
3225 start = data + offset;
3226
3227 nr = (chunk_len + CB_MAX_LENGTH - 1) / CB_MAX_LENGTH;
3228 for (i = 0; i < nr; i++) {
3229 virts[total_nr] = pci_pool_alloc(pool, GFP_KERNEL,
3230 &phys[total_nr]);
3231 if (!virts[total_nr]) {
3232 ret = -ENOMEM;
3233 goto out;
3234 }
3235 size = min_t(u32, chunk_len - i * CB_MAX_LENGTH,
3236 CB_MAX_LENGTH);
3237 memcpy(virts[total_nr], start, size);
3238 start += size;
3239 total_nr++;
3240
3241 BUG_ON(total_nr > CB_NUMBER_OF_ELEMENTS_SMALL);
3242 }
3243
3244
3245
3246
3247
3248 ret = ipw_fw_dma_add_buffer(priv, &phys[total_nr - nr],
3249 nr, le32_to_cpu(chunk->address),
3250 chunk_len);
3251 if (ret) {
3252 IPW_DEBUG_INFO("dmaAddBuffer Failed\n");
3253 goto out;
3254 }
3255
3256 offset += chunk_len;
3257 } while (offset < len);
3258
3259
3260 ret = ipw_fw_dma_kick(priv);
3261 if (ret) {
3262 IPW_ERROR("dmaKick Failed\n");
3263 goto out;
3264 }
3265
3266 ret = ipw_fw_dma_wait(priv);
3267 if (ret) {
3268 IPW_ERROR("dmaWaitSync Failed\n");
3269 goto out;
3270 }
3271 out:
3272 for (i = 0; i < total_nr; i++)
3273 pci_pool_free(pool, virts[i], phys[i]);
3274
3275 pci_pool_destroy(pool);
3276 kfree(phys);
3277 kfree(virts);
3278
3279 return ret;
3280}
3281
3282
3283static int ipw_stop_nic(struct ipw_priv *priv)
3284{
3285 int rc = 0;
3286
3287
3288 ipw_write32(priv, IPW_RESET_REG, IPW_RESET_REG_STOP_MASTER);
3289
3290 rc = ipw_poll_bit(priv, IPW_RESET_REG,
3291 IPW_RESET_REG_MASTER_DISABLED, 500);
3292 if (rc < 0) {
3293 IPW_ERROR("wait for reg master disabled failed after 500ms\n");
3294 return rc;
3295 }
3296
3297 ipw_set_bit(priv, IPW_RESET_REG, CBD_RESET_REG_PRINCETON_RESET);
3298
3299 return rc;
3300}
3301
3302static void ipw_start_nic(struct ipw_priv *priv)
3303{
3304 IPW_DEBUG_TRACE(">>\n");
3305
3306
3307 ipw_clear_bit(priv, IPW_RESET_REG,
3308 IPW_RESET_REG_MASTER_DISABLED |
3309 IPW_RESET_REG_STOP_MASTER |
3310 CBD_RESET_REG_PRINCETON_RESET);
3311
3312
3313 ipw_set_bit(priv, IPW_GP_CNTRL_RW,
3314 IPW_GP_CNTRL_BIT_HOST_ALLOWS_STANDBY);
3315
3316 IPW_DEBUG_TRACE("<<\n");
3317}
3318
3319static int ipw_init_nic(struct ipw_priv *priv)
3320{
3321 int rc;
3322
3323 IPW_DEBUG_TRACE(">>\n");
3324
3325
3326
3327 ipw_set_bit(priv, IPW_GP_CNTRL_RW, IPW_GP_CNTRL_BIT_INIT_DONE);
3328
3329
3330 ipw_write32(priv, IPW_READ_INT_REGISTER,
3331 IPW_BIT_INT_HOST_SRAM_READ_INT_REGISTER);
3332
3333
3334 rc = ipw_poll_bit(priv, IPW_GP_CNTRL_RW,
3335 IPW_GP_CNTRL_BIT_CLOCK_READY, 250);
3336 if (rc < 0)
3337 IPW_DEBUG_INFO("FAILED wait for clock stablization\n");
3338
3339
3340 ipw_set_bit(priv, IPW_RESET_REG, IPW_RESET_REG_SW_RESET);
3341
3342 udelay(10);
3343
3344
3345 ipw_set_bit(priv, IPW_GP_CNTRL_RW, IPW_GP_CNTRL_BIT_INIT_DONE);
3346
3347 IPW_DEBUG_TRACE(">>\n");
3348 return 0;
3349}
3350
3351
3352
3353
3354static int ipw_reset_nic(struct ipw_priv *priv)
3355{
3356 int rc = 0;
3357 unsigned long flags;
3358
3359 IPW_DEBUG_TRACE(">>\n");
3360
3361 rc = ipw_init_nic(priv);
3362
3363 spin_lock_irqsave(&priv->lock, flags);
3364
3365 priv->status &= ~STATUS_HCMD_ACTIVE;
3366 wake_up_interruptible(&priv->wait_command_queue);
3367 priv->status &= ~(STATUS_SCANNING | STATUS_SCAN_ABORTING);
3368 wake_up_interruptible(&priv->wait_state);
3369 spin_unlock_irqrestore(&priv->lock, flags);
3370
3371 IPW_DEBUG_TRACE("<<\n");
3372 return rc;
3373}
3374
3375
3376struct ipw_fw {
3377 __le32 ver;
3378 __le32 boot_size;
3379 __le32 ucode_size;
3380 __le32 fw_size;
3381 u8 data[0];
3382};
3383
3384static int ipw_get_fw(struct ipw_priv *priv,
3385 const struct firmware **raw, const char *name)
3386{
3387 struct ipw_fw *fw;
3388 int rc;
3389
3390
3391 rc = request_firmware(raw, name, &priv->pci_dev->dev);
3392 if (rc < 0) {
3393 IPW_ERROR("%s request_firmware failed: Reason %d\n", name, rc);
3394 return rc;
3395 }
3396
3397 if ((*raw)->size < sizeof(*fw)) {
3398 IPW_ERROR("%s is too small (%zd)\n", name, (*raw)->size);
3399 return -EINVAL;
3400 }
3401
3402 fw = (void *)(*raw)->data;
3403
3404 if ((*raw)->size < sizeof(*fw) + le32_to_cpu(fw->boot_size) +
3405 le32_to_cpu(fw->ucode_size) + le32_to_cpu(fw->fw_size)) {
3406 IPW_ERROR("%s is too small or corrupt (%zd)\n",
3407 name, (*raw)->size);
3408 return -EINVAL;
3409 }
3410
3411 IPW_DEBUG_INFO("Read firmware '%s' image v%d.%d (%zd bytes)\n",
3412 name,
3413 le32_to_cpu(fw->ver) >> 16,
3414 le32_to_cpu(fw->ver) & 0xff,
3415 (*raw)->size - sizeof(*fw));
3416 return 0;
3417}
3418
3419#define IPW_RX_BUF_SIZE (3000)
3420
3421static void ipw_rx_queue_reset(struct ipw_priv *priv,
3422 struct ipw_rx_queue *rxq)
3423{
3424 unsigned long flags;
3425 int i;
3426
3427 spin_lock_irqsave(&rxq->lock, flags);
3428
3429 INIT_LIST_HEAD(&rxq->rx_free);
3430 INIT_LIST_HEAD(&rxq->rx_used);
3431
3432
3433 for (i = 0; i < RX_FREE_BUFFERS + RX_QUEUE_SIZE; i++) {
3434
3435
3436 if (rxq->pool[i].skb != NULL) {
3437 pci_unmap_single(priv->pci_dev, rxq->pool[i].dma_addr,
3438 IPW_RX_BUF_SIZE, PCI_DMA_FROMDEVICE);
3439 dev_kfree_skb(rxq->pool[i].skb);
3440 rxq->pool[i].skb = NULL;
3441 }
3442 list_add_tail(&rxq->pool[i].list, &rxq->rx_used);
3443 }
3444
3445
3446
3447 rxq->read = rxq->write = 0;
3448 rxq->free_count = 0;
3449 spin_unlock_irqrestore(&rxq->lock, flags);
3450}
3451
3452#ifdef CONFIG_PM
3453static int fw_loaded = 0;
3454static const struct firmware *raw = NULL;
3455
3456static void free_firmware(void)
3457{
3458 if (fw_loaded) {
3459 release_firmware(raw);
3460 raw = NULL;
3461 fw_loaded = 0;
3462 }
3463}
3464#else
3465#define free_firmware() do {} while (0)
3466#endif
3467
3468static int ipw_load(struct ipw_priv *priv)
3469{
3470#ifndef CONFIG_PM
3471 const struct firmware *raw = NULL;
3472#endif
3473 struct ipw_fw *fw;
3474 u8 *boot_img, *ucode_img, *fw_img;
3475 u8 *name = NULL;
3476 int rc = 0, retries = 3;
3477
3478 switch (priv->ieee->iw_mode) {
3479 case IW_MODE_ADHOC:
3480 name = "ipw2200-ibss.fw";
3481 break;
3482#ifdef CONFIG_IPW2200_MONITOR
3483 case IW_MODE_MONITOR:
3484 name = "ipw2200-sniffer.fw";
3485 break;
3486#endif
3487 case IW_MODE_INFRA:
3488 name = "ipw2200-bss.fw";
3489 break;
3490 }
3491
3492 if (!name) {
3493 rc = -EINVAL;
3494 goto error;
3495 }
3496
3497#ifdef CONFIG_PM
3498 if (!fw_loaded) {
3499#endif
3500 rc = ipw_get_fw(priv, &raw, name);
3501 if (rc < 0)
3502 goto error;
3503#ifdef CONFIG_PM
3504 }
3505#endif
3506
3507 fw = (void *)raw->data;
3508 boot_img = &fw->data[0];
3509 ucode_img = &fw->data[le32_to_cpu(fw->boot_size)];
3510 fw_img = &fw->data[le32_to_cpu(fw->boot_size) +
3511 le32_to_cpu(fw->ucode_size)];
3512
3513 if (rc < 0)
3514 goto error;
3515
3516 if (!priv->rxq)
3517 priv->rxq = ipw_rx_queue_alloc(priv);
3518 else
3519 ipw_rx_queue_reset(priv, priv->rxq);
3520 if (!priv->rxq) {
3521 IPW_ERROR("Unable to initialize Rx queue\n");
3522 goto error;
3523 }
3524
3525 retry:
3526
3527 ipw_write32(priv, IPW_INTA_MASK_R, ~IPW_INTA_MASK_ALL);
3528 priv->status &= ~STATUS_INT_ENABLED;
3529
3530
3531 ipw_write32(priv, IPW_INTA_RW, IPW_INTA_MASK_ALL);
3532
3533 ipw_stop_nic(priv);
3534
3535 rc = ipw_reset_nic(priv);
3536 if (rc < 0) {
3537 IPW_ERROR("Unable to reset NIC\n");
3538 goto error;
3539 }
3540
3541 ipw_zero_memory(priv, IPW_NIC_SRAM_LOWER_BOUND,
3542 IPW_NIC_SRAM_UPPER_BOUND - IPW_NIC_SRAM_LOWER_BOUND);
3543
3544
3545 rc = ipw_load_firmware(priv, boot_img, le32_to_cpu(fw->boot_size));
3546 if (rc < 0) {
3547 IPW_ERROR("Unable to load boot firmware: %d\n", rc);
3548 goto error;
3549 }
3550
3551
3552 ipw_start_nic(priv);
3553
3554
3555 rc = ipw_poll_bit(priv, IPW_INTA_RW,
3556 IPW_INTA_BIT_FW_INITIALIZATION_DONE, 500);
3557 if (rc < 0) {
3558 IPW_ERROR("device failed to boot initial fw image\n");
3559 goto error;
3560 }
3561 IPW_DEBUG_INFO("initial device response after %dms\n", rc);
3562
3563
3564 ipw_write32(priv, IPW_INTA_RW, IPW_INTA_BIT_FW_INITIALIZATION_DONE);
3565
3566
3567 rc = ipw_load_ucode(priv, ucode_img, le32_to_cpu(fw->ucode_size));
3568 if (rc < 0) {
3569 IPW_ERROR("Unable to load ucode: %d\n", rc);
3570 goto error;
3571 }
3572
3573
3574 ipw_stop_nic(priv);
3575
3576
3577 rc = ipw_load_firmware(priv, fw_img, le32_to_cpu(fw->fw_size));
3578 if (rc < 0) {
3579 IPW_ERROR("Unable to load firmware: %d\n", rc);
3580 goto error;
3581 }
3582#ifdef CONFIG_PM
3583 fw_loaded = 1;
3584#endif
3585
3586 ipw_write32(priv, IPW_EEPROM_LOAD_DISABLE, 0);
3587
3588 rc = ipw_queue_reset(priv);
3589 if (rc < 0) {
3590 IPW_ERROR("Unable to initialize queues\n");
3591 goto error;
3592 }
3593
3594
3595 ipw_write32(priv, IPW_INTA_MASK_R, ~IPW_INTA_MASK_ALL);
3596
3597 ipw_write32(priv, IPW_INTA_RW, IPW_INTA_MASK_ALL);
3598
3599
3600 ipw_start_nic(priv);
3601
3602 if (ipw_read32(priv, IPW_INTA_RW) & IPW_INTA_BIT_PARITY_ERROR) {
3603 if (retries > 0) {
3604 IPW_WARNING("Parity error. Retrying init.\n");
3605 retries--;
3606 goto retry;
3607 }
3608
3609 IPW_ERROR("TODO: Handle parity error -- schedule restart?\n");
3610 rc = -EIO;
3611 goto error;
3612 }
3613
3614
3615 rc = ipw_poll_bit(priv, IPW_INTA_RW,
3616 IPW_INTA_BIT_FW_INITIALIZATION_DONE, 500);
3617 if (rc < 0) {
3618 IPW_ERROR("device failed to start within 500ms\n");
3619 goto error;
3620 }
3621 IPW_DEBUG_INFO("device response after %dms\n", rc);
3622
3623
3624 ipw_write32(priv, IPW_INTA_RW, IPW_INTA_BIT_FW_INITIALIZATION_DONE);
3625
3626
3627 priv->eeprom_delay = 1;
3628 ipw_eeprom_init_sram(priv);
3629
3630
3631 ipw_enable_interrupts(priv);
3632
3633
3634 ipw_rx_queue_replenish(priv);
3635
3636 ipw_write32(priv, IPW_RX_READ_INDEX, priv->rxq->read);
3637
3638
3639 ipw_write32(priv, IPW_INTA_RW, IPW_INTA_MASK_ALL);
3640
3641#ifndef CONFIG_PM
3642 release_firmware(raw);
3643#endif
3644 return 0;
3645
3646 error:
3647 if (priv->rxq) {
3648 ipw_rx_queue_free(priv, priv->rxq);
3649 priv->rxq = NULL;
3650 }
3651 ipw_tx_queue_free(priv);
3652 if (raw)
3653 release_firmware(raw);
3654#ifdef CONFIG_PM
3655 fw_loaded = 0;
3656 raw = NULL;
3657#endif
3658
3659 return rc;
3660}
3661
3662
3663
3664
3665
3666
3667
3668
3669
3670
3671
3672
3673
3674
3675
3676
3677
3678
3679
3680
3681
3682
3683
3684
3685
3686
3687
3688
3689
3690
3691
3692static int ipw_rx_queue_space(const struct ipw_rx_queue *q)
3693{
3694 int s = q->read - q->write;
3695 if (s <= 0)
3696 s += RX_QUEUE_SIZE;
3697
3698 s -= 2;
3699 if (s < 0)
3700 s = 0;
3701 return s;
3702}
3703
3704static inline int ipw_tx_queue_space(const struct clx2_queue *q)
3705{
3706 int s = q->last_used - q->first_empty;
3707 if (s <= 0)
3708 s += q->n_bd;
3709 s -= 2;
3710 if (s < 0)
3711 s = 0;
3712 return s;
3713}
3714
3715static inline int ipw_queue_inc_wrap(int index, int n_bd)
3716{
3717 return (++index == n_bd) ? 0 : index;
3718}
3719
3720
3721
3722
3723
3724
3725
3726
3727
3728
3729
3730
3731
3732
3733
3734static void ipw_queue_init(struct ipw_priv *priv, struct clx2_queue *q,
3735 int count, u32 read, u32 write, u32 base, u32 size)
3736{
3737 q->n_bd = count;
3738
3739 q->low_mark = q->n_bd / 4;
3740 if (q->low_mark < 4)
3741 q->low_mark = 4;
3742
3743 q->high_mark = q->n_bd / 8;
3744 if (q->high_mark < 2)
3745 q->high_mark = 2;
3746
3747 q->first_empty = q->last_used = 0;
3748 q->reg_r = read;
3749 q->reg_w = write;
3750
3751 ipw_write32(priv, base, q->dma_addr);
3752 ipw_write32(priv, size, count);
3753 ipw_write32(priv, read, 0);
3754 ipw_write32(priv, write, 0);
3755
3756 _ipw_read32(priv, 0x90);
3757}
3758
3759static int ipw_queue_tx_init(struct ipw_priv *priv,
3760 struct clx2_tx_queue *q,
3761 int count, u32 read, u32 write, u32 base, u32 size)
3762{
3763 struct pci_dev *dev = priv->pci_dev;
3764
3765 q->txb = kmalloc(sizeof(q->txb[0]) * count, GFP_KERNEL);
3766 if (!q->txb) {
3767 IPW_ERROR("vmalloc for auxiliary BD structures failed\n");
3768 return -ENOMEM;
3769 }
3770
3771 q->bd =
3772 pci_alloc_consistent(dev, sizeof(q->bd[0]) * count, &q->q.dma_addr);
3773 if (!q->bd) {
3774 IPW_ERROR("pci_alloc_consistent(%zd) failed\n",
3775 sizeof(q->bd[0]) * count);
3776 kfree(q->txb);
3777 q->txb = NULL;
3778 return -ENOMEM;
3779 }
3780
3781 ipw_queue_init(priv, &q->q, count, read, write, base, size);
3782 return 0;
3783}
3784
3785
3786
3787
3788
3789
3790
3791
3792static void ipw_queue_tx_free_tfd(struct ipw_priv *priv,
3793 struct clx2_tx_queue *txq)
3794{
3795 struct tfd_frame *bd = &txq->bd[txq->q.last_used];
3796 struct pci_dev *dev = priv->pci_dev;
3797 int i;
3798
3799
3800 if (bd->control_flags.message_type == TX_HOST_COMMAND_TYPE)
3801
3802 return;
3803
3804
3805 if (le32_to_cpu(bd->u.data.num_chunks) > NUM_TFD_CHUNKS) {
3806 IPW_ERROR("Too many chunks: %i\n",
3807 le32_to_cpu(bd->u.data.num_chunks));
3808
3809 return;
3810 }
3811
3812
3813 for (i = 0; i < le32_to_cpu(bd->u.data.num_chunks); i++) {
3814 pci_unmap_single(dev, le32_to_cpu(bd->u.data.chunk_ptr[i]),
3815 le16_to_cpu(bd->u.data.chunk_len[i]),
3816 PCI_DMA_TODEVICE);
3817 if (txq->txb[txq->q.last_used]) {
3818 libipw_txb_free(txq->txb[txq->q.last_used]);
3819 txq->txb[txq->q.last_used] = NULL;
3820 }
3821 }
3822}
3823
3824
3825
3826
3827
3828
3829
3830
3831
3832
3833static void ipw_queue_tx_free(struct ipw_priv *priv, struct clx2_tx_queue *txq)
3834{
3835 struct clx2_queue *q = &txq->q;
3836 struct pci_dev *dev = priv->pci_dev;
3837
3838 if (q->n_bd == 0)
3839 return;
3840
3841
3842 for (; q->first_empty != q->last_used;
3843 q->last_used = ipw_queue_inc_wrap(q->last_used, q->n_bd)) {
3844 ipw_queue_tx_free_tfd(priv, txq);
3845 }
3846
3847
3848 pci_free_consistent(dev, sizeof(txq->bd[0]) * q->n_bd, txq->bd,
3849 q->dma_addr);
3850 kfree(txq->txb);
3851
3852
3853 memset(txq, 0, sizeof(*txq));
3854}
3855
3856
3857
3858
3859
3860
3861static void ipw_tx_queue_free(struct ipw_priv *priv)
3862{
3863
3864 ipw_queue_tx_free(priv, &priv->txq_cmd);
3865
3866
3867 ipw_queue_tx_free(priv, &priv->txq[0]);
3868 ipw_queue_tx_free(priv, &priv->txq[1]);
3869 ipw_queue_tx_free(priv, &priv->txq[2]);
3870 ipw_queue_tx_free(priv, &priv->txq[3]);
3871}
3872
3873static void ipw_create_bssid(struct ipw_priv *priv, u8 * bssid)
3874{
3875
3876 bssid[0] = priv->mac_addr[0];
3877 bssid[1] = priv->mac_addr[1];
3878 bssid[2] = priv->mac_addr[2];
3879
3880
3881 get_random_bytes(&bssid[3], ETH_ALEN - 3);
3882
3883 bssid[0] &= 0xfe;
3884 bssid[0] |= 0x02;
3885}
3886
3887static u8 ipw_add_station(struct ipw_priv *priv, u8 * bssid)
3888{
3889 struct ipw_station_entry entry;
3890 int i;
3891
3892 for (i = 0; i < priv->num_stations; i++) {
3893 if (!memcmp(priv->stations[i], bssid, ETH_ALEN)) {
3894
3895 priv->missed_adhoc_beacons = 0;
3896 if (!(priv->config & CFG_STATIC_CHANNEL))
3897
3898 priv->config &= ~CFG_ADHOC_PERSIST;
3899
3900 return i;
3901 }
3902 }
3903
3904 if (i == MAX_STATIONS)
3905 return IPW_INVALID_STATION;
3906
3907 IPW_DEBUG_SCAN("Adding AdHoc station: %pM\n", bssid);
3908
3909 entry.reserved = 0;
3910 entry.support_mode = 0;
3911 memcpy(entry.mac_addr, bssid, ETH_ALEN);
3912 memcpy(priv->stations[i], bssid, ETH_ALEN);
3913 ipw_write_direct(priv, IPW_STATION_TABLE_LOWER + i * sizeof(entry),
3914 &entry, sizeof(entry));
3915 priv->num_stations++;
3916
3917 return i;
3918}
3919
3920static u8 ipw_find_station(struct ipw_priv *priv, u8 * bssid)
3921{
3922 int i;
3923
3924 for (i = 0; i < priv->num_stations; i++)
3925 if (!memcmp(priv->stations[i], bssid, ETH_ALEN))
3926 return i;
3927
3928 return IPW_INVALID_STATION;
3929}
3930
3931static void ipw_send_disassociate(struct ipw_priv *priv, int quiet)
3932{
3933 int err;
3934
3935 if (priv->status & STATUS_ASSOCIATING) {
3936 IPW_DEBUG_ASSOC("Disassociating while associating.\n");
3937 schedule_work(&priv->disassociate);
3938 return;
3939 }
3940
3941 if (!(priv->status & STATUS_ASSOCIATED)) {
3942 IPW_DEBUG_ASSOC("Disassociating while not associated.\n");
3943 return;
3944 }
3945
3946 IPW_DEBUG_ASSOC("Disassocation attempt from %pM "
3947 "on channel %d.\n",
3948 priv->assoc_request.bssid,
3949 priv->assoc_request.channel);
3950
3951 priv->status &= ~(STATUS_ASSOCIATING | STATUS_ASSOCIATED);
3952 priv->status |= STATUS_DISASSOCIATING;
3953
3954 if (quiet)
3955 priv->assoc_request.assoc_type = HC_DISASSOC_QUIET;
3956 else
3957 priv->assoc_request.assoc_type = HC_DISASSOCIATE;
3958
3959 err = ipw_send_associate(priv, &priv->assoc_request);
3960 if (err) {
3961 IPW_DEBUG_HC("Attempt to send [dis]associate command "
3962 "failed.\n");
3963 return;
3964 }
3965
3966}
3967
3968static int ipw_disassociate(void *data)
3969{
3970 struct ipw_priv *priv = data;
3971 if (!(priv->status & (STATUS_ASSOCIATED | STATUS_ASSOCIATING)))
3972 return 0;
3973 ipw_send_disassociate(data, 0);
3974 netif_carrier_off(priv->net_dev);
3975 return 1;
3976}
3977
3978static void ipw_bg_disassociate(struct work_struct *work)
3979{
3980 struct ipw_priv *priv =
3981 container_of(work, struct ipw_priv, disassociate);
3982 mutex_lock(&priv->mutex);
3983 ipw_disassociate(priv);
3984 mutex_unlock(&priv->mutex);
3985}
3986
3987static void ipw_system_config(struct work_struct *work)
3988{
3989 struct ipw_priv *priv =
3990 container_of(work, struct ipw_priv, system_config);
3991
3992#ifdef CONFIG_IPW2200_PROMISCUOUS
3993 if (priv->prom_net_dev && netif_running(priv->prom_net_dev)) {
3994 priv->sys_config.accept_all_data_frames = 1;
3995 priv->sys_config.accept_non_directed_frames = 1;
3996 priv->sys_config.accept_all_mgmt_bcpr = 1;
3997 priv->sys_config.accept_all_mgmt_frames = 1;
3998 }
3999#endif
4000
4001 ipw_send_system_config(priv);
4002}
4003
4004struct ipw_status_code {
4005 u16 status;
4006 const char *reason;
4007};
4008
4009static const struct ipw_status_code ipw_status_codes[] = {
4010 {0x00, "Successful"},
4011 {0x01, "Unspecified failure"},
4012 {0x0A, "Cannot support all requested capabilities in the "
4013 "Capability information field"},
4014 {0x0B, "Reassociation denied due to inability to confirm that "
4015 "association exists"},
4016 {0x0C, "Association denied due to reason outside the scope of this "
4017 "standard"},
4018 {0x0D,
4019 "Responding station does not support the specified authentication "
4020 "algorithm"},
4021 {0x0E,
4022 "Received an Authentication frame with authentication sequence "
4023 "transaction sequence number out of expected sequence"},
4024 {0x0F, "Authentication rejected because of challenge failure"},
4025 {0x10, "Authentication rejected due to timeout waiting for next "
4026 "frame in sequence"},
4027 {0x11, "Association denied because AP is unable to handle additional "
4028 "associated stations"},
4029 {0x12,
4030 "Association denied due to requesting station not supporting all "
4031 "of the datarates in the BSSBasicServiceSet Parameter"},
4032 {0x13,
4033 "Association denied due to requesting station not supporting "
4034 "short preamble operation"},
4035 {0x14,
4036 "Association denied due to requesting station not supporting "
4037 "PBCC encoding"},
4038 {0x15,
4039 "Association denied due to requesting station not supporting "
4040 "channel agility"},
4041 {0x19,
4042 "Association denied due to requesting station not supporting "
4043 "short slot operation"},
4044 {0x1A,
4045 "Association denied due to requesting station not supporting "
4046 "DSSS-OFDM operation"},
4047 {0x28, "Invalid Information Element"},
4048 {0x29, "Group Cipher is not valid"},
4049 {0x2A, "Pairwise Cipher is not valid"},
4050 {0x2B, "AKMP is not valid"},
4051 {0x2C, "Unsupported RSN IE version"},
4052 {0x2D, "Invalid RSN IE Capabilities"},
4053 {0x2E, "Cipher suite is rejected per security policy"},
4054};
4055
4056static const char *ipw_get_status_code(u16 status)
4057{
4058 int i;
4059 for (i = 0; i < ARRAY_SIZE(ipw_status_codes); i++)
4060 if (ipw_status_codes[i].status == (status & 0xff))
4061 return ipw_status_codes[i].reason;
4062 return "Unknown status value.";
4063}
4064
4065static void inline average_init(struct average *avg)
4066{
4067 memset(avg, 0, sizeof(*avg));
4068}
4069
4070#define DEPTH_RSSI 8
4071#define DEPTH_NOISE 16
4072static s16 exponential_average(s16 prev_avg, s16 val, u8 depth)
4073{
4074 return ((depth-1)*prev_avg + val)/depth;
4075}
4076
4077static void average_add(struct average *avg, s16 val)
4078{
4079 avg->sum -= avg->entries[avg->pos];
4080 avg->sum += val;
4081 avg->entries[avg->pos++] = val;
4082 if (unlikely(avg->pos == AVG_ENTRIES)) {
4083 avg->init = 1;
4084 avg->pos = 0;
4085 }
4086}
4087
4088static s16 average_value(struct average *avg)
4089{
4090 if (!unlikely(avg->init)) {
4091 if (avg->pos)
4092 return avg->sum / avg->pos;
4093 return 0;
4094 }
4095
4096 return avg->sum / AVG_ENTRIES;
4097}
4098
4099static void ipw_reset_stats(struct ipw_priv *priv)
4100{
4101 u32 len = sizeof(u32);
4102
4103 priv->quality = 0;
4104
4105 average_init(&priv->average_missed_beacons);
4106 priv->exp_avg_rssi = -60;
4107 priv->exp_avg_noise = -85 + 0x100;
4108
4109 priv->last_rate = 0;
4110 priv->last_missed_beacons = 0;
4111 priv->last_rx_packets = 0;
4112 priv->last_tx_packets = 0;
4113 priv->last_tx_failures = 0;
4114
4115
4116
4117 ipw_get_ordinal(priv, IPW_ORD_STAT_RX_ERR_CRC,
4118 &priv->last_rx_err, &len);
4119 ipw_get_ordinal(priv, IPW_ORD_STAT_TX_FAILURE,
4120 &priv->last_tx_failures, &len);
4121
4122
4123 priv->missed_adhoc_beacons = 0;
4124 priv->missed_beacons = 0;
4125 priv->tx_packets = 0;
4126 priv->rx_packets = 0;
4127
4128}
4129
4130static u32 ipw_get_max_rate(struct ipw_priv *priv)
4131{
4132 u32 i = 0x80000000;
4133 u32 mask = priv->rates_mask;
4134
4135
4136 if (priv->assoc_request.ieee_mode == IPW_B_MODE)
4137 mask &= LIBIPW_CCK_RATES_MASK;
4138
4139
4140
4141
4142 while (i && !(mask & i))
4143 i >>= 1;
4144 switch (i) {
4145 case LIBIPW_CCK_RATE_1MB_MASK:
4146 return 1000000;
4147 case LIBIPW_CCK_RATE_2MB_MASK:
4148 return 2000000;
4149 case LIBIPW_CCK_RATE_5MB_MASK:
4150 return 5500000;
4151 case LIBIPW_OFDM_RATE_6MB_MASK:
4152 return 6000000;
4153 case LIBIPW_OFDM_RATE_9MB_MASK:
4154 return 9000000;
4155 case LIBIPW_CCK_RATE_11MB_MASK:
4156 return 11000000;
4157 case LIBIPW_OFDM_RATE_12MB_MASK:
4158 return 12000000;
4159 case LIBIPW_OFDM_RATE_18MB_MASK:
4160 return 18000000;
4161 case LIBIPW_OFDM_RATE_24MB_MASK:
4162 return 24000000;
4163 case LIBIPW_OFDM_RATE_36MB_MASK:
4164 return 36000000;
4165 case LIBIPW_OFDM_RATE_48MB_MASK:
4166 return 48000000;
4167 case LIBIPW_OFDM_RATE_54MB_MASK:
4168 return 54000000;
4169 }
4170
4171 if (priv->ieee->mode == IEEE_B)
4172 return 11000000;
4173 else
4174 return 54000000;
4175}
4176
4177static u32 ipw_get_current_rate(struct ipw_priv *priv)
4178{
4179 u32 rate, len = sizeof(rate);
4180 int err;
4181
4182 if (!(priv->status & STATUS_ASSOCIATED))
4183 return 0;
4184
4185 if (priv->tx_packets > IPW_REAL_RATE_RX_PACKET_THRESHOLD) {
4186 err = ipw_get_ordinal(priv, IPW_ORD_STAT_TX_CURR_RATE, &rate,
4187 &len);
4188 if (err) {
4189 IPW_DEBUG_INFO("failed querying ordinals.\n");
4190 return 0;
4191 }
4192 } else
4193 return ipw_get_max_rate(priv);
4194
4195 switch (rate) {
4196 case IPW_TX_RATE_1MB:
4197 return 1000000;
4198 case IPW_TX_RATE_2MB:
4199 return 2000000;
4200 case IPW_TX_RATE_5MB:
4201 return 5500000;
4202 case IPW_TX_RATE_6MB:
4203 return 6000000;
4204 case IPW_TX_RATE_9MB:
4205 return 9000000;
4206 case IPW_TX_RATE_11MB:
4207 return 11000000;
4208 case IPW_TX_RATE_12MB:
4209 return 12000000;
4210 case IPW_TX_RATE_18MB:
4211 return 18000000;
4212 case IPW_TX_RATE_24MB:
4213 return 24000000;
4214 case IPW_TX_RATE_36MB:
4215 return 36000000;
4216 case IPW_TX_RATE_48MB:
4217 return 48000000;
4218 case IPW_TX_RATE_54MB:
4219 return 54000000;
4220 }
4221
4222 return 0;
4223}
4224
4225#define IPW_STATS_INTERVAL (2 * HZ)
4226static void ipw_gather_stats(struct ipw_priv *priv)
4227{
4228 u32 rx_err, rx_err_delta, rx_packets_delta;
4229 u32 tx_failures, tx_failures_delta, tx_packets_delta;
4230 u32 missed_beacons_percent, missed_beacons_delta;
4231 u32 quality = 0;
4232 u32 len = sizeof(u32);
4233 s16 rssi;
4234 u32 beacon_quality, signal_quality, tx_quality, rx_quality,
4235 rate_quality;
4236 u32 max_rate;
4237
4238 if (!(priv->status & STATUS_ASSOCIATED)) {
4239 priv->quality = 0;
4240 return;
4241 }
4242
4243
4244 ipw_get_ordinal(priv, IPW_ORD_STAT_MISSED_BEACONS,
4245 &priv->missed_beacons, &len);
4246 missed_beacons_delta = priv->missed_beacons - priv->last_missed_beacons;
4247 priv->last_missed_beacons = priv->missed_beacons;
4248 if (priv->assoc_request.beacon_interval) {
4249 missed_beacons_percent = missed_beacons_delta *
4250 (HZ * le16_to_cpu(priv->assoc_request.beacon_interval)) /
4251 (IPW_STATS_INTERVAL * 10);
4252 } else {
4253 missed_beacons_percent = 0;
4254 }
4255 average_add(&priv->average_missed_beacons, missed_beacons_percent);
4256
4257 ipw_get_ordinal(priv, IPW_ORD_STAT_RX_ERR_CRC, &rx_err, &len);
4258 rx_err_delta = rx_err - priv->last_rx_err;
4259 priv->last_rx_err = rx_err;
4260
4261 ipw_get_ordinal(priv, IPW_ORD_STAT_TX_FAILURE, &tx_failures, &len);
4262 tx_failures_delta = tx_failures - priv->last_tx_failures;
4263 priv->last_tx_failures = tx_failures;
4264
4265 rx_packets_delta = priv->rx_packets - priv->last_rx_packets;
4266 priv->last_rx_packets = priv->rx_packets;
4267
4268 tx_packets_delta = priv->tx_packets - priv->last_tx_packets;
4269 priv->last_tx_packets = priv->tx_packets;
4270
4271
4272
4273
4274
4275
4276
4277
4278
4279
4280
4281
4282#define BEACON_THRESHOLD 5
4283 beacon_quality = 100 - missed_beacons_percent;
4284 if (beacon_quality < BEACON_THRESHOLD)
4285 beacon_quality = 0;
4286 else
4287 beacon_quality = (beacon_quality - BEACON_THRESHOLD) * 100 /
4288 (100 - BEACON_THRESHOLD);
4289 IPW_DEBUG_STATS("Missed beacon: %3d%% (%d%%)\n",
4290 beacon_quality, missed_beacons_percent);
4291
4292 priv->last_rate = ipw_get_current_rate(priv);
4293 max_rate = ipw_get_max_rate(priv);
4294 rate_quality = priv->last_rate * 40 / max_rate + 60;
4295 IPW_DEBUG_STATS("Rate quality : %3d%% (%dMbs)\n",
4296 rate_quality, priv->last_rate / 1000000);
4297
4298 if (rx_packets_delta > 100 && rx_packets_delta + rx_err_delta)
4299 rx_quality = 100 - (rx_err_delta * 100) /
4300 (rx_packets_delta + rx_err_delta);
4301 else
4302 rx_quality = 100;
4303 IPW_DEBUG_STATS("Rx quality : %3d%% (%u errors, %u packets)\n",
4304 rx_quality, rx_err_delta, rx_packets_delta);
4305
4306 if (tx_packets_delta > 100 && tx_packets_delta + tx_failures_delta)
4307 tx_quality = 100 - (tx_failures_delta * 100) /
4308 (tx_packets_delta + tx_failures_delta);
4309 else
4310 tx_quality = 100;
4311 IPW_DEBUG_STATS("Tx quality : %3d%% (%u errors, %u packets)\n",
4312 tx_quality, tx_failures_delta, tx_packets_delta);
4313
4314 rssi = priv->exp_avg_rssi;
4315 signal_quality =
4316 (100 *
4317 (priv->ieee->perfect_rssi - priv->ieee->worst_rssi) *
4318 (priv->ieee->perfect_rssi - priv->ieee->worst_rssi) -
4319 (priv->ieee->perfect_rssi - rssi) *
4320 (15 * (priv->ieee->perfect_rssi - priv->ieee->worst_rssi) +
4321 62 * (priv->ieee->perfect_rssi - rssi))) /
4322 ((priv->ieee->perfect_rssi - priv->ieee->worst_rssi) *
4323 (priv->ieee->perfect_rssi - priv->ieee->worst_rssi));
4324 if (signal_quality > 100)
4325 signal_quality = 100;
4326 else if (signal_quality < 1)
4327 signal_quality = 0;
4328
4329 IPW_DEBUG_STATS("Signal level : %3d%% (%d dBm)\n",
4330 signal_quality, rssi);
4331
4332 quality = min(rx_quality, signal_quality);
4333 quality = min(tx_quality, quality);
4334 quality = min(rate_quality, quality);
4335 quality = min(beacon_quality, quality);
4336 if (quality == beacon_quality)
4337 IPW_DEBUG_STATS("Quality (%d%%): Clamped to missed beacons.\n",
4338 quality);
4339 if (quality == rate_quality)
4340 IPW_DEBUG_STATS("Quality (%d%%): Clamped to rate quality.\n",
4341 quality);
4342 if (quality == tx_quality)
4343 IPW_DEBUG_STATS("Quality (%d%%): Clamped to Tx quality.\n",
4344 quality);
4345 if (quality == rx_quality)
4346 IPW_DEBUG_STATS("Quality (%d%%): Clamped to Rx quality.\n",
4347 quality);
4348 if (quality == signal_quality)
4349 IPW_DEBUG_STATS("Quality (%d%%): Clamped to signal quality.\n",
4350 quality);
4351
4352 priv->quality = quality;
4353
4354 schedule_delayed_work(&priv->gather_stats, IPW_STATS_INTERVAL);
4355}
4356
4357static void ipw_bg_gather_stats(struct work_struct *work)
4358{
4359 struct ipw_priv *priv =
4360 container_of(work, struct ipw_priv, gather_stats.work);
4361 mutex_lock(&priv->mutex);
4362 ipw_gather_stats(priv);
4363 mutex_unlock(&priv->mutex);
4364}
4365
4366
4367
4368
4369
4370
4371static void ipw_handle_missed_beacon(struct ipw_priv *priv,
4372 int missed_count)
4373{
4374 priv->notif_missed_beacons = missed_count;
4375
4376 if (missed_count > priv->disassociate_threshold &&
4377 priv->status & STATUS_ASSOCIATED) {
4378
4379
4380
4381 IPW_DEBUG(IPW_DL_INFO | IPW_DL_NOTIF |
4382 IPW_DL_STATE | IPW_DL_ASSOC,
4383 "Missed beacon: %d - disassociate\n", missed_count);
4384 priv->status &= ~STATUS_ROAMING;
4385 if (priv->status & STATUS_SCANNING) {
4386 IPW_DEBUG(IPW_DL_INFO | IPW_DL_NOTIF |
4387 IPW_DL_STATE,
4388 "Aborting scan with missed beacon.\n");
4389 schedule_work(&priv->abort_scan);
4390 }
4391
4392 schedule_work(&priv->disassociate);
4393 return;
4394 }
4395
4396 if (priv->status & STATUS_ROAMING) {
4397
4398
4399 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE,
4400 "Missed beacon: %d - roam in progress\n",
4401 missed_count);
4402 return;
4403 }
4404
4405 if (roaming &&
4406 (missed_count > priv->roaming_threshold &&
4407 missed_count <= priv->disassociate_threshold)) {
4408
4409
4410
4411
4412 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE,
4413 "Missed beacon: %d - initiate "
4414 "roaming\n", missed_count);
4415 if (!(priv->status & STATUS_ROAMING)) {
4416 priv->status |= STATUS_ROAMING;
4417 if (!(priv->status & STATUS_SCANNING))
4418 schedule_delayed_work(&priv->request_scan, 0);
4419 }
4420 return;
4421 }
4422
4423 if (priv->status & STATUS_SCANNING &&
4424 missed_count > IPW_MB_SCAN_CANCEL_THRESHOLD) {
4425
4426
4427
4428
4429 IPW_DEBUG(IPW_DL_INFO | IPW_DL_NOTIF | IPW_DL_STATE,
4430 "Aborting scan with missed beacon.\n");
4431 schedule_work(&priv->abort_scan);
4432 }
4433
4434 IPW_DEBUG_NOTIF("Missed beacon: %d\n", missed_count);
4435}
4436
4437static void ipw_scan_event(struct work_struct *work)
4438{
4439 union iwreq_data wrqu;
4440
4441 struct ipw_priv *priv =
4442 container_of(work, struct ipw_priv, scan_event.work);
4443
4444 wrqu.data.length = 0;
4445 wrqu.data.flags = 0;
4446 wireless_send_event(priv->net_dev, SIOCGIWSCAN, &wrqu, NULL);
4447}
4448
4449static void handle_scan_event(struct ipw_priv *priv)
4450{
4451
4452 if (!priv->user_requested_scan) {
4453 if (!delayed_work_pending(&priv->scan_event))
4454 schedule_delayed_work(&priv->scan_event,
4455 round_jiffies_relative(msecs_to_jiffies(4000)));
4456 } else {
4457 union iwreq_data wrqu;
4458
4459 priv->user_requested_scan = 0;
4460 cancel_delayed_work(&priv->scan_event);
4461
4462 wrqu.data.length = 0;
4463 wrqu.data.flags = 0;
4464 wireless_send_event(priv->net_dev, SIOCGIWSCAN, &wrqu, NULL);
4465 }
4466}
4467
4468
4469
4470
4471
4472static void ipw_rx_notification(struct ipw_priv *priv,
4473 struct ipw_rx_notification *notif)
4474{
4475 DECLARE_SSID_BUF(ssid);
4476 u16 size = le16_to_cpu(notif->size);
4477
4478 IPW_DEBUG_NOTIF("type = %i (%d bytes)\n", notif->subtype, size);
4479
4480 switch (notif->subtype) {
4481 case HOST_NOTIFICATION_STATUS_ASSOCIATED:{
4482 struct notif_association *assoc = ¬if->u.assoc;
4483
4484 switch (assoc->state) {
4485 case CMAS_ASSOCIATED:{
4486 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4487 IPW_DL_ASSOC,
4488 "associated: '%s' %pM\n",
4489 print_ssid(ssid, priv->essid,
4490 priv->essid_len),
4491 priv->bssid);
4492
4493 switch (priv->ieee->iw_mode) {
4494 case IW_MODE_INFRA:
4495 memcpy(priv->ieee->bssid,
4496 priv->bssid, ETH_ALEN);
4497 break;
4498
4499 case IW_MODE_ADHOC:
4500 memcpy(priv->ieee->bssid,
4501 priv->bssid, ETH_ALEN);
4502
4503
4504 priv->num_stations = 0;
4505
4506 IPW_DEBUG_ASSOC
4507 ("queueing adhoc check\n");
4508 schedule_delayed_work(
4509 &priv->adhoc_check,
4510 le16_to_cpu(priv->
4511 assoc_request.
4512 beacon_interval));
4513 break;
4514 }
4515
4516 priv->status &= ~STATUS_ASSOCIATING;
4517 priv->status |= STATUS_ASSOCIATED;
4518 schedule_work(&priv->system_config);
4519
4520#ifdef CONFIG_IPW2200_QOS
4521#define IPW_GET_PACKET_STYPE(x) WLAN_FC_GET_STYPE( \
4522 le16_to_cpu(((struct ieee80211_hdr *)(x))->frame_control))
4523 if ((priv->status & STATUS_AUTH) &&
4524 (IPW_GET_PACKET_STYPE(¬if->u.raw)
4525 == IEEE80211_STYPE_ASSOC_RESP)) {
4526 if ((sizeof
4527 (struct
4528 libipw_assoc_response)
4529 <= size)
4530 && (size <= 2314)) {
4531 struct
4532 libipw_rx_stats
4533 stats = {
4534 .len = size - 1,
4535 };
4536
4537 IPW_DEBUG_QOS
4538 ("QoS Associate "
4539 "size %d\n", size);
4540 libipw_rx_mgt(priv->
4541 ieee,
4542 (struct
4543 libipw_hdr_4addr
4544 *)
4545 ¬if->u.raw, &stats);
4546 }
4547 }
4548#endif
4549
4550 schedule_work(&priv->link_up);
4551
4552 break;
4553 }
4554
4555 case CMAS_AUTHENTICATED:{
4556 if (priv->
4557 status & (STATUS_ASSOCIATED |
4558 STATUS_AUTH)) {
4559 struct notif_authenticate *auth
4560 = ¬if->u.auth;
4561 IPW_DEBUG(IPW_DL_NOTIF |
4562 IPW_DL_STATE |
4563 IPW_DL_ASSOC,
4564 "deauthenticated: '%s' "
4565 "%pM"
4566 ": (0x%04X) - %s\n",
4567 print_ssid(ssid,
4568 priv->
4569 essid,
4570 priv->
4571 essid_len),
4572 priv->bssid,
4573 le16_to_cpu(auth->status),
4574 ipw_get_status_code
4575 (le16_to_cpu
4576 (auth->status)));
4577
4578 priv->status &=
4579 ~(STATUS_ASSOCIATING |
4580 STATUS_AUTH |
4581 STATUS_ASSOCIATED);
4582
4583 schedule_work(&priv->link_down);
4584 break;
4585 }
4586
4587 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4588 IPW_DL_ASSOC,
4589 "authenticated: '%s' %pM\n",
4590 print_ssid(ssid, priv->essid,
4591 priv->essid_len),
4592 priv->bssid);
4593 break;
4594 }
4595
4596 case CMAS_INIT:{
4597 if (priv->status & STATUS_AUTH) {
4598 struct
4599 libipw_assoc_response
4600 *resp;
4601 resp =
4602 (struct
4603 libipw_assoc_response
4604 *)¬if->u.raw;
4605 IPW_DEBUG(IPW_DL_NOTIF |
4606 IPW_DL_STATE |
4607 IPW_DL_ASSOC,
4608 "association failed (0x%04X): %s\n",
4609 le16_to_cpu(resp->status),
4610 ipw_get_status_code
4611 (le16_to_cpu
4612 (resp->status)));
4613 }
4614
4615 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4616 IPW_DL_ASSOC,
4617 "disassociated: '%s' %pM\n",
4618 print_ssid(ssid, priv->essid,
4619 priv->essid_len),
4620 priv->bssid);
4621
4622 priv->status &=
4623 ~(STATUS_DISASSOCIATING |
4624 STATUS_ASSOCIATING |
4625 STATUS_ASSOCIATED | STATUS_AUTH);
4626 if (priv->assoc_network
4627 && (priv->assoc_network->
4628 capability &
4629 WLAN_CAPABILITY_IBSS))
4630 ipw_remove_current_network
4631 (priv);
4632
4633 schedule_work(&priv->link_down);
4634
4635 break;
4636 }
4637
4638 case CMAS_RX_ASSOC_RESP:
4639 break;
4640
4641 default:
4642 IPW_ERROR("assoc: unknown (%d)\n",
4643 assoc->state);
4644 break;
4645 }
4646
4647 break;
4648 }
4649
4650 case HOST_NOTIFICATION_STATUS_AUTHENTICATE:{
4651 struct notif_authenticate *auth = ¬if->u.auth;
4652 switch (auth->state) {
4653 case CMAS_AUTHENTICATED:
4654 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE,
4655 "authenticated: '%s' %pM\n",
4656 print_ssid(ssid, priv->essid,
4657 priv->essid_len),
4658 priv->bssid);
4659 priv->status |= STATUS_AUTH;
4660 break;
4661
4662 case CMAS_INIT:
4663 if (priv->status & STATUS_AUTH) {
4664 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4665 IPW_DL_ASSOC,
4666 "authentication failed (0x%04X): %s\n",
4667 le16_to_cpu(auth->status),
4668 ipw_get_status_code(le16_to_cpu
4669 (auth->
4670 status)));
4671 }
4672 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4673 IPW_DL_ASSOC,
4674 "deauthenticated: '%s' %pM\n",
4675 print_ssid(ssid, priv->essid,
4676 priv->essid_len),
4677 priv->bssid);
4678
4679 priv->status &= ~(STATUS_ASSOCIATING |
4680 STATUS_AUTH |
4681 STATUS_ASSOCIATED);
4682
4683 schedule_work(&priv->link_down);
4684 break;
4685
4686 case CMAS_TX_AUTH_SEQ_1:
4687 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4688 IPW_DL_ASSOC, "AUTH_SEQ_1\n");
4689 break;
4690 case CMAS_RX_AUTH_SEQ_2:
4691 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4692 IPW_DL_ASSOC, "AUTH_SEQ_2\n");
4693 break;
4694 case CMAS_AUTH_SEQ_1_PASS:
4695 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4696 IPW_DL_ASSOC, "AUTH_SEQ_1_PASS\n");
4697 break;
4698 case CMAS_AUTH_SEQ_1_FAIL:
4699 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4700 IPW_DL_ASSOC, "AUTH_SEQ_1_FAIL\n");
4701 break;
4702 case CMAS_TX_AUTH_SEQ_3:
4703 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4704 IPW_DL_ASSOC, "AUTH_SEQ_3\n");
4705 break;
4706 case CMAS_RX_AUTH_SEQ_4:
4707 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4708 IPW_DL_ASSOC, "RX_AUTH_SEQ_4\n");
4709 break;
4710 case CMAS_AUTH_SEQ_2_PASS:
4711 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4712 IPW_DL_ASSOC, "AUTH_SEQ_2_PASS\n");
4713 break;
4714 case CMAS_AUTH_SEQ_2_FAIL:
4715 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4716 IPW_DL_ASSOC, "AUT_SEQ_2_FAIL\n");
4717 break;
4718 case CMAS_TX_ASSOC:
4719 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4720 IPW_DL_ASSOC, "TX_ASSOC\n");
4721 break;
4722 case CMAS_RX_ASSOC_RESP:
4723 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4724 IPW_DL_ASSOC, "RX_ASSOC_RESP\n");
4725
4726 break;
4727 case CMAS_ASSOCIATED:
4728 IPW_DEBUG(IPW_DL_NOTIF | IPW_DL_STATE |
4729 IPW_DL_ASSOC, "ASSOCIATED\n");
4730 break;
4731 default:
4732 IPW_DEBUG_NOTIF("auth: failure - %d\n",
4733 auth->state);
4734 break;
4735 }
4736 break;
4737 }
4738
4739 case HOST_NOTIFICATION_STATUS_SCAN_CHANNEL_RESULT:{
4740 struct notif_channel_result *x =
4741 ¬if->u.channel_result;
4742
4743 if (size == sizeof(*x)) {
4744 IPW_DEBUG_SCAN("Scan result for channel %d\n",
4745 x->channel_num);
4746 } else {
4747 IPW_DEBUG_SCAN("Scan result of wrong size %d "
4748 "(should be %zd)\n",
4749 size, sizeof(*x));
4750 }
4751 break;
4752 }
4753
4754 case HOST_NOTIFICATION_STATUS_SCAN_COMPLETED:{
4755 struct notif_scan_complete *x = ¬if->u.scan_complete;
4756 if (size == sizeof(*x)) {
4757 IPW_DEBUG_SCAN
4758 ("Scan completed: type %d, %d channels, "
4759 "%d status\n", x->scan_type,
4760 x->num_channels, x->status);
4761 } else {
4762 IPW_ERROR("Scan completed of wrong size %d "
4763 "(should be %zd)\n",
4764 size, sizeof(*x));
4765 }
4766
4767 priv->status &=
4768 ~(STATUS_SCANNING | STATUS_SCAN_ABORTING);
4769
4770 wake_up_interruptible(&priv->wait_state);
4771 cancel_delayed_work(&priv->scan_check);
4772
4773 if (priv->status & STATUS_EXIT_PENDING)
4774 break;
4775
4776 priv->ieee->scans++;
4777
4778#ifdef CONFIG_IPW2200_MONITOR
4779 if (priv->ieee->iw_mode == IW_MODE_MONITOR) {
4780 priv->status |= STATUS_SCAN_FORCED;
4781 schedule_delayed_work(&priv->request_scan, 0);
4782 break;
4783 }
4784 priv->status &= ~STATUS_SCAN_FORCED;
4785#endif
4786
4787
4788 if (priv->status & STATUS_DIRECT_SCAN_PENDING)
4789 schedule_delayed_work(&priv->request_direct_scan, 0);
4790
4791 if (!(priv->status & (STATUS_ASSOCIATED |
4792 STATUS_ASSOCIATING |
4793 STATUS_ROAMING |
4794 STATUS_DISASSOCIATING)))
4795 schedule_work(&priv->associate);
4796 else if (priv->status & STATUS_ROAMING) {
4797 if (x->status == SCAN_COMPLETED_STATUS_COMPLETE)
4798
4799
4800
4801
4802 schedule_work(&priv->roam);
4803 else
4804
4805 priv->status &= ~STATUS_ROAMING;
4806 } else if (priv->status & STATUS_SCAN_PENDING)
4807 schedule_delayed_work(&priv->request_scan, 0);
4808 else if (priv->config & CFG_BACKGROUND_SCAN
4809 && priv->status & STATUS_ASSOCIATED)
4810 schedule_delayed_work(&priv->request_scan,
4811 round_jiffies_relative(HZ));
4812
4813
4814
4815
4816
4817
4818
4819
4820
4821
4822 if (x->status == SCAN_COMPLETED_STATUS_COMPLETE)
4823 handle_scan_event(priv);
4824 break;
4825 }
4826
4827 case HOST_NOTIFICATION_STATUS_FRAG_LENGTH:{
4828 struct notif_frag_length *x = ¬if->u.frag_len;
4829
4830 if (size == sizeof(*x))
4831 IPW_ERROR("Frag length: %d\n",
4832 le16_to_cpu(x->frag_length));
4833 else
4834 IPW_ERROR("Frag length of wrong size %d "
4835 "(should be %z