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
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60#include "wavelan_cs.p.h"
61
62#ifdef WAVELAN_ROAMING
63static void wl_cell_expiry(unsigned long data);
64static void wl_del_wavepoint(wavepoint_history *wavepoint, struct net_local *lp);
65static void wv_nwid_filter(unsigned char mode, net_local *lp);
66#endif
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83static inline u_char
84hasr_read(u_long base)
85{
86 return(inb(HASR(base)));
87}
88
89
90
91
92
93static inline void
94hacr_write(u_long base,
95 u_char hacr)
96{
97 outb(hacr, HACR(base));
98}
99
100
101
102
103
104
105static void
106hacr_write_slow(u_long base,
107 u_char hacr)
108{
109 hacr_write(base, hacr);
110
111 mdelay(1);
112}
113
114
115
116
117
118static void
119psa_read(struct net_device * dev,
120 int o,
121 u_char * b,
122 int n)
123{
124 net_local *lp = netdev_priv(dev);
125 u_char __iomem *ptr = lp->mem + PSA_ADDR + (o << 1);
126
127 while(n-- > 0)
128 {
129 *b++ = readb(ptr);
130
131
132
133
134
135 ptr += 2;
136 }
137}
138
139
140
141
142
143static void
144psa_write(struct net_device * dev,
145 int o,
146 u_char * b,
147 int n)
148{
149 net_local *lp = netdev_priv(dev);
150 u_char __iomem *ptr = lp->mem + PSA_ADDR + (o << 1);
151 int count = 0;
152 unsigned int base = dev->base_addr;
153
154
155 volatile u_char __iomem *verify = lp->mem + PSA_ADDR +
156 (psaoff(0, psa_comp_number) << 1);
157
158
159 hacr_write(base, HACR_PWR_STAT | HACR_ROM_WEN);
160
161 while(n-- > 0)
162 {
163
164 writeb(*b++, ptr);
165 ptr += 2;
166
167
168
169 count = 0;
170 while((readb(verify) != PSA_COMP_PCMCIA_915) && (count++ < 100))
171 mdelay(1);
172 }
173
174
175 hacr_write(base, HACR_DEFAULT);
176}
177
178#ifdef SET_PSA_CRC
179
180
181
182
183
184
185
186
187
188
189static u_short
190psa_crc(unsigned char * psa,
191 int size)
192{
193 int byte_cnt;
194 u_short crc_bytes = 0;
195 int bit_cnt;
196
197 for(byte_cnt = 0; byte_cnt < size; byte_cnt++ )
198 {
199 crc_bytes ^= psa[byte_cnt];
200
201 for(bit_cnt = 1; bit_cnt < 9; bit_cnt++ )
202 {
203 if(crc_bytes & 0x0001)
204 crc_bytes = (crc_bytes >> 1) ^ 0xA001;
205 else
206 crc_bytes >>= 1 ;
207 }
208 }
209
210 return crc_bytes;
211}
212#endif
213
214
215
216
217
218static void
219update_psa_checksum(struct net_device * dev)
220{
221#ifdef SET_PSA_CRC
222 psa_t psa;
223 u_short crc;
224
225
226 psa_read(dev, 0, (unsigned char *) &psa, sizeof(psa));
227
228
229 crc = psa_crc((unsigned char *) &psa,
230 sizeof(psa) - sizeof(psa.psa_crc[0]) - sizeof(psa.psa_crc[1])
231 - sizeof(psa.psa_crc_status));
232
233 psa.psa_crc[0] = crc & 0xFF;
234 psa.psa_crc[1] = (crc & 0xFF00) >> 8;
235
236
237 psa_write(dev, (char *)&psa.psa_crc - (char *)&psa,
238 (unsigned char *)&psa.psa_crc, 2);
239
240#ifdef DEBUG_IOCTL_INFO
241 printk (KERN_DEBUG "%s: update_psa_checksum(): crc = 0x%02x%02x\n",
242 dev->name, psa.psa_crc[0], psa.psa_crc[1]);
243
244
245 crc = psa_crc((unsigned char *) &psa,
246 sizeof(psa) - sizeof(psa.psa_crc_status));
247
248 if(crc != 0)
249 printk(KERN_WARNING "%s: update_psa_checksum(): CRC does not agree with PSA data (even after recalculating)\n", dev->name);
250#endif
251#endif
252}
253
254
255
256
257
258static void
259mmc_out(u_long base,
260 u_short o,
261 u_char d)
262{
263 int count = 0;
264
265
266 while((count++ < 100) && (inb(HASR(base)) & HASR_MMI_BUSY))
267 udelay(10);
268
269 outb((u_char)((o << 1) | MMR_MMI_WR), MMR(base));
270 outb(d, MMD(base));
271}
272
273
274
275
276
277
278static void
279mmc_write(u_long base,
280 u_char o,
281 u_char * b,
282 int n)
283{
284 o += n;
285 b += n;
286
287 while(n-- > 0 )
288 mmc_out(base, --o, *(--b));
289}
290
291
292
293
294
295
296static u_char
297mmc_in(u_long base,
298 u_short o)
299{
300 int count = 0;
301
302 while((count++ < 100) && (inb(HASR(base)) & HASR_MMI_BUSY))
303 udelay(10);
304 outb(o << 1, MMR(base));
305
306 outb(0, MMD(base));
307
308 while((count++ < 100) && (inb(HASR(base)) & HASR_MMI_BUSY))
309 udelay(10);
310 return (u_char) (inb(MMD(base)));
311}
312
313
314
315
316
317
318
319
320
321static void
322mmc_read(u_long base,
323 u_char o,
324 u_char * b,
325 int n)
326{
327 o += n;
328 b += n;
329
330 while(n-- > 0)
331 *(--b) = mmc_in(base, --o);
332}
333
334
335
336
337
338static inline int
339mmc_encr(u_long base)
340{
341 int temp;
342
343 temp = mmc_in(base, mmroff(0, mmr_des_avail));
344 if((temp != MMR_DES_AVAIL_DES) && (temp != MMR_DES_AVAIL_AES))
345 return 0;
346 else
347 return temp;
348}
349
350
351
352
353
354static void
355fee_wait(u_long base,
356 int delay,
357 int number)
358{
359 int count = 0;
360
361 while((count++ < number) &&
362 (mmc_in(base, mmroff(0, mmr_fee_status)) & MMR_FEE_STATUS_BUSY))
363 udelay(delay);
364}
365
366
367
368
369
370static void
371fee_read(u_long base,
372 u_short o,
373 u_short * b,
374 int n)
375{
376 b += n;
377
378
379 mmc_out(base, mmwoff(0, mmw_fee_addr), o + n - 1);
380
381
382 while(n-- > 0)
383 {
384
385 mmc_out(base, mmwoff(0, mmw_fee_ctrl), MMW_FEE_CTRL_READ);
386
387
388 fee_wait(base, 10, 100);
389
390
391 *--b = ((mmc_in(base, mmroff(0, mmr_fee_data_h)) << 8) |
392 mmc_in(base, mmroff(0, mmr_fee_data_l)));
393 }
394}
395
396
397
398
399
400
401
402
403
404static void
405fee_write(u_long base,
406 u_short o,
407 u_short * b,
408 int n)
409{
410 b += n;
411
412#ifdef EEPROM_IS_PROTECTED
413#ifdef DOESNT_SEEM_TO_WORK
414
415 mmc_out(base, mmwoff(0, mmw_fee_ctrl), MMW_FEE_CTRL_PRREAD);
416
417 fee_wait(base, 10, 100);
418
419
420 printk("Protected 2 : %02X-%02X\n",
421 mmc_in(base, mmroff(0, mmr_fee_data_h)),
422 mmc_in(base, mmroff(0, mmr_fee_data_l)));
423#endif
424
425
426 mmc_out(base, mmwoff(0, mmw_fee_addr), MMW_FEE_ADDR_EN);
427 mmc_out(base, mmwoff(0, mmw_fee_ctrl), MMW_FEE_CTRL_PREN);
428
429 fee_wait(base, 10, 100);
430
431
432 mmc_out(base, mmwoff(0, mmw_fee_addr), o + n);
433 mmc_out(base, mmwoff(0, mmw_fee_ctrl), MMW_FEE_CTRL_PRWRITE);
434#ifdef DOESNT_SEEM_TO_WORK
435
436 mmc_out(base, mmwoff(0, mmw_fee_ctrl), MMW_FEE_CTRL_PRCLEAR);
437#endif
438
439 fee_wait(base, 10, 100);
440#endif
441
442
443 mmc_out(base, mmwoff(0, mmw_fee_addr), MMW_FEE_ADDR_EN);
444 mmc_out(base, mmwoff(0, mmw_fee_ctrl), MMW_FEE_CTRL_WREN);
445
446 fee_wait(base, 10, 100);
447
448
449 mmc_out(base, mmwoff(0, mmw_fee_addr), o + n - 1);
450
451
452 while(n-- > 0)
453 {
454
455 mmc_out(base, mmwoff(0, mmw_fee_data_h), (*--b) >> 8);
456 mmc_out(base, mmwoff(0, mmw_fee_data_l), *b & 0xFF);
457
458
459 mmc_out(base, mmwoff(0, mmw_fee_ctrl), MMW_FEE_CTRL_WRITE);
460
461
462 mdelay(10);
463 fee_wait(base, 10, 100);
464 }
465
466
467 mmc_out(base, mmwoff(0, mmw_fee_addr), MMW_FEE_ADDR_DS);
468 mmc_out(base, mmwoff(0, mmw_fee_ctrl), MMW_FEE_CTRL_WDS);
469
470 fee_wait(base, 10, 100);
471
472#ifdef EEPROM_IS_PROTECTED
473
474 mmc_out(base, mmwoff(0, mmw_fee_addr), 0x00);
475 mmc_out(base, mmwoff(0, mmw_fee_ctrl), MMW_FEE_CTRL_PRWRITE);
476
477 fee_wait(base, 10, 100);
478#endif
479}
480
481
482
483#ifdef WAVELAN_ROAMING
484
485static unsigned char WAVELAN_BEACON_ADDRESS[] = {0x09,0x00,0x0e,0x20,0x03,0x00};
486
487static void wv_roam_init(struct net_device *dev)
488{
489 net_local *lp= netdev_priv(dev);
490
491
492 printk(KERN_NOTICE "%s: Warning, you have enabled roaming on"
493 " device %s !\n", dev->name, dev->name);
494 printk(KERN_NOTICE "Roaming is currently an experimental unsupported feature"
495 " of the Wavelan driver.\n");
496 printk(KERN_NOTICE "It may work, but may also make the driver behave in"
497 " erratic ways or crash.\n");
498
499 lp->wavepoint_table.head=NULL;
500 lp->wavepoint_table.num_wavepoints=0;
501 lp->wavepoint_table.locked=0;
502 lp->curr_point=NULL;
503 lp->cell_search=0;
504
505 lp->cell_timer.data=(long)lp;
506 lp->cell_timer.function=wl_cell_expiry;
507 lp->cell_timer.expires=jiffies+CELL_TIMEOUT;
508 add_timer(&lp->cell_timer);
509
510 wv_nwid_filter(NWID_PROMISC,lp) ;
511
512
513 printk(KERN_DEBUG "WaveLAN: Roaming enabled on device %s\n",dev->name);
514}
515
516static void wv_roam_cleanup(struct net_device *dev)
517{
518 wavepoint_history *ptr,*old_ptr;
519 net_local *lp= netdev_priv(dev);
520
521 printk(KERN_DEBUG "WaveLAN: Roaming Disabled on device %s\n",dev->name);
522
523
524 del_timer(&lp->cell_timer);
525 ptr=lp->wavepoint_table.head;
526 while(ptr!=NULL)
527 {
528 old_ptr=ptr;
529 ptr=ptr->next;
530 wl_del_wavepoint(old_ptr,lp);
531 }
532}
533
534
535static void wv_nwid_filter(unsigned char mode, net_local *lp)
536{
537 mm_t m;
538 unsigned long flags;
539
540#ifdef WAVELAN_ROAMING_DEBUG
541 printk(KERN_DEBUG "WaveLAN: NWID promisc %s, device %s\n",(mode==NWID_PROMISC) ? "on" : "off", lp->dev->name);
542#endif
543
544
545 spin_lock_irqsave(&lp->spinlock, flags);
546
547 m.w.mmw_loopt_sel = (mode==NWID_PROMISC) ? MMW_LOOPT_SEL_DIS_NWID : 0x00;
548 mmc_write(lp->dev->base_addr, (char *)&m.w.mmw_loopt_sel - (char *)&m, (unsigned char *)&m.w.mmw_loopt_sel, 1);
549
550 if(mode==NWID_PROMISC)
551 lp->cell_search=1;
552 else
553 lp->cell_search=0;
554
555
556 spin_unlock_irqrestore(&lp->spinlock, flags);
557}
558
559
560static wavepoint_history *wl_roam_check(unsigned short nwid, net_local *lp)
561{
562 wavepoint_history *ptr=lp->wavepoint_table.head;
563
564 while(ptr!=NULL){
565 if(ptr->nwid==nwid)
566 return ptr;
567 ptr=ptr->next;
568 }
569 return NULL;
570}
571
572
573static wavepoint_history *wl_new_wavepoint(unsigned short nwid, unsigned char seq, net_local* lp)
574{
575 wavepoint_history *new_wavepoint;
576
577#ifdef WAVELAN_ROAMING_DEBUG
578 printk(KERN_DEBUG "WaveLAN: New Wavepoint, NWID:%.4X\n",nwid);
579#endif
580
581 if(lp->wavepoint_table.num_wavepoints==MAX_WAVEPOINTS)
582 return NULL;
583
584 new_wavepoint = kmalloc(sizeof(wavepoint_history),GFP_ATOMIC);
585 if(new_wavepoint==NULL)
586 return NULL;
587
588 new_wavepoint->nwid=nwid;
589 new_wavepoint->average_fast=0;
590 new_wavepoint->average_slow=0;
591 new_wavepoint->qualptr=0;
592 new_wavepoint->last_seq=seq-1;
593 memset(new_wavepoint->sigqual,0,WAVEPOINT_HISTORY);
594
595 new_wavepoint->next=lp->wavepoint_table.head;
596 new_wavepoint->prev=NULL;
597
598 if(lp->wavepoint_table.head!=NULL)
599 lp->wavepoint_table.head->prev=new_wavepoint;
600
601 lp->wavepoint_table.head=new_wavepoint;
602
603 lp->wavepoint_table.num_wavepoints++;
604
605 return new_wavepoint;
606}
607
608
609static void wl_del_wavepoint(wavepoint_history *wavepoint, struct net_local *lp)
610{
611 if(wavepoint==NULL)
612 return;
613
614 if(lp->curr_point==wavepoint)
615 lp->curr_point=NULL;
616
617 if(wavepoint->prev!=NULL)
618 wavepoint->prev->next=wavepoint->next;
619
620 if(wavepoint->next!=NULL)
621 wavepoint->next->prev=wavepoint->prev;
622
623 if(lp->wavepoint_table.head==wavepoint)
624 lp->wavepoint_table.head=wavepoint->next;
625
626 lp->wavepoint_table.num_wavepoints--;
627 kfree(wavepoint);
628}
629
630
631static void wl_cell_expiry(unsigned long data)
632{
633 net_local *lp=(net_local *)data;
634 wavepoint_history *wavepoint=lp->wavepoint_table.head,*old_point;
635
636#if WAVELAN_ROAMING_DEBUG > 1
637 printk(KERN_DEBUG "WaveLAN: Wavepoint timeout, dev %s\n",lp->dev->name);
638#endif
639
640 if(lp->wavepoint_table.locked)
641 {
642#if WAVELAN_ROAMING_DEBUG > 1
643 printk(KERN_DEBUG "WaveLAN: Wavepoint table locked...\n");
644#endif
645
646 lp->cell_timer.expires=jiffies+1;
647 add_timer(&lp->cell_timer);
648 return;
649 }
650
651 while(wavepoint!=NULL)
652 {
653 if(time_after(jiffies, wavepoint->last_seen + CELL_TIMEOUT))
654 {
655#ifdef WAVELAN_ROAMING_DEBUG
656 printk(KERN_DEBUG "WaveLAN: Bye bye %.4X\n",wavepoint->nwid);
657#endif
658
659 old_point=wavepoint;
660 wavepoint=wavepoint->next;
661 wl_del_wavepoint(old_point,lp);
662 }
663 else
664 wavepoint=wavepoint->next;
665 }
666 lp->cell_timer.expires=jiffies+CELL_TIMEOUT;
667 add_timer(&lp->cell_timer);
668}
669
670
671static void wl_update_history(wavepoint_history *wavepoint, unsigned char sigqual, unsigned char seq)
672{
673 int i=0,num_missed=0,ptr=0;
674 int average_fast=0,average_slow=0;
675
676 num_missed=(seq-wavepoint->last_seq)%WAVEPOINT_HISTORY;
677
678 if(num_missed)
679 for(i=0;i<num_missed;i++)
680 {
681 wavepoint->sigqual[wavepoint->qualptr++]=0;
682 wavepoint->qualptr %=WAVEPOINT_HISTORY;
683 }
684 wavepoint->last_seen=jiffies;
685 wavepoint->last_seq=seq;
686 wavepoint->sigqual[wavepoint->qualptr++]=sigqual;
687 wavepoint->qualptr %=WAVEPOINT_HISTORY;
688 ptr=(wavepoint->qualptr-WAVEPOINT_FAST_HISTORY+WAVEPOINT_HISTORY)%WAVEPOINT_HISTORY;
689
690 for(i=0;i<WAVEPOINT_FAST_HISTORY;i++)
691 {
692 average_fast+=wavepoint->sigqual[ptr++];
693 ptr %=WAVEPOINT_HISTORY;
694 }
695
696 average_slow=average_fast;
697 for(i=WAVEPOINT_FAST_HISTORY;i<WAVEPOINT_HISTORY;i++)
698 {
699 average_slow+=wavepoint->sigqual[ptr++];
700 ptr %=WAVEPOINT_HISTORY;
701 }
702
703 wavepoint->average_fast=average_fast/WAVEPOINT_FAST_HISTORY;
704 wavepoint->average_slow=average_slow/WAVEPOINT_HISTORY;
705}
706
707
708static void wv_roam_handover(wavepoint_history *wavepoint, net_local *lp)
709{
710 unsigned int base = lp->dev->base_addr;
711 mm_t m;
712 unsigned long flags;
713
714 if(wavepoint==lp->curr_point)
715 {
716 wv_nwid_filter(!NWID_PROMISC,lp);
717 return;
718 }
719
720#ifdef WAVELAN_ROAMING_DEBUG
721 printk(KERN_DEBUG "WaveLAN: Doing handover to %.4X, dev %s\n",wavepoint->nwid,lp->dev->name);
722#endif
723
724
725 spin_lock_irqsave(&lp->spinlock, flags);
726
727 m.w.mmw_netw_id_l = wavepoint->nwid & 0xFF;
728 m.w.mmw_netw_id_h = (wavepoint->nwid & 0xFF00) >> 8;
729
730 mmc_write(base, (char *)&m.w.mmw_netw_id_l - (char *)&m, (unsigned char *)&m.w.mmw_netw_id_l, 2);
731
732
733 spin_unlock_irqrestore(&lp->spinlock, flags);
734
735 wv_nwid_filter(!NWID_PROMISC,lp);
736 lp->curr_point=wavepoint;
737}
738
739
740static void wl_roam_gather(struct net_device * dev,
741 u_char * hdr,
742 u_char * stats)
743
744{
745 wavepoint_beacon *beacon= (wavepoint_beacon *)hdr;
746 unsigned short nwid=ntohs(beacon->nwid);
747 unsigned short sigqual=stats[2] & MMR_SGNL_QUAL;
748 wavepoint_history *wavepoint=NULL;
749 net_local *lp = netdev_priv(dev);
750
751#ifdef I_NEED_THIS_FEATURE
752
753 nwid=nwid^ntohs(beacon->domain_id);
754#endif
755
756#if WAVELAN_ROAMING_DEBUG > 1
757 printk(KERN_DEBUG "WaveLAN: beacon, dev %s:\n",dev->name);
758 printk(KERN_DEBUG "Domain: %.4X NWID: %.4X SigQual=%d\n",ntohs(beacon->domain_id),nwid,sigqual);
759#endif
760
761 lp->wavepoint_table.locked=1;
762
763 wavepoint=wl_roam_check(nwid,lp);
764 if(wavepoint==NULL)
765 {
766 wavepoint=wl_new_wavepoint(nwid,beacon->seq,lp);
767 if(wavepoint==NULL)
768 goto out;
769 }
770 if(lp->curr_point==NULL)
771 wv_roam_handover(wavepoint, lp);
772
773 wl_update_history(wavepoint, sigqual, beacon->seq);
774
775
776 if(lp->curr_point->average_slow < SEARCH_THRESH_LOW)
777 if(!lp->cell_search)
778 wv_nwid_filter(NWID_PROMISC,lp);
779
780 if(wavepoint->average_slow >
781 lp->curr_point->average_slow + WAVELAN_ROAMING_DELTA)
782 wv_roam_handover(wavepoint, lp);
783
784 if(lp->curr_point->average_slow > SEARCH_THRESH_HIGH)
785 if(lp->cell_search)
786 wv_nwid_filter(!NWID_PROMISC,lp);
787
788out:
789 lp->wavepoint_table.locked=0;
790}
791
792
793static inline int WAVELAN_BEACON(unsigned char *data)
794{
795 wavepoint_beacon *beacon= (wavepoint_beacon *)data;
796 static const wavepoint_beacon beacon_template={0xaa,0xaa,0x03,0x08,0x00,0x0e,0x20,0x03,0x00};
797
798 if(memcmp(beacon,&beacon_template,9)==0)
799 return 1;
800 else
801 return 0;
802}
803#endif
804
805
806
807
808
809
810
811
812
813
814
815
816
817static int
818wv_82593_cmd(struct net_device * dev,
819 char * str,
820 int cmd,
821 int result)
822{
823 unsigned int base = dev->base_addr;
824 int status;
825 int wait_completed;
826 long spin;
827
828
829 spin = 1000;
830 do
831 {
832
833 udelay(10);
834
835
836 outb(OP0_NOP | CR0_STATUS_3, LCCR(base));
837 status = inb(LCSR(base));
838 }
839 while(((status & SR3_EXEC_STATE_MASK) != SR3_EXEC_IDLE) && (spin-- > 0));
840
841
842 if (spin < 0) {
843#ifdef DEBUG_INTERRUPT_ERROR
844 printk(KERN_INFO "wv_82593_cmd: %s timeout (previous command), status 0x%02x\n",
845 str, status);
846#endif
847 return(FALSE);
848 }
849
850
851 outb(cmd, LCCR(base));
852
853
854
855 if(result == SR0_NO_RESULT)
856 return(TRUE);
857
858
859 wait_completed = TRUE;
860
861
862 spin = 1000;
863 do
864 {
865
866 udelay(10);
867
868
869 outb(CR0_STATUS_0 | OP0_NOP, LCCR(base));
870 status = inb(LCSR(base));
871
872
873 if((status & SR0_INTERRUPT))
874 {
875
876 outb(CR0_INT_ACK | OP0_NOP, LCCR(base));
877
878
879 if(((status & SR0_BOTH_RX_TX) != SR0_BOTH_RX_TX) &&
880 ((status & SR0_BOTH_RX_TX) != 0x0) &&
881 !(status & SR0_RECEPTION))
882 {
883
884 wait_completed = FALSE;
885 }
886 else
887 {
888
889
890#ifdef DEBUG_INTERRUPT_INFO
891 printk(KERN_INFO "wv_82593_cmd: not our interrupt\n");
892#endif
893 }
894 }
895 }
896 while(wait_completed && (spin-- > 0));
897
898
899 if(wait_completed)
900 {
901#ifdef DEBUG_INTERRUPT_ERROR
902 printk(KERN_INFO "wv_82593_cmd: %s timeout, status 0x%02x\n",
903 str, status);
904#endif
905 return(FALSE);
906 }
907
908
909
910 if((status & SR0_EVENT_MASK) != result)
911 {
912#ifdef DEBUG_INTERRUPT_ERROR
913 printk(KERN_INFO "wv_82593_cmd: %s failed, status = 0x%x\n",
914 str, status);
915#endif
916 return(FALSE);
917 }
918
919 return(TRUE);
920}
921
922
923
924
925
926
927static inline int
928wv_diag(struct net_device * dev)
929{
930 return(wv_82593_cmd(dev, "wv_diag(): diagnose",
931 OP0_DIAGNOSE, SR0_DIAGNOSE_PASSED));
932}
933
934
935
936
937
938
939
940static int
941read_ringbuf(struct net_device * dev,
942 int addr,
943 char * buf,
944 int len)
945{
946 unsigned int base = dev->base_addr;
947 int ring_ptr = addr;
948 int chunk_len;
949 char * buf_ptr = buf;
950
951
952 while(len > 0)
953 {
954
955 outb(ring_ptr & 0xff, PIORL(base));
956 outb(((ring_ptr >> 8) & PIORH_MASK), PIORH(base));
957
958
959
960 if((addr + len) < (RX_BASE + RX_SIZE))
961 chunk_len = len;
962 else
963 chunk_len = RX_BASE + RX_SIZE - addr;
964 insb(PIOP(base), buf_ptr, chunk_len);
965 buf_ptr += chunk_len;
966 len -= chunk_len;
967 ring_ptr = (ring_ptr - RX_BASE + chunk_len) % RX_SIZE + RX_BASE;
968 }
969 return(ring_ptr);
970}
971
972
973
974
975
976
977
978
979
980
981static void
982wv_82593_reconfig(struct net_device * dev)
983{
984 net_local * lp = netdev_priv(dev);
985 struct pcmcia_device * link = lp->link;
986 unsigned long flags;
987
988
989 lp->reconfig_82593 = TRUE;
990
991
992 if((link->open) && (netif_running(dev)) && !(netif_queue_stopped(dev)))
993 {
994 spin_lock_irqsave(&lp->spinlock, flags);
995 wv_82593_config(dev);
996 spin_unlock_irqrestore(&lp->spinlock, flags);
997 }
998 else
999 {
1000#ifdef DEBUG_IOCTL_INFO
1001 printk(KERN_DEBUG
1002 "%s: wv_82593_reconfig(): delayed (state = %lX, link = %d)\n",
1003 dev->name, dev->state, link->open);
1004#endif
1005 }
1006}
1007
1008
1009
1010
1011
1012
1013
1014#ifdef DEBUG_PSA_SHOW
1015
1016
1017
1018
1019static void
1020wv_psa_show(psa_t * p)
1021{
1022 printk(KERN_DEBUG "##### wavelan psa contents: #####\n");
1023 printk(KERN_DEBUG "psa_io_base_addr_1: 0x%02X %02X %02X %02X\n",
1024 p->psa_io_base_addr_1,
1025 p->psa_io_base_addr_2,
1026 p->psa_io_base_addr_3,
1027 p->psa_io_base_addr_4);
1028 printk(KERN_DEBUG "psa_rem_boot_addr_1: 0x%02X %02X %02X\n",
1029 p->psa_rem_boot_addr_1,
1030 p->psa_rem_boot_addr_2,
1031 p->psa_rem_boot_addr_3);
1032 printk(KERN_DEBUG "psa_holi_params: 0x%02x, ", p->psa_holi_params);
1033 printk("psa_int_req_no: %d\n", p->psa_int_req_no);
1034#ifdef DEBUG_SHOW_UNUSED
1035 printk(KERN_DEBUG "psa_unused0[]: %pM\n", p->psa_unused0);
1036#endif
1037 printk(KERN_DEBUG "psa_univ_mac_addr[]: %pM\n", p->psa_univ_mac_addr);
1038 printk(KERN_DEBUG "psa_local_mac_addr[]: %pM\n", p->psa_local_mac_addr);
1039 printk(KERN_DEBUG "psa_univ_local_sel: %d, ", p->psa_univ_local_sel);
1040 printk("psa_comp_number: %d, ", p->psa_comp_number);
1041 printk("psa_thr_pre_set: 0x%02x\n", p->psa_thr_pre_set);
1042 printk(KERN_DEBUG "psa_feature_select/decay_prm: 0x%02x, ",
1043 p->psa_feature_select);
1044 printk("psa_subband/decay_update_prm: %d\n", p->psa_subband);
1045 printk(KERN_DEBUG "psa_quality_thr: 0x%02x, ", p->psa_quality_thr);
1046 printk("psa_mod_delay: 0x%02x\n", p->psa_mod_delay);
1047 printk(KERN_DEBUG "psa_nwid: 0x%02x%02x, ", p->psa_nwid[0], p->psa_nwid[1]);
1048 printk("psa_nwid_select: %d\n", p->psa_nwid_select);
1049 printk(KERN_DEBUG "psa_encryption_select: %d, ", p->psa_encryption_select);
1050 printk("psa_encryption_key[]: %02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x\n",
1051 p->psa_encryption_key[0],
1052 p->psa_encryption_key[1],
1053 p->psa_encryption_key[2],
1054 p->psa_encryption_key[3],
1055 p->psa_encryption_key[4],
1056 p->psa_encryption_key[5],
1057 p->psa_encryption_key[6],
1058 p->psa_encryption_key[7]);
1059 printk(KERN_DEBUG "psa_databus_width: %d\n", p->psa_databus_width);
1060 printk(KERN_DEBUG "psa_call_code/auto_squelch: 0x%02x, ",
1061 p->psa_call_code[0]);
1062 printk("psa_call_code[]: %02X:%02X:%02X:%02X:%02X:%02X:%02X:%02X\n",
1063 p->psa_call_code[0],
1064 p->psa_call_code[1],
1065 p->psa_call_code[2],
1066 p->psa_call_code[3],
1067 p->psa_call_code[4],
1068 p->psa_call_code[5],
1069 p->psa_call_code[6],
1070 p->psa_call_code[7]);
1071#ifdef DEBUG_SHOW_UNUSED
1072 printk(KERN_DEBUG "psa_reserved[]: %02X:%02X\n",
1073 p->psa_reserved[0],
1074 p->psa_reserved[1]);
1075#endif
1076 printk(KERN_DEBUG "psa_conf_status: %d, ", p->psa_conf_status);
1077 printk("psa_crc: 0x%02x%02x, ", p->psa_crc[0], p->psa_crc[1]);
1078 printk("psa_crc_status: 0x%02x\n", p->psa_crc_status);
1079}
1080#endif
1081
1082#ifdef DEBUG_MMC_SHOW
1083
1084
1085
1086
1087
1088static void
1089wv_mmc_show(struct net_device * dev)
1090{
1091 unsigned int base = dev->base_addr;
1092 net_local * lp = netdev_priv(dev);
1093 mmr_t m;
1094
1095
1096 if(hasr_read(base) & HASR_NO_CLK)
1097 {
1098 printk(KERN_WARNING "%s: wv_mmc_show: modem not connected\n",
1099 dev->name);
1100 return;
1101 }
1102
1103 spin_lock_irqsave(&lp->spinlock, flags);
1104
1105
1106 mmc_out(base, mmwoff(0, mmw_freeze), 1);
1107 mmc_read(base, 0, (u_char *)&m, sizeof(m));
1108 mmc_out(base, mmwoff(0, mmw_freeze), 0);
1109
1110
1111 lp->wstats.discard.nwid += (m.mmr_wrong_nwid_h << 8) | m.mmr_wrong_nwid_l;
1112
1113 spin_unlock_irqrestore(&lp->spinlock, flags);
1114
1115 printk(KERN_DEBUG "##### wavelan modem status registers: #####\n");
1116#ifdef DEBUG_SHOW_UNUSED
1117 printk(KERN_DEBUG "mmc_unused0[]: %02X:%02X:%02X:%02X:%02X:%02X:%02X:%02X\n",
1118 m.mmr_unused0[0],
1119 m.mmr_unused0[1],
1120 m.mmr_unused0[2],
1121 m.mmr_unused0[3],
1122 m.mmr_unused0[4],
1123 m.mmr_unused0[5],
1124 m.mmr_unused0[6],
1125 m.mmr_unused0[7]);
1126#endif
1127 printk(KERN_DEBUG "Encryption algorithm: %02X - Status: %02X\n",
1128 m.mmr_des_avail, m.mmr_des_status);
1129#ifdef DEBUG_SHOW_UNUSED
1130 printk(KERN_DEBUG "mmc_unused1[]: %02X:%02X:%02X:%02X:%02X\n",
1131 m.mmr_unused1[0],
1132 m.mmr_unused1[1],
1133 m.mmr_unused1[2],
1134 m.mmr_unused1[3],
1135 m.mmr_unused1[4]);
1136#endif
1137 printk(KERN_DEBUG "dce_status: 0x%x [%s%s%s%s]\n",
1138 m.mmr_dce_status,
1139 (m.mmr_dce_status & MMR_DCE_STATUS_RX_BUSY) ? "energy detected,":"",
1140 (m.mmr_dce_status & MMR_DCE_STATUS_LOOPT_IND) ?
1141 "loop test indicated," : "",
1142 (m.mmr_dce_status & MMR_DCE_STATUS_TX_BUSY) ? "transmitter on," : "",
1143 (m.mmr_dce_status & MMR_DCE_STATUS_JBR_EXPIRED) ?
1144 "jabber timer expired," : "");
1145 printk(KERN_DEBUG "Dsp ID: %02X\n",
1146 m.mmr_dsp_id);
1147#ifdef DEBUG_SHOW_UNUSED
1148 printk(KERN_DEBUG "mmc_unused2[]: %02X:%02X\n",
1149 m.mmr_unused2[0],
1150 m.mmr_unused2[1]);
1151#endif
1152 printk(KERN_DEBUG "# correct_nwid: %d, # wrong_nwid: %d\n",
1153 (m.mmr_correct_nwid_h << 8) | m.mmr_correct_nwid_l,
1154 (m.mmr_wrong_nwid_h << 8) | m.mmr_wrong_nwid_l);
1155 printk(KERN_DEBUG "thr_pre_set: 0x%x [current signal %s]\n",
1156 m.mmr_thr_pre_set & MMR_THR_PRE_SET,
1157 (m.mmr_thr_pre_set & MMR_THR_PRE_SET_CUR) ? "above" : "below");
1158 printk(KERN_DEBUG "signal_lvl: %d [%s], ",
1159 m.mmr_signal_lvl & MMR_SIGNAL_LVL,
1160 (m.mmr_signal_lvl & MMR_SIGNAL_LVL_VALID) ? "new msg" : "no new msg");
1161 printk("silence_lvl: %d [%s], ", m.mmr_silence_lvl & MMR_SILENCE_LVL,
1162 (m.mmr_silence_lvl & MMR_SILENCE_LVL_VALID) ? "update done" : "no new update");
1163 printk("sgnl_qual: 0x%x [%s]\n", m.mmr_sgnl_qual & MMR_SGNL_QUAL,
1164 (m.mmr_sgnl_qual & MMR_SGNL_QUAL_ANT) ? "Antenna 1" : "Antenna 0");
1165#ifdef DEBUG_SHOW_UNUSED
1166 printk(KERN_DEBUG "netw_id_l: %x\n", m.mmr_netw_id_l);
1167#endif
1168}
1169#endif
1170
1171#ifdef DEBUG_I82593_SHOW
1172
1173
1174
1175
1176static void
1177wv_ru_show(struct net_device * dev)
1178{
1179 net_local *lp = netdev_priv(dev);
1180
1181 printk(KERN_DEBUG "##### wavelan i82593 receiver status: #####\n");
1182 printk(KERN_DEBUG "ru: rfp %d stop %d", lp->rfp, lp->stop);
1183
1184
1185
1186 printk("\n");
1187}
1188#endif
1189
1190#ifdef DEBUG_DEVICE_SHOW
1191
1192
1193
1194
1195static void
1196wv_dev_show(struct net_device * dev)
1197{
1198 printk(KERN_DEBUG "dev:");
1199 printk(" state=%lX,", dev->state);
1200 printk(" trans_start=%ld,", dev->trans_start);
1201 printk(" flags=0x%x,", dev->flags);
1202 printk("\n");
1203}
1204
1205
1206
1207
1208
1209
1210static void
1211wv_local_show(struct net_device * dev)
1212{
1213 net_local *lp = netdev_priv(dev);
1214
1215 printk(KERN_DEBUG "local:");
1216
1217
1218
1219 printk("\n");
1220}
1221#endif
1222
1223#if defined(DEBUG_RX_INFO) || defined(DEBUG_TX_INFO)
1224
1225
1226
1227
1228static void
1229wv_packet_info(u_char * p,
1230 int length,
1231 char * msg1,
1232 char * msg2)
1233{
1234 int i;
1235 int maxi;
1236
1237 printk(KERN_DEBUG "%s: %s(): dest %pM, length %d\n",
1238 msg1, msg2, p, length);
1239 printk(KERN_DEBUG "%s: %s(): src %pM, type 0x%02X%02X\n",
1240 msg1, msg2, &p[6], p[12], p[13]);
1241
1242#ifdef DEBUG_PACKET_DUMP
1243
1244 printk(KERN_DEBUG "data=\"");
1245
1246 if((maxi = length) > DEBUG_PACKET_DUMP)
1247 maxi = DEBUG_PACKET_DUMP;
1248 for(i = 14; i < maxi; i++)
1249 if(p[i] >= ' ' && p[i] <= '~')
1250 printk(" %c", p[i]);
1251 else
1252 printk("%02X", p[i]);
1253 if(maxi < length)
1254 printk("..");
1255 printk("\"\n");
1256 printk(KERN_DEBUG "\n");
1257#endif
1258}
1259#endif
1260
1261
1262
1263
1264
1265
1266static void
1267wv_init_info(struct net_device * dev)
1268{
1269 unsigned int base = dev->base_addr;
1270 psa_t psa;
1271
1272
1273 psa_read(dev, 0, (unsigned char *) &psa, sizeof(psa));
1274
1275#ifdef DEBUG_PSA_SHOW
1276 wv_psa_show(&psa);
1277#endif
1278#ifdef DEBUG_MMC_SHOW
1279 wv_mmc_show(dev);
1280#endif
1281#ifdef DEBUG_I82593_SHOW
1282 wv_ru_show(dev);
1283#endif
1284
1285#ifdef DEBUG_BASIC_SHOW
1286
1287 printk(KERN_NOTICE "%s: WaveLAN: port %#x, irq %d, hw_addr %pM",
1288 dev->name, base, dev->irq, dev->dev_addr);
1289
1290
1291 if(psa.psa_nwid_select)
1292 printk(", nwid 0x%02X-%02X", psa.psa_nwid[0], psa.psa_nwid[1]);
1293 else
1294 printk(", nwid off");
1295
1296
1297 if(!(mmc_in(base, mmroff(0, mmr_fee_status)) &
1298 (MMR_FEE_STATUS_DWLD | MMR_FEE_STATUS_BUSY)))
1299 {
1300 unsigned short freq;
1301
1302
1303 fee_read(base, 0x00 ,
1304 &freq, 1);
1305
1306
1307 printk(", 2.00, %ld", (freq >> 6) + 2400L);
1308
1309
1310 if(freq & 0x20)
1311 printk(".5");
1312 }
1313 else
1314 {
1315 printk(", PCMCIA, ");
1316 switch (psa.psa_subband)
1317 {
1318 case PSA_SUBBAND_915:
1319 printk("915");
1320 break;
1321 case PSA_SUBBAND_2425:
1322 printk("2425");
1323 break;
1324 case PSA_SUBBAND_2460:
1325 printk("2460");
1326 break;
1327 case PSA_SUBBAND_2484:
1328 printk("2484");
1329 break;
1330 case PSA_SUBBAND_2430_5:
1331 printk("2430.5");
1332 break;
1333 default:
1334 printk("unknown");
1335 }
1336 }
1337
1338 printk(" MHz\n");
1339#endif
1340
1341#ifdef DEBUG_VERSION_SHOW
1342
1343 printk(KERN_NOTICE "%s", version);
1344#endif
1345}
1346
1347
1348
1349
1350
1351
1352
1353
1354
1355
1356
1357
1358
1359
1360
1361
1362
1363
1364
1365static void
1366wavelan_set_multicast_list(struct net_device * dev)
1367{
1368 net_local * lp = netdev_priv(dev);
1369
1370#ifdef DEBUG_IOCTL_TRACE
1371 printk(KERN_DEBUG "%s: ->wavelan_set_multicast_list()\n", dev->name);
1372#endif
1373
1374#ifdef DEBUG_IOCTL_INFO
1375 printk(KERN_DEBUG "%s: wavelan_set_multicast_list(): setting Rx mode %02X to %d addresses.\n",
1376 dev->name, dev->flags, dev->mc_count);
1377#endif
1378
1379 if(dev->flags & IFF_PROMISC)
1380 {
1381
1382
1383
1384 if(!lp->promiscuous)
1385 {
1386 lp->promiscuous = 1;
1387 lp->allmulticast = 0;
1388 lp->mc_count = 0;
1389
1390 wv_82593_reconfig(dev);
1391 }
1392 }
1393 else
1394
1395
1396 if((dev->flags & IFF_ALLMULTI) ||
1397 (dev->mc_count > I82593_MAX_MULTICAST_ADDRESSES))
1398 {
1399
1400
1401
1402 if(!lp->allmulticast)
1403 {
1404 lp->promiscuous = 0;
1405 lp->allmulticast = 1;
1406 lp->mc_count = 0;
1407
1408 wv_82593_reconfig(dev);
1409 }
1410 }
1411 else
1412
1413 if(dev->mc_list != (struct dev_mc_list *) NULL)
1414 {
1415
1416
1417
1418
1419#ifdef MULTICAST_AVOID
1420 if(lp->promiscuous || lp->allmulticast ||
1421 (dev->mc_count != lp->mc_count))
1422#endif
1423 {
1424 lp->promiscuous = 0;
1425 lp->allmulticast = 0;
1426 lp->mc_count = dev->mc_count;
1427
1428 wv_82593_reconfig(dev);
1429 }
1430 }
1431 else
1432 {
1433
1434
1435
1436
1437 if(lp->promiscuous || lp->mc_count == 0)
1438 {
1439 lp->promiscuous = 0;
1440 lp->allmulticast = 0;
1441 lp->mc_count = 0;
1442
1443 wv_82593_reconfig(dev);
1444 }
1445 }
1446#ifdef DEBUG_IOCTL_TRACE
1447 printk(KERN_DEBUG "%s: <-wavelan_set_multicast_list()\n", dev->name);
1448#endif
1449}
1450
1451
1452
1453
1454
1455
1456#ifdef SET_MAC_ADDRESS
1457static int
1458wavelan_set_mac_address(struct net_device * dev,
1459 void * addr)
1460{
1461 struct sockaddr * mac = addr;
1462
1463
1464 memcpy(dev->dev_addr, mac->sa_data, WAVELAN_ADDR_SIZE);
1465
1466
1467 wv_82593_reconfig(dev);
1468
1469 return 0;
1470}
1471#endif
1472
1473
1474
1475
1476
1477
1478
1479static int
1480wv_set_frequency(u_long base,
1481 iw_freq * frequency)
1482{
1483 const int BAND_NUM = 10;
1484 long freq = 0L;
1485#ifdef DEBUG_IOCTL_INFO
1486 int i;
1487#endif
1488
1489
1490
1491
1492
1493
1494 if((frequency->e == 1) &&
1495 (frequency->m >= (int) 2.412e8) && (frequency->m <= (int) 2.487e8))
1496 {
1497 freq = ((frequency->m / 10000) - 24000L) / 5;
1498 }
1499
1500
1501
1502
1503 if((frequency->e == 0) &&
1504 (frequency->m >= 0) && (frequency->m < BAND_NUM))
1505 {
1506
1507 freq = channel_bands[frequency->m] >> 1;
1508 }
1509
1510
1511 if(freq != 0L)
1512 {
1513 u_short table[10];
1514
1515
1516 fee_read(base, 0x71 ,
1517 table, 10);
1518
1519#ifdef DEBUG_IOCTL_INFO
1520 printk(KERN_DEBUG "Frequency table :");
1521 for(i = 0; i < 10; i++)
1522 {
1523 printk(" %04X",
1524 table[i]);
1525 }
1526 printk("\n");
1527#endif
1528
1529
1530 if(!(table[9 - ((freq - 24) / 16)] &
1531 (1 << ((freq - 24) % 16))))
1532 return -EINVAL;
1533 }
1534 else
1535 return -EINVAL;
1536
1537
1538 if(freq != 0L)
1539 {
1540 unsigned short area[16];
1541 unsigned short dac[2];
1542 unsigned short area_verify[16];
1543 unsigned short dac_verify[2];
1544
1545
1546
1547 unsigned short power_limit[] = { 40, 80, 120, 160, 0 };
1548 int power_band = 0;
1549 unsigned short power_adjust;
1550
1551
1552 power_band = 0;
1553 while((freq > power_limit[power_band]) &&
1554 (power_limit[++power_band] != 0))
1555 ;
1556
1557
1558 fee_read(base, 0x00,
1559 area, 16);
1560
1561
1562 fee_read(base, 0x60,
1563 dac, 2);
1564
1565
1566 fee_read(base, 0x6B - (power_band >> 1),
1567 &power_adjust, 1);
1568 if(power_band & 0x1)
1569 power_adjust >>= 8;
1570 else
1571 power_adjust &= 0xFF;
1572
1573#ifdef DEBUG_IOCTL_INFO
1574 printk(KERN_DEBUG "Wavelan EEprom Area 1 :");
1575 for(i = 0; i < 16; i++)
1576 {
1577 printk(" %04X",
1578 area[i]);
1579 }
1580 printk("\n");
1581
1582 printk(KERN_DEBUG "Wavelan EEprom DAC : %04X %04X\n",
1583 dac[0], dac[1]);
1584#endif
1585
1586
1587 area[0] = ((freq << 5) & 0xFFE0) | (area[0] & 0x1F);
1588
1589
1590 area[3] = (freq >> 1) + 2400L - 352L;
1591 area[2] = ((freq & 0x1) << 4) | (area[2] & 0xFFEF);
1592
1593
1594 area[13] = (freq >> 1) + 2400L;
1595 area[12] = ((freq & 0x1) << 4) | (area[2] & 0xFFEF);
1596
1597
1598
1599
1600 dac[1] = ((power_adjust >> 1) & 0x7F) | (dac[1] & 0xFF80);
1601 dac[0] = ((power_adjust & 0x1) << 4) | (dac[0] & 0xFFEF);
1602
1603
1604 fee_write(base, 0x00,
1605 area, 16);
1606
1607
1608 fee_write(base, 0x60,
1609 dac, 2);
1610
1611
1612
1613
1614 fee_read(base, 0x00,
1615 area_verify, 16);
1616
1617
1618 fee_read(base, 0x60,
1619 dac_verify, 2);
1620
1621
1622 if(memcmp(area, area_verify, 16 * 2) ||
1623 memcmp(dac, dac_verify, 2 * 2))
1624 {
1625#ifdef DEBUG_IOCTL_ERROR
1626 printk(KERN_INFO "Wavelan: wv_set_frequency : unable to write new frequency to EEprom (?)\n");
1627#endif
1628 return -EOPNOTSUPP;
1629 }
1630
1631
1632
1633
1634
1635 mmc_out(base, mmwoff(0, mmw_fee_addr), 0x0F);
1636 mmc_out(base, mmwoff(0, mmw_fee_ctrl),
1637 MMW_FEE_CTRL_READ | MMW_FEE_CTRL_DWLD);
1638
1639
1640 fee_wait(base, 100, 100);
1641
1642
1643
1644 mmc_out(base, mmwoff(0, mmw_fee_addr), 0x61);
1645 mmc_out(base, mmwoff(0, mmw_fee_ctrl),
1646 MMW_FEE_CTRL_READ | MMW_FEE_CTRL_DWLD);
1647
1648
1649 fee_wait(base, 100, 100);
1650
1651#ifdef DEBUG_IOCTL_INFO
1652
1653
1654 printk(KERN_DEBUG "Wavelan EEprom Area 1 :");
1655 for(i = 0; i < 16; i++)
1656 {
1657 printk(" %04X",
1658 area_verify[i]);
1659 }
1660 printk("\n");
1661
1662 printk(KERN_DEBUG "Wavelan EEprom DAC : %04X %04X\n",
1663 dac_verify[0], dac_verify[1]);
1664#endif
1665
1666 return 0;
1667 }
1668 else
1669 return -EINVAL;
1670}
1671
1672
1673
1674
1675
1676static int
1677wv_frequency_list(u_long base,
1678 iw_freq * list,
1679 int max)
1680{
1681 u_short table[10];
1682 long freq = 0L;
1683 int i;
1684 const int BAND_NUM = 10;
1685 int c = 0;
1686
1687
1688 fee_read(base, 0x71 ,
1689 table, 10);
1690
1691
1692 i = 0;
1693 for(freq = 0; freq < 150; freq++)
1694
1695 if(table[9 - (freq / 16)] & (1 << (freq % 16)))
1696 {
1697
1698 while((((channel_bands[c] >> 1) - 24) < freq) &&
1699 (c < BAND_NUM))
1700 c++;
1701 list[i].i = c;
1702
1703
1704 list[i].m = (((freq + 24) * 5) + 24000L) * 10000;
1705 list[i++].e = 1;
1706
1707
1708 if(i >= max)
1709 return(i);
1710 }
1711
1712 return(i);
1713}
1714
1715#ifdef IW_WIRELESS_SPY
1716
1717
1718
1719
1720
1721
1722static inline void
1723wl_spy_gather(struct net_device * dev,
1724 u_char * mac,
1725 u_char * stats)
1726{
1727 struct iw_quality wstats;
1728
1729 wstats.qual = stats[2] & MMR_SGNL_QUAL;
1730 wstats.level = stats[0] & MMR_SIGNAL_LVL;
1731 wstats.noise = stats[1] & MMR_SILENCE_LVL;
1732 wstats.updated = 0x7;
1733
1734
1735 wireless_spy_update(dev, mac, &wstats);
1736}
1737#endif
1738
1739#ifdef HISTOGRAM
1740
1741
1742
1743
1744
1745
1746
1747
1748
1749static inline void
1750wl_his_gather(struct net_device * dev,
1751 u_char * stats)
1752{
1753 net_local * lp = netdev_priv(dev);
1754 u_char level = stats[0] & MMR_SIGNAL_LVL;
1755 int i;
1756
1757
1758 i = 0;
1759 while((i < (lp->his_number - 1)) && (level >= lp->his_range[i++]))
1760 ;
1761
1762
1763 (lp->his_sum[i])++;
1764}
1765#endif
1766
1767static void wl_get_drvinfo(struct net_device *dev, struct ethtool_drvinfo *info)
1768{
1769 strncpy(info->driver, "wavelan_cs", sizeof(info->driver)-1);
1770}
1771
1772static const struct ethtool_ops ops = {
1773 .get_drvinfo = wl_get_drvinfo
1774};
1775
1776
1777
1778
1779
1780static int wavelan_get_name(struct net_device *dev,
1781 struct iw_request_info *info,
1782 union iwreq_data *wrqu,
1783 char *extra)
1784{
1785 strcpy(wrqu->name, "WaveLAN");
1786 return 0;
1787}
1788
1789
1790
1791
1792
1793static int wavelan_set_nwid(struct net_device *dev,
1794 struct iw_request_info *info,
1795 union iwreq_data *wrqu,
1796 char *extra)
1797{
1798 unsigned int base = dev->base_addr;
1799 net_local *lp = netdev_priv(dev);
1800 psa_t psa;
1801 mm_t m;
1802 unsigned long flags;
1803 int ret = 0;
1804
1805
1806 spin_lock_irqsave(&lp->spinlock, flags);
1807
1808
1809 if (!wrqu->nwid.disabled) {
1810
1811 psa.psa_nwid[0] = (wrqu->nwid.value & 0xFF00) >> 8;
1812 psa.psa_nwid[1] = wrqu->nwid.value & 0xFF;
1813 psa.psa_nwid_select = 0x01;
1814 psa_write(dev,
1815 (char *) psa.psa_nwid - (char *) &psa,
1816 (unsigned char *) psa.psa_nwid, 3);
1817
1818
1819 m.w.mmw_netw_id_l = psa.psa_nwid[1];
1820 m.w.mmw_netw_id_h = psa.psa_nwid[0];
1821 mmc_write(base,
1822 (char *) &m.w.mmw_netw_id_l -
1823 (char *) &m,
1824 (unsigned char *) &m.w.mmw_netw_id_l, 2);
1825 mmc_out(base, mmwoff(0, mmw_loopt_sel), 0x00);
1826 } else {
1827
1828 psa.psa_nwid_select = 0x00;
1829 psa_write(dev,
1830 (char *) &psa.psa_nwid_select -
1831 (char *) &psa,
1832 (unsigned char *) &psa.psa_nwid_select,
1833 1);
1834
1835
1836 mmc_out(base, mmwoff(0, mmw_loopt_sel),
1837 MMW_LOOPT_SEL_DIS_NWID);
1838 }
1839
1840 update_psa_checksum(dev);
1841
1842
1843 spin_unlock_irqrestore(&lp->spinlock, flags);
1844
1845 return ret;
1846}
1847
1848
1849
1850
1851
1852static int wavelan_get_nwid(struct net_device *dev,
1853 struct iw_request_info *info,
1854 union iwreq_data *wrqu,
1855 char *extra)
1856{
1857 net_local *lp = netdev_priv(dev);
1858 psa_t psa;
1859 unsigned long flags;
1860 int ret = 0;
1861
1862
1863 spin_lock_irqsave(&lp->spinlock, flags);
1864
1865
1866 psa_read(dev,
1867 (char *) psa.psa_nwid - (char *) &psa,
1868 (unsigned char *) psa.psa_nwid, 3);
1869 wrqu->nwid.value = (psa.psa_nwid[0] << 8) + psa.psa_nwid[1];
1870 wrqu->nwid.disabled = !(psa.psa_nwid_select);
1871 wrqu->nwid.fixed = 1;
1872
1873
1874 spin_unlock_irqrestore(&lp->spinlock, flags);
1875
1876 return ret;
1877}
1878
1879
1880
1881
1882
1883static int wavelan_set_freq(struct net_device *dev,
1884 struct iw_request_info *info,
1885 union iwreq_data *wrqu,
1886 char *extra)
1887{
1888 unsigned int base = dev->base_addr;
1889 net_local *lp = netdev_priv(dev);
1890 unsigned long flags;
1891 int ret;
1892
1893
1894 spin_lock_irqsave(&lp->spinlock, flags);
1895
1896
1897 if (!(mmc_in(base, mmroff(0, mmr_fee_status)) &
1898 (MMR_FEE_STATUS_DWLD | MMR_FEE_STATUS_BUSY)))
1899 ret = wv_set_frequency(base, &(wrqu->freq));
1900 else
1901 ret = -EOPNOTSUPP;
1902
1903
1904 spin_unlock_irqrestore(&lp->spinlock, flags);
1905
1906 return ret;
1907}
1908
1909
1910
1911
1912
1913static int wavelan_get_freq(struct net_device *dev,
1914 struct iw_request_info *info,
1915 union iwreq_data *wrqu,
1916 char *extra)
1917{
1918 unsigned int base = dev->base_addr;
1919 net_local *lp = netdev_priv(dev);
1920 psa_t psa;
1921 unsigned long flags;
1922 int ret = 0;
1923
1924
1925 spin_lock_irqsave(&lp->spinlock, flags);
1926
1927
1928
1929 if (!(mmc_in(base, mmroff(0, mmr_fee_status)) &
1930 (MMR_FEE_STATUS_DWLD | MMR_FEE_STATUS_BUSY))) {
1931 unsigned short freq;
1932
1933
1934 fee_read(base, 0x00, &freq, 1);
1935 wrqu->freq.m = ((freq >> 5) * 5 + 24000L) * 10000;
1936 wrqu->freq.e = 1;
1937 } else {
1938 psa_read(dev,
1939 (char *) &psa.psa_subband - (char *) &psa,
1940 (unsigned char *) &psa.psa_subband, 1);
1941
1942 if (psa.psa_subband <= 4) {
1943 wrqu->freq.m = fixed_bands[psa.psa_subband];
1944 wrqu->freq.e = (psa.psa_subband != 0);
1945 } else
1946 ret = -EOPNOTSUPP;
1947 }
1948
1949
1950 spin_unlock_irqrestore(&lp->spinlock, flags);
1951
1952 return ret;
1953}
1954
1955
1956
1957
1958
1959static int wavelan_set_sens(struct net_device *dev,
1960 struct iw_request_info *info,
1961 union iwreq_data *wrqu,
1962 char *extra)
1963{
1964 unsigned int base = dev->base_addr;
1965 net_local *lp = netdev_priv(dev);
1966 psa_t psa;
1967 unsigned long flags;
1968 int ret = 0;
1969
1970
1971 spin_lock_irqsave(&lp->spinlock, flags);
1972
1973
1974
1975
1976 psa.psa_thr_pre_set = wrqu->sens.value & 0x3F;
1977 psa_write(dev,
1978 (char *) &psa.psa_thr_pre_set - (char *) &psa,
1979 (unsigned char *) &psa.psa_thr_pre_set, 1);
1980
1981 update_psa_checksum(dev);
1982 mmc_out(base, mmwoff(0, mmw_thr_pre_set),
1983 psa.psa_thr_pre_set);
1984
1985
1986 spin_unlock_irqrestore(&lp->spinlock, flags);
1987
1988 return ret;
1989}
1990
1991
1992
1993
1994
1995static int wavelan_get_sens(struct net_device *dev,
1996 struct iw_request_info *info,
1997 union iwreq_data *wrqu,
1998 char *extra)
1999{
2000 net_local *lp = netdev_priv(dev);
2001 psa_t psa;
2002 unsigned long flags;
2003 int ret = 0;
2004
2005
2006 spin_lock_irqsave(&lp->spinlock, flags);
2007
2008
2009 psa_read(dev,
2010 (char *) &psa.psa_thr_pre_set - (char *) &psa,
2011 (unsigned char *) &psa.psa_thr_pre_set, 1);
2012 wrqu->sens.value = psa.psa_thr_pre_set & 0x3F;
2013 wrqu->sens.fixed = 1;
2014
2015
2016 spin_unlock_irqrestore(&lp->spinlock, flags);
2017
2018 return ret;
2019}
2020
2021
2022
2023
2024
2025static int wavelan_set_encode(struct net_device *dev,
2026 struct iw_request_info *info,
2027 union iwreq_data *wrqu,
2028 char *extra)
2029{
2030 unsigned int base = dev->base_addr;
2031 net_local *lp = netdev_priv(dev);
2032 unsigned long flags;
2033 psa_t psa;
2034 int ret = 0;
2035
2036
2037 spin_lock_irqsave(&lp->spinlock, flags);
2038
2039
2040 if (!mmc_encr(base)) {
2041 ret = -EOPNOTSUPP;
2042 }
2043
2044
2045 if((wrqu->encoding.length != 8) && (wrqu->encoding.length != 0)) {
2046 ret = -EINVAL;
2047 }
2048
2049 if(!ret) {
2050
2051 if (wrqu->encoding.length == 8) {
2052
2053 memcpy(psa.psa_encryption_key, extra,
2054 wrqu->encoding.length);
2055 psa.psa_encryption_select = 1;
2056
2057 psa_write(dev,
2058 (char *) &psa.psa_encryption_select -
2059 (char *) &psa,
2060 (unsigned char *) &psa.
2061 psa_encryption_select, 8 + 1);
2062
2063 mmc_out(base, mmwoff(0, mmw_encr_enable),
2064 MMW_ENCR_ENABLE_EN | MMW_ENCR_ENABLE_MODE);
2065 mmc_write(base, mmwoff(0, mmw_encr_key),
2066 (unsigned char *) &psa.
2067 psa_encryption_key, 8);
2068 }
2069
2070
2071 if (wrqu->encoding.flags & IW_ENCODE_DISABLED) {
2072 psa.psa_encryption_select = 0;
2073 psa_write(dev,
2074 (char *) &psa.psa_encryption_select -
2075 (char *) &psa,
2076 (unsigned char *) &psa.
2077 psa_encryption_select, 1);
2078
2079 mmc_out(base, mmwoff(0, mmw_encr_enable), 0);
2080 }
2081
2082 update_psa_checksum(dev);
2083 }
2084
2085
2086 spin_unlock_irqrestore(&lp->spinlock, flags);
2087
2088 return ret;
2089}
2090
2091
2092
2093
2094
2095static int wavelan_get_encode(struct net_device *dev,
2096 struct iw_request_info *info,
2097 union iwreq_data *wrqu,
2098 char *extra)
2099{
2100 unsigned int base = dev->base_addr;
2101 net_local *lp = netdev_priv(dev);
2102 psa_t psa;
2103 unsigned long flags;
2104 int ret = 0;
2105
2106
2107 spin_lock_irqsave(&lp->spinlock, flags);
2108
2109
2110 if (!mmc_encr(base)) {
2111 ret = -EOPNOTSUPP;
2112 } else {
2113
2114 psa_read(dev,
2115 (char *) &psa.psa_encryption_select -
2116 (char *) &psa,
2117 (unsigned char *) &psa.
2118 psa_encryption_select, 1 + 8);
2119
2120
2121 if (psa.psa_encryption_select)
2122 wrqu->encoding.flags = IW_ENCODE_ENABLED;
2123 else
2124 wrqu->encoding.flags = IW_ENCODE_DISABLED;
2125 wrqu->encoding.flags |= mmc_encr(base);
2126
2127
2128 wrqu->encoding.length = 8;
2129 memcpy(extra, psa.psa_encryption_key, wrqu->encoding.length);
2130 }
2131
2132
2133 spin_unlock_irqrestore(&lp->spinlock, flags);
2134
2135 return ret;
2136}
2137
2138#ifdef WAVELAN_ROAMING_EXT
2139
2140
2141
2142
2143static int wavelan_set_essid(struct net_device *dev,
2144 struct iw_request_info *info,
2145 union iwreq_data *wrqu,
2146 char *extra)
2147{
2148 net_local *lp = netdev_priv(dev);
2149 unsigned long flags;
2150 int ret = 0;
2151
2152
2153 spin_lock_irqsave(&lp->spinlock, flags);
2154
2155
2156 if(wrqu->data.flags == 0)
2157 lp->filter_domains = 0;
2158 else {
2159 char essid[IW_ESSID_MAX_SIZE + 1];
2160 char * endp;
2161
2162
2163 memcpy(essid, extra, wrqu->data.length);
2164 essid[IW_ESSID_MAX_SIZE] = '\0';
2165
2166#ifdef DEBUG_IOCTL_INFO
2167 printk(KERN_DEBUG "SetEssid : ``%s''\n", essid);
2168#endif
2169
2170
2171 lp->domain_id = simple_strtoul(essid, &endp, 16);
2172
2173 if(endp > essid)
2174 lp->filter_domains = 1;
2175 else {
2176 lp->filter_domains = 0;
2177 ret = -EINVAL;
2178 }
2179 }
2180
2181
2182 spin_unlock_irqrestore(&lp->spinlock, flags);
2183
2184 return ret;
2185}
2186
2187
2188
2189
2190
2191static int wavelan_get_essid(struct net_device *dev,
2192 struct iw_request_info *info,
2193 union iwreq_data *wrqu,
2194 char *extra)
2195{
2196 net_local *lp = netdev_priv(dev);
2197
2198
2199 wrqu->data.flags = lp->filter_domains;
2200
2201
2202
2203 sprintf(extra, "%lX", lp->domain_id);
2204 extra[IW_ESSID_MAX_SIZE] = '\0';
2205
2206
2207 wrqu->data.length = strlen(extra);
2208
2209 return 0;
2210}
2211
2212
2213
2214
2215
2216static int wavelan_set_wap(struct net_device *dev,
2217 struct iw_request_info *info,
2218 union iwreq_data *wrqu,
2219 char *extra)
2220{
2221#ifdef DEBUG_IOCTL_INFO
2222 printk(KERN_DEBUG "Set AP to : %pM\n", wrqu->ap_addr.sa_data);
2223#endif
2224
2225 return -EOPNOTSUPP;
2226}
2227
2228
2229
2230
2231
2232static int wavelan_get_wap(struct net_device *dev,
2233 struct iw_request_info *info,
2234 union iwreq_data *wrqu,
2235 char *extra)
2236{
2237
2238 memcpy(wrqu->ap_addr.sa_data, dev->dev_addr, WAVELAN_ADDR_SIZE);
2239 wrqu->ap_addr.sa_family = ARPHRD_ETHER;
2240
2241 return -EOPNOTSUPP;
2242}
2243#endif
2244
2245#ifdef WAVELAN_ROAMING
2246
2247
2248
2249
2250static int wavelan_set_mode(struct net_device *dev,
2251 struct iw_request_info *info,
2252 union iwreq_data *wrqu,
2253 char *extra)
2254{
2255 net_local *lp = netdev_priv(dev);
2256 unsigned long flags;
2257 int ret = 0;
2258
2259
2260 spin_lock_irqsave(&lp->spinlock, flags);
2261
2262
2263 switch(wrqu->mode) {
2264 case IW_MODE_ADHOC:
2265 if(do_roaming) {
2266 wv_roam_cleanup(dev);
2267 do_roaming = 0;
2268 }
2269 break;
2270 case IW_MODE_INFRA:
2271 if(!do_roaming) {
2272 wv_roam_init(dev);
2273 do_roaming = 1;
2274 }
2275 break;
2276 default:
2277 ret = -EINVAL;
2278 }
2279
2280
2281 spin_unlock_irqrestore(&lp->spinlock, flags);
2282
2283 return ret;
2284}
2285
2286
2287
2288
2289
2290static int wavelan_get_mode(struct net_device *dev,
2291 struct iw_request_info *info,
2292 union iwreq_data *wrqu,
2293 char *extra)
2294{
2295 if(do_roaming)
2296 wrqu->mode = IW_MODE_INFRA;
2297 else
2298 wrqu->mode = IW_MODE_ADHOC;
2299
2300 return 0;
2301}
2302#endif
2303
2304
2305
2306
2307
2308static int wavelan_get_range(struct net_device *dev,
2309 struct iw_request_info *info,
2310 union iwreq_data *wrqu,
2311 char *extra)
2312{
2313 unsigned int base = dev->base_addr;
2314 net_local *lp = netdev_priv(dev);
2315 struct iw_range *range = (struct iw_range *) extra;
2316 unsigned long flags;
2317 int ret = 0;
2318
2319
2320 wrqu->data.length = sizeof(struct iw_range);
2321
2322
2323 memset(range, 0, sizeof(struct iw_range));
2324
2325
2326 range->we_version_compiled = WIRELESS_EXT;
2327 range->we_version_source = 9;
2328
2329
2330 range->throughput = 1.4 * 1000 * 1000;
2331 range->min_nwid = 0x0000;
2332 range->max_nwid = 0xFFFF;
2333
2334 range->sensitivity = 0x3F;
2335 range->max_qual.qual = MMR_SGNL_QUAL;
2336 range->max_qual.level = MMR_SIGNAL_LVL;
2337 range->max_qual.noise = MMR_SILENCE_LVL;
2338 range->avg_qual.qual = MMR_SGNL_QUAL;
2339
2340 range->avg_qual.level = 30;
2341 range->avg_qual.noise = 8;
2342
2343 range->num_bitrates = 1;
2344 range->bitrate[0] = 2000000;
2345
2346
2347 range->event_capa[0] = (IW_EVENT_CAPA_MASK(0x8B02) |
2348 IW_EVENT_CAPA_MASK(0x8B04) |
2349 IW_EVENT_CAPA_MASK(0x8B06));
2350 range->event_capa[1] = IW_EVENT_CAPA_K_1;
2351
2352
2353 spin_lock_irqsave(&lp->spinlock, flags);
2354
2355
2356 if (!(mmc_in(base, mmroff(0, mmr_fee_status)) &
2357 (MMR_FEE_STATUS_DWLD | MMR_FEE_STATUS_BUSY))) {
2358 range->num_channels = 10;
2359 range->num_frequency = wv_frequency_list(base, range->freq,
2360 IW_MAX_FREQUENCIES);
2361 } else
2362 range->num_channels = range->num_frequency = 0;
2363
2364
2365 if (mmc_encr(base)) {
2366 range->encoding_size[0] = 8;
2367 range->num_encoding_sizes = 1;
2368 range->max_encoding_tokens = 1;
2369 } else {
2370 range->num_encoding_sizes = 0;
2371 range->max_encoding_tokens = 0;
2372 }
2373
2374
2375 spin_unlock_irqrestore(&lp->spinlock, flags);
2376
2377 return ret;
2378}
2379
2380
2381
2382
2383
2384static int wavelan_set_qthr(struct net_device *dev,
2385 struct iw_request_info *info,
2386 union iwreq_data *wrqu,
2387 char *extra)
2388{
2389 unsigned int base = dev->base_addr;
2390 net_local *lp = netdev_priv(dev);
2391 psa_t psa;
2392 unsigned long flags;
2393
2394
2395 spin_lock_irqsave(&lp->spinlock, flags);
2396
2397 psa.psa_quality_thr = *(extra) & 0x0F;
2398 psa_write(dev,
2399 (char *) &psa.psa_quality_thr - (char *) &psa,
2400 (unsigned char *) &psa.psa_quality_thr, 1);
2401
2402 update_psa_checksum(dev);
2403 mmc_out(base, mmwoff(0, mmw_quality_thr),
2404 psa.psa_quality_thr);
2405
2406
2407 spin_unlock_irqrestore(&lp->spinlock, flags);
2408
2409 return 0;
2410}
2411
2412
2413
2414
2415
2416static int wavelan_get_qthr(struct net_device *dev,
2417 struct iw_request_info *info,
2418 union iwreq_data *wrqu,
2419 char *extra)
2420{
2421 net_local *lp = netdev_priv(dev);
2422 psa_t psa;
2423 unsigned long flags;
2424
2425
2426 spin_lock_irqsave(&lp->spinlock, flags);
2427
2428 psa_read(dev,
2429 (char *) &psa.psa_quality_thr - (char *) &psa,
2430 (unsigned char *) &psa.psa_quality_thr, 1);
2431 *(extra) = psa.psa_quality_thr & 0x0F;
2432
2433
2434 spin_unlock_irqrestore(&lp->spinlock, flags);
2435
2436 return 0;
2437}
2438
2439#ifdef WAVELAN_ROAMING
2440
2441
2442
2443
2444static int wavelan_set_roam(struct net_device *dev,
2445 struct iw_request_info *info,
2446 union iwreq_data *wrqu,
2447 char *extra)
2448{
2449 net_local *lp = netdev_priv(dev);
2450 unsigned long flags;
2451
2452
2453 spin_lock_irqsave(&lp->spinlock, flags);
2454
2455
2456 if(do_roaming && (*extra)==0)
2457 wv_roam_cleanup(dev);
2458 else if(do_roaming==0 && (*extra)!=0)
2459 wv_roam_init(dev);
2460
2461 do_roaming = (*extra);
2462
2463
2464 spin_unlock_irqrestore(&lp->spinlock, flags);
2465
2466 return 0;
2467}
2468
2469
2470
2471
2472
2473static int wavelan_get_roam(struct net_device *dev,
2474 struct iw_request_info *info,
2475 union iwreq_data *wrqu,
2476 char *extra)
2477{
2478 *(extra) = do_roaming;
2479
2480 return 0;
2481}
2482#endif
2483
2484#ifdef HISTOGRAM
2485
2486
2487
2488
2489static int wavelan_set_histo(struct net_device *dev,
2490 struct iw_request_info *info,
2491 union iwreq_data *wrqu,
2492 char *extra)
2493{
2494 net_local *lp = netdev_priv(dev);
2495
2496
2497 if (wrqu->data.length > 16) {
2498 return(-E2BIG);
2499 }
2500
2501
2502
2503 lp->his_number = 0;
2504
2505
2506 if (wrqu->data.length > 0) {
2507
2508 memcpy(lp->his_range, extra, wrqu->data.length);
2509
2510 {
2511 int i;
2512 printk(KERN_DEBUG "Histo :");
2513 for(i = 0; i < wrqu->data.length; i++)
2514 printk(" %d", lp->his_range[i]);
2515 printk("\n");
2516 }
2517
2518
2519 memset(lp->his_sum, 0x00, sizeof(long) * 16);
2520 }
2521
2522
2523 lp->his_number = wrqu->data.length;
2524
2525 return(0);
2526}
2527
2528
2529
2530
2531
2532static int wavelan_get_histo(struct net_device *dev,
2533 struct iw_request_info *info,
2534 union iwreq_data *wrqu,
2535 char *extra)
2536{
2537 net_local *lp = netdev_priv(dev);
2538
2539
2540 wrqu->data.length = lp->his_number;
2541
2542
2543 if(lp->his_number > 0)
2544 memcpy(extra, lp->his_sum, sizeof(long) * lp->his_number);
2545
2546 return(0);
2547}
2548#endif
2549
2550
2551
2552
2553
2554
2555static const struct iw_priv_args wavelan_private_args[] = {
2556
2557 { SIOCSIPQTHR, IW_PRIV_TYPE_BYTE | IW_PRIV_SIZE_FIXED | 1, 0, "setqualthr" },
2558 { SIOCGIPQTHR, 0, IW_PRIV_TYPE_BYTE | IW_PRIV_SIZE_FIXED | 1, "getqualthr" },
2559 { SIOCSIPROAM, IW_PRIV_TYPE_BYTE | IW_PRIV_SIZE_FIXED | 1, 0, "setroam" },
2560 { SIOCGIPROAM, 0, IW_PRIV_TYPE_BYTE | IW_PRIV_SIZE_FIXED | 1, "getroam" },
2561 { SIOCSIPHISTO, IW_PRIV_TYPE_BYTE | 16, 0, "sethisto" },
2562 { SIOCGIPHISTO, 0, IW_PRIV_TYPE_INT | 16, "gethisto" },
2563};
2564
2565static const iw_handler wavelan_handler[] =
2566{
2567 NULL,
2568 wavelan_get_name,
2569 wavelan_set_nwid,
2570 wavelan_get_nwid,
2571 wavelan_set_freq,
2572 wavelan_get_freq,
2573#ifdef WAVELAN_ROAMING
2574 wavelan_set_mode,
2575 wavelan_get_mode,
2576#else
2577 NULL,
2578 NULL,
2579#endif
2580 wavelan_set_sens,
2581 wavelan_get_sens,
2582 NULL,
2583 wavelan_get_range,
2584 NULL,
2585 NULL,
2586 NULL,
2587 NULL,
2588 iw_handler_set_spy,
2589 iw_handler_get_spy,
2590 iw_handler_set_thrspy,
2591 iw_handler_get_thrspy,
2592#ifdef WAVELAN_ROAMING_EXT
2593 wavelan_set_wap,
2594 wavelan_get_wap,
2595 NULL,
2596 NULL,
2597 NULL,
2598 NULL,
2599 wavelan_set_essid,
2600 wavelan_get_essid,
2601#else
2602 NULL,
2603 NULL,
2604 NULL,
2605 NULL,
2606 NULL,
2607 NULL,
2608 NULL,
2609 NULL,
2610#endif
2611 NULL,
2612 NULL,
2613 NULL,
2614 NULL,
2615 NULL,
2616 NULL,
2617 NULL,
2618 NULL,
2619 NULL,
2620 NULL,
2621 NULL,
2622 NULL,
2623 NULL,
2624 NULL,
2625 wavelan_set_encode,
2626 wavelan_get_encode,
2627};
2628
2629static const iw_handler wavelan_private_handler[] =
2630{
2631 wavelan_set_qthr,
2632 wavelan_get_qthr,
2633#ifdef WAVELAN_ROAMING
2634 wavelan_set_roam,
2635 wavelan_get_roam,
2636#else
2637 NULL,
2638 NULL,
2639#endif
2640#ifdef HISTOGRAM
2641 wavelan_set_histo,
2642 wavelan_get_histo,
2643#endif
2644};
2645
2646static const struct iw_handler_def wavelan_handler_def =
2647{
2648 .num_standard = ARRAY_SIZE(wavelan_handler),
2649 .num_private = ARRAY_SIZE(wavelan_private_handler),
2650 .num_private_args = ARRAY_SIZE(wavelan_private_args),
2651 .standard = wavelan_handler,
2652 .private = wavelan_private_handler,
2653 .private_args = wavelan_private_args,
2654 .get_wireless_stats = wavelan_get_wireless_stats,
2655};
2656
2657
2658
2659
2660
2661
2662static iw_stats *
2663wavelan_get_wireless_stats(struct net_device * dev)
2664{
2665 unsigned int base = dev->base_addr;
2666 net_local * lp = netdev_priv(dev);
2667 mmr_t m;
2668 iw_stats * wstats;
2669 unsigned long flags;
2670
2671#ifdef DEBUG_IOCTL_TRACE
2672 printk(KERN_DEBUG "%s: ->wavelan_get_wireless_stats()\n", dev->name);
2673#endif
2674
2675
2676 spin_lock_irqsave(&lp->spinlock, flags);
2677
2678 wstats = &lp->wstats;
2679
2680
2681 mmc_out(base, mmwoff(0, mmw_freeze), 1);
2682
2683 mmc_read(base, mmroff(0, mmr_dce_status), &m.mmr_dce_status, 1);
2684 mmc_read(base, mmroff(0, mmr_wrong_nwid_l), &m.mmr_wrong_nwid_l, 2);
2685 mmc_read(base, mmroff(0, mmr_thr_pre_set), &m.mmr_thr_pre_set, 4);
2686
2687 mmc_out(base, mmwoff(0, mmw_freeze), 0);
2688
2689
2690 wstats->status = m.mmr_dce_status & MMR_DCE_STATUS;
2691 wstats->qual.qual = m.mmr_sgnl_qual & MMR_SGNL_QUAL;
2692 wstats->qual.level = m.mmr_signal_lvl & MMR_SIGNAL_LVL;
2693 wstats->qual.noise = m.mmr_silence_lvl & MMR_SILENCE_LVL;
2694 wstats->qual.updated = (((m.mmr_signal_lvl & MMR_SIGNAL_LVL_VALID) >> 7) |
2695 ((m.mmr_signal_lvl & MMR_SIGNAL_LVL_VALID) >> 6) |
2696 ((m.mmr_silence_lvl & MMR_SILENCE_LVL_VALID) >> 5));
2697 wstats->discard.nwid += (m.mmr_wrong_nwid_h << 8) | m.mmr_wrong_nwid_l;
2698 wstats->discard.code = 0L;
2699 wstats->discard.misc = 0L;
2700
2701
2702 spin_unlock_irqrestore(&lp->spinlock, flags);
2703
2704#ifdef DEBUG_IOCTL_TRACE
2705 printk(KERN_DEBUG "%s: <-wavelan_get_wireless_stats()\n", dev->name);
2706#endif
2707 return &lp->wstats;
2708}
2709
2710
2711
2712
2713
2714
2715
2716
2717
2718
2719
2720
2721
2722
2723static int
2724wv_start_of_frame(struct net_device * dev,
2725 int rfp,
2726 int wrap)
2727{
2728 unsigned int base = dev->base_addr;
2729 int rp;
2730 int len;
2731
2732 rp = (rfp - 5 + RX_SIZE) % RX_SIZE;
2733 outb(rp & 0xff, PIORL(base));
2734 outb(((rp >> 8) & PIORH_MASK), PIORH(base));
2735 len = inb(PIOP(base));
2736 len |= inb(PIOP(base)) << 8;
2737
2738
2739
2740 if(len > MAXDATAZ + 100)
2741 {
2742#ifdef DEBUG_RX_ERROR
2743 printk(KERN_INFO "%s: wv_start_of_frame: Received frame too large, rfp %d len 0x%x\n",
2744 dev->name, rfp, len);
2745#endif
2746 return(-1);
2747 }
2748
2749
2750 if(len < 7)
2751 {
2752#ifdef DEBUG_RX_ERROR
2753 printk(KERN_INFO "%s: wv_start_of_frame: Received null frame, rfp %d len 0x%x\n",
2754 dev->name, rfp, len);
2755#endif
2756 return(-1);
2757 }
2758
2759
2760 if(len > ((wrap - (rfp - len) + RX_SIZE) % RX_SIZE))
2761 {
2762#ifdef DEBUG_RX_ERROR
2763 printk(KERN_INFO "%s: wv_start_of_frame: wrap around buffer, wrap %d rfp %d len 0x%x\n",
2764 dev->name, wrap, rfp, len);
2765#endif
2766 return(-1);
2767 }
2768
2769 return((rp - len + RX_SIZE) % RX_SIZE);
2770}
2771
2772
2773
2774
2775
2776
2777
2778
2779
2780
2781
2782
2783
2784
2785static void
2786wv_packet_read(struct net_device * dev,
2787 int fd_p,
2788 int sksize)
2789{
2790 net_local * lp = netdev_priv(dev);
2791 struct sk_buff * skb;
2792
2793#ifdef DEBUG_RX_TRACE
2794 printk(KERN_DEBUG "%s: ->wv_packet_read(0x%X, %d)\n",
2795 dev->name, fd_p, sksize);
2796#endif
2797
2798
2799 if((skb = dev_alloc_skb(sksize+2)) == (struct sk_buff *) NULL)
2800 {
2801#ifdef DEBUG_RX_ERROR
2802 printk(KERN_INFO "%s: wv_packet_read(): could not alloc_skb(%d, GFP_ATOMIC)\n",
2803 dev->name, sksize);
2804#endif
2805 dev->stats.rx_dropped++;
2806
2807
2808
2809
2810 return;
2811 }
2812
2813 skb_reserve(skb, 2);
2814 fd_p = read_ringbuf(dev, fd_p, (char *) skb_put(skb, sksize), sksize);
2815 skb->protocol = eth_type_trans(skb, dev);
2816
2817#ifdef DEBUG_RX_INFO
2818 wv_packet_info(skb_mac_header(skb), sksize, dev->name, "wv_packet_read");
2819#endif
2820
2821
2822
2823 if(
2824#ifdef IW_WIRELESS_SPY
2825 (lp->spy_data.spy_number > 0) ||
2826#endif
2827#ifdef HISTOGRAM
2828 (lp->his_number > 0) ||
2829#endif
2830#ifdef WAVELAN_ROAMING
2831 (do_roaming) ||
2832#endif
2833 0)
2834 {
2835 u_char stats[3];
2836
2837
2838 fd_p = read_ringbuf(dev, (fd_p + 4) % RX_SIZE + RX_BASE,
2839 stats, 3);
2840#ifdef DEBUG_RX_INFO
2841 printk(KERN_DEBUG "%s: wv_packet_read(): Signal level %d/63, Silence level %d/63, signal quality %d/16\n",
2842 dev->name, stats[0] & 0x3F, stats[1] & 0x3F, stats[2] & 0x0F);
2843#endif
2844
2845#ifdef WAVELAN_ROAMING
2846 if(do_roaming)
2847 if(WAVELAN_BEACON(skb->data))
2848 wl_roam_gather(dev, skb->data, stats);
2849#endif
2850
2851#ifdef WIRELESS_SPY
2852 wl_spy_gather(dev, skb_mac_header(skb) + WAVELAN_ADDR_SIZE, stats);
2853#endif
2854#ifdef HISTOGRAM
2855 wl_his_gather(dev, stats);
2856#endif
2857 }
2858
2859
2860
2861
2862 netif_rx(skb);
2863
2864
2865 dev->stats.rx_packets++;
2866 dev->stats.rx_bytes += sksize;
2867
2868#ifdef DEBUG_RX_TRACE
2869 printk(KERN_DEBUG "%s: <-wv_packet_read()\n", dev->name);
2870#endif
2871 return;
2872}
2873
2874
2875
2876
2877
2878
2879
2880
2881
2882
2883
2884
2885static void
2886wv_packet_rcv(struct net_device * dev)
2887{
2888 unsigned int base = dev->base_addr;
2889 net_local * lp = netdev_priv(dev);
2890 int newrfp;
2891 int rp;
2892 int len;
2893 int f_start;
2894 int status;
2895 int i593_rfp;
2896 int stat_ptr;
2897 u_char c[4];
2898
2899#ifdef DEBUG_RX_TRACE
2900 printk(KERN_DEBUG "%s: ->wv_packet_rcv()\n", dev->name);
2901#endif
2902
2903
2904 outb(CR0_STATUS_2 | OP0_NOP, LCCR(base));
2905 i593_rfp = inb(LCSR(base));
2906 i593_rfp |= inb(LCSR(base)) << 8;
2907 i593_rfp %= RX_SIZE;
2908
2909
2910
2911
2912
2913
2914 newrfp = inb(RPLL(base));
2915 newrfp |= inb(RPLH(base)) << 8;
2916 newrfp %= RX_SIZE;
2917
2918#ifdef DEBUG_RX_INFO
2919 printk(KERN_DEBUG "%s: wv_packet_rcv(): i593_rfp %d stop %d newrfp %d lp->rfp %d\n",
2920 dev->name, i593_rfp, lp->stop, newrfp, lp->rfp);
2921#endif
2922
2923#ifdef DEBUG_RX_ERROR
2924
2925 if(lp->overrunning || newrfp == lp->rfp)
2926 printk(KERN_INFO "%s: wv_packet_rcv(): no new frame: i593_rfp %d stop %d newrfp %d lp->rfp %d\n",
2927 dev->name, i593_rfp, lp->stop, newrfp, lp->rfp);
2928#endif
2929
2930
2931 while(newrfp != lp->rfp)
2932 {
2933
2934
2935
2936
2937
2938
2939 rp = newrfp;
2940 while(((f_start = wv_start_of_frame(dev, rp, newrfp)) != lp->rfp) &&
2941 (f_start != -1))
2942 rp = f_start;
2943
2944
2945 if(f_start == -1)
2946 {
2947#ifdef DEBUG_RX_ERROR
2948 printk(KERN_INFO "wavelan_cs: cannot find start of frame ");
2949 printk(" i593_rfp %d stop %d newrfp %d lp->rfp %d\n",
2950 i593_rfp, lp->stop, newrfp, lp->rfp);
2951#endif
2952 lp->rfp = rp;
2953 continue;
2954 }
2955
2956
2957
2958
2959
2960 stat_ptr = (rp - 7 + RX_SIZE) % RX_SIZE;
2961 stat_ptr = read_ringbuf(dev, stat_ptr, c, 4);
2962 status = c[0] | (c[1] << 8);
2963 len = c[2] | (c[3] << 8);
2964
2965
2966 if((status & RX_RCV_OK) != RX_RCV_OK)
2967 {
2968 dev->stats.rx_errors++;
2969 if(status & RX_NO_SFD)
2970 dev->stats.rx_frame_errors++;
2971 if(status & RX_CRC_ERR)
2972 dev->stats.rx_crc_errors++;
2973 if(status & RX_OVRRUN)
2974 dev->stats.rx_over_errors++;
2975
2976#ifdef DEBUG_RX_FAIL
2977 printk(KERN_DEBUG "%s: wv_packet_rcv(): packet not received ok, status = 0x%x\n",
2978 dev->name, status);
2979#endif
2980 }
2981 else
2982
2983 wv_packet_read(dev, f_start, len - 2);
2984
2985
2986 lp->rfp = rp;
2987 }
2988
2989
2990
2991
2992
2993
2994 lp->stop = (i593_rfp + RX_SIZE - ((RX_SIZE / 64) * 3)) % RX_SIZE;
2995 outb(OP0_SWIT_TO_PORT_1 | CR0_CHNL, LCCR(base));
2996 outb(CR1_STOP_REG_UPDATE | (lp->stop >> RX_SIZE_SHIFT), LCCR(base));
2997 outb(OP1_SWIT_TO_PORT_0, LCCR(base));
2998
2999#ifdef DEBUG_RX_TRACE
3000 printk(KERN_DEBUG "%s: <-wv_packet_rcv()\n", dev->name);
3001#endif
3002}
3003
3004
3005
3006
3007
3008
3009
3010
3011
3012
3013
3014
3015
3016
3017
3018
3019static void
3020wv_packet_write(struct net_device * dev,
3021 void * buf,
3022 short length)
3023{
3024 net_local * lp = netdev_priv(dev);
3025 unsigned int base = dev->base_addr;
3026 unsigned long flags;
3027 int clen = length;
3028 register u_short xmtdata_base = TX_BASE;
3029
3030#ifdef DEBUG_TX_TRACE
3031 printk(KERN_DEBUG "%s: ->wv_packet_write(%d)\n", dev->name, length);
3032#endif
3033
3034 spin_lock_irqsave(&lp->spinlock, flags);
3035
3036
3037 outb(xmtdata_base & 0xff, PIORL(base));
3038 outb(((xmtdata_base >> 8) & PIORH_MASK) | PIORH_SEL_TX, PIORH(base));
3039 outb(clen & 0xff, PIOP(base));
3040 outb(clen >> 8, PIOP(base));
3041
3042
3043 outsb(PIOP(base), buf, clen);
3044
3045
3046 outb(OP0_NOP, PIOP(base));
3047
3048 outb(OP0_NOP, PIOP(base));
3049
3050
3051 hacr_write_slow(base, HACR_PWR_STAT | HACR_TX_DMA_RESET);
3052 hacr_write(base, HACR_DEFAULT);
3053
3054 wv_82593_cmd(dev, "wv_packet_write(): transmit",
3055 OP0_TRANSMIT, SR0_NO_RESULT);
3056
3057
3058 dev->trans_start = jiffies;
3059
3060
3061 dev->stats.tx_bytes += length;
3062
3063 spin_unlock_irqrestore(&lp->spinlock, flags);
3064
3065#ifdef DEBUG_TX_INFO
3066 wv_packet_info((u_char *) buf, length, dev->name, "wv_packet_write");
3067#endif
3068
3069#ifdef DEBUG_TX_TRACE
3070 printk(KERN_DEBUG "%s: <-wv_packet_write()\n", dev->name);
3071#endif
3072}
3073
3074
3075
3076
3077
3078
3079
3080
3081static netdev_tx_t
3082wavelan_packet_xmit(struct sk_buff * skb,
3083 struct net_device * dev)
3084{
3085 net_local * lp = netdev_priv(dev);
3086 unsigned long flags;
3087
3088#ifdef DEBUG_TX_TRACE
3089 printk(KERN_DEBUG "%s: ->wavelan_packet_xmit(0x%X)\n", dev->name,
3090 (unsigned) skb);
3091#endif
3092
3093
3094
3095
3096
3097 netif_stop_queue(dev);
3098
3099
3100
3101 if(lp->reconfig_82593)
3102 {
3103 spin_lock_irqsave(&lp->spinlock, flags);
3104 wv_82593_config(dev);
3105 spin_unlock_irqrestore(&lp->spinlock, flags);
3106
3107
3108 }
3109
3110
3111
3112
3113
3114
3115 if (skb_padto(skb, ETH_ZLEN))
3116 return NETDEV_TX_OK;
3117
3118 wv_packet_write(dev, skb->data, skb->len);
3119
3120 dev_kfree_skb(skb);
3121
3122#ifdef DEBUG_TX_TRACE
3123 printk(KERN_DEBUG "%s: <-wavelan_packet_xmit()\n", dev->name);
3124#endif
3125 return NETDEV_TX_OK;
3126}
3127
3128
3129
3130
3131
3132
3133
3134
3135
3136
3137
3138static int
3139wv_mmc_init(struct net_device * dev)
3140{
3141 unsigned int base = dev->base_addr;
3142 psa_t psa;
3143 mmw_t m;
3144 int configured;
3145 int i;
3146
3147#ifdef DEBUG_CONFIG_TRACE
3148 printk(KERN_DEBUG "%s: ->wv_mmc_init()\n", dev->name);
3149#endif
3150
3151
3152 psa_read(dev, 0, (unsigned char *) &psa, sizeof(psa));
3153
3154
3155
3156
3157
3158
3159
3160 for (i = 0; i < ARRAY_SIZE(MAC_ADDRESSES); i++)
3161 if ((psa.psa_univ_mac_addr[0] == MAC_ADDRESSES[i][0]) &&
3162 (psa.psa_univ_mac_addr[1] == MAC_ADDRESSES[i][1]) &&
3163 (psa.psa_univ_mac_addr[2] == MAC_ADDRESSES[i][2]))
3164 break;
3165
3166
3167 if (i == ARRAY_SIZE(MAC_ADDRESSES))
3168 {
3169#ifdef DEBUG_CONFIG_ERRORS
3170 printk(KERN_WARNING "%s: wv_mmc_init(): Invalid MAC address: %02X:%02X:%02X:...\n",
3171 dev->name, psa.psa_univ_mac_addr[0],
3172 psa.psa_univ_mac_addr[1], psa.psa_univ_mac_addr[2]);
3173#endif
3174 return FALSE;
3175 }
3176
3177
3178 memcpy(&dev->dev_addr[0], &psa.psa_univ_mac_addr[0], WAVELAN_ADDR_SIZE);
3179
3180#ifdef USE_PSA_CONFIG
3181 configured = psa.psa_conf_status & 1;
3182#else
3183 configured = 0;
3184#endif
3185
3186
3187 if(!configured)
3188 {
3189
3190 psa.psa_nwid[0] = 0;
3191 psa.psa_nwid[1] = 0;
3192
3193
3194 psa.psa_nwid_select = 0;
3195
3196
3197 psa.psa_encryption_select = 0;
3198
3199
3200
3201
3202
3203
3204 if (psa.psa_comp_number & 1)
3205 psa.psa_thr_pre_set = 0x01;
3206 else
3207 psa.psa_thr_pre_set = 0x04;
3208 psa.psa_quality_thr = 0x03;
3209
3210
3211 psa.psa_conf_status |= 1;
3212
3213#ifdef USE_PSA_CONFIG
3214
3215 psa_write(dev, (char *)psa.psa_nwid - (char *)&psa,
3216 (unsigned char *)psa.psa_nwid, 4);
3217 psa_write(dev, (char *)&psa.psa_thr_pre_set - (char *)&psa,
3218 (unsigned char *)&psa.psa_thr_pre_set, 1);
3219 psa_write(dev, (char *)&psa.psa_quality_thr - (char *)&psa,
3220 (unsigned char *)&psa.psa_quality_thr, 1);
3221 psa_write(dev, (char *)&psa.psa_conf_status - (char *)&psa,
3222 (unsigned char *)&psa.psa_conf_status, 1);
3223
3224 update_psa_checksum(dev);
3225#endif
3226 }
3227
3228
3229 memset(&m, 0x00, sizeof(m));
3230
3231
3232 m.mmw_netw_id_l = psa.psa_nwid[1];
3233 m.mmw_netw_id_h = psa.psa_nwid[0];
3234
3235 if(psa.psa_nwid_select & 1)
3236 m.mmw_loopt_sel = 0x00;
3237 else
3238 m.mmw_loopt_sel = MMW_LOOPT_SEL_DIS_NWID;
3239
3240 memcpy(&m.mmw_encr_key, &psa.psa_encryption_key,
3241 sizeof(m.mmw_encr_key));
3242
3243 if(psa.psa_encryption_select)
3244 m.mmw_encr_enable = MMW_ENCR_ENABLE_EN | MMW_ENCR_ENABLE_MODE;
3245 else
3246 m.mmw_encr_enable = 0;
3247
3248 m.mmw_thr_pre_set = psa.psa_thr_pre_set & 0x3F;
3249 m.mmw_quality_thr = psa.psa_quality_thr & 0x0F;
3250
3251
3252
3253
3254
3255 m.mmw_jabber_enable = 0x01;
3256 m.mmw_anten_sel = MMW_ANTEN_SEL_ALG_EN;
3257 m.mmw_ifs = 0x20;
3258 m.mmw_mod_delay = 0x04;
3259 m.mmw_jam_time = 0x38;
3260
3261 m.mmw_des_io_invert = 0;
3262 m.mmw_freeze = 0;
3263 m.mmw_decay_prm = 0;
3264 m.mmw_decay_updat_prm = 0;
3265
3266
3267 mmc_write(base, 0, (u_char *)&m, sizeof(m));
3268
3269
3270
3271
3272
3273
3274
3275
3276
3277
3278
3279
3280
3281
3282
3283 if(!(mmc_in(base, mmroff(0, mmr_fee_status)) &
3284 (MMR_FEE_STATUS_DWLD | MMR_FEE_STATUS_BUSY)))
3285 {
3286
3287
3288
3289
3290 m.mmw_fee_addr = 0x0F;
3291 m.mmw_fee_ctrl = MMW_FEE_CTRL_READ | MMW_FEE_CTRL_DWLD;
3292 mmc_write(base, (char *)&m.mmw_fee_ctrl - (char *)&m,
3293 (unsigned char *)&m.mmw_fee_ctrl, 2);
3294
3295
3296 fee_wait(base, 100, 100);
3297
3298#ifdef DEBUG_CONFIG_INFO
3299
3300 mmc_read(base, (char *)&m.mmw_fee_data_l - (char *)&m,
3301 (unsigned char *)&m.mmw_fee_data_l, 2);
3302
3303
3304 printk(KERN_DEBUG "%s: Wavelan 2.00 recognised (frequency select) : Current frequency = %ld\n",
3305 dev->name,
3306 ((m.mmw_fee_data_h << 4) |
3307 (m.mmw_fee_data_l >> 4)) * 5 / 2 + 24000L);
3308#endif
3309
3310
3311
3312 m.mmw_fee_addr = 0x61;
3313 m.mmw_fee_ctrl = MMW_FEE_CTRL_READ | MMW_FEE_CTRL_DWLD;
3314 mmc_write(base, (char *)&m.mmw_fee_ctrl - (char *)&m,
3315 (unsigned char *)&m.mmw_fee_ctrl, 2);
3316
3317
3318 }
3319
3320#ifdef DEBUG_CONFIG_TRACE
3321 printk(KERN_DEBUG "%s: <-wv_mmc_init()\n", dev->name);
3322#endif
3323 return TRUE;
3324}
3325
3326
3327
3328
3329
3330
3331
3332static int
3333wv_ru_stop(struct net_device * dev)
3334{
3335 unsigned int base = dev->base_addr;
3336 net_local * lp = netdev_priv(dev);
3337 unsigned long flags;
3338 int status;
3339 int spin;
3340
3341#ifdef DEBUG_CONFIG_TRACE
3342 printk(KERN_DEBUG "%s: ->wv_ru_stop()\n", dev->name);
3343#endif
3344
3345 spin_lock_irqsave(&lp->spinlock, flags);
3346
3347
3348 wv_82593_cmd(dev, "wv_graceful_shutdown(): stop-rcv",
3349 OP0_STOP_RCV, SR0_NO_RESULT);
3350
3351
3352 spin = 300;
3353 do
3354 {
3355 udelay(10);
3356 outb(OP0_NOP | CR0_STATUS_3, LCCR(base));
3357 status = inb(LCSR(base));
3358 }
3359 while(((status & SR3_RCV_STATE_MASK) != SR3_RCV_IDLE) && (spin-- > 0));
3360
3361
3362 do
3363 {
3364 udelay(10);
3365 outb(OP0_NOP | CR0_STATUS_3, LCCR(base));
3366 status = inb(LCSR(base));
3367 }
3368 while(((status & SR3_EXEC_STATE_MASK) != SR3_EXEC_IDLE) && (spin-- > 0));
3369
3370 spin_unlock_irqrestore(&lp->spinlock, flags);
3371
3372
3373 if(spin <= 0)
3374 {
3375#ifdef DEBUG_CONFIG_ERRORS
3376 printk(KERN_INFO "%s: wv_ru_stop(): The chip doesn't want to stop...\n",
3377 dev->name);
3378#endif
3379 return FALSE;
3380 }
3381
3382#ifdef DEBUG_CONFIG_TRACE
3383 printk(KERN_DEBUG "%s: <-wv_ru_stop()\n", dev->name);
3384#endif
3385 return TRUE;
3386}
3387
3388
3389
3390
3391
3392
3393
3394
3395static int
3396wv_ru_start(struct net_device * dev)
3397{
3398 unsigned int base = dev->base_addr;
3399 net_local * lp = netdev_priv(dev);
3400 unsigned long flags;
3401
3402#ifdef DEBUG_CONFIG_TRACE
3403 printk(KERN_DEBUG "%s: ->wv_ru_start()\n", dev->name);
3404#endif
3405
3406
3407
3408
3409
3410
3411 if(!wv_ru_stop(dev))
3412 return FALSE;
3413
3414 spin_lock_irqsave(&lp->spinlock, flags);
3415
3416
3417
3418
3419 lp->rfp = 0;
3420 outb(OP0_SWIT_TO_PORT_1 | CR0_CHNL, LCCR(base));
3421
3422
3423 outb(OP1_RESET_RING_MNGMT, LCCR(base));
3424
3425#if 0
3426
3427
3428
3429#elif 0
3430
3431 lp->stop = 0;
3432#else
3433
3434 lp->stop = (0 + RX_SIZE - ((RX_SIZE / 64) * 3)) % RX_SIZE;
3435#endif
3436 outb(CR1_STOP_REG_UPDATE | (lp->stop >> RX_SIZE_SHIFT), LCCR(base));
3437 outb(OP1_INT_ENABLE, LCCR(base));
3438 outb(OP1_SWIT_TO_PORT_0, LCCR(base));
3439
3440
3441 hacr_write_slow(base, HACR_PWR_STAT | HACR_TX_DMA_RESET);
3442 hacr_write_slow(base, HACR_DEFAULT);
3443
3444
3445 wv_82593_cmd(dev, "wv_ru_start(): rcv-enable",
3446 CR0_CHNL | OP0_RCV_ENABLE, SR0_NO_RESULT);
3447
3448#ifdef DEBUG_I82593_SHOW
3449 {
3450 int status;
3451 int opri;
3452 int spin = 10000;
3453
3454
3455 do
3456 {
3457 outb(OP0_NOP | CR0_STATUS_3, LCCR(base));
3458 status = inb(LCSR(base));
3459 if(spin-- <= 0)
3460 break;
3461 }
3462 while(((status & SR3_RCV_STATE_MASK) != SR3_RCV_ACTIVE) &&
3463 ((status & SR3_RCV_STATE_MASK) != SR3_RCV_READY));
3464 printk(KERN_DEBUG "rcv status is 0x%x [i:%d]\n",
3465 (status & SR3_RCV_STATE_MASK), i);
3466 }
3467#endif
3468
3469 spin_unlock_irqrestore(&lp->spinlock, flags);
3470
3471#ifdef DEBUG_CONFIG_TRACE
3472 printk(KERN_DEBUG "%s: <-wv_ru_start()\n", dev->name);
3473#endif
3474 return TRUE;
3475}
3476
3477
3478
3479
3480
3481
3482
3483static int
3484wv_82593_config(struct net_device * dev)
3485{
3486 unsigned int base = dev->base_addr;
3487 net_local * lp = netdev_priv(dev);
3488 struct i82593_conf_block cfblk;
3489 int ret = TRUE;
3490
3491#ifdef DEBUG_CONFIG_TRACE
3492 printk(KERN_DEBUG "%s: ->wv_82593_config()\n", dev->name);
3493#endif
3494
3495
3496
3497
3498
3499 memset(&cfblk, 0x00, sizeof(struct i82593_conf_block));
3500 cfblk.d6mod = FALSE;
3501 cfblk.fifo_limit = 5;
3502 cfblk.forgnesi = FALSE;
3503 cfblk.fifo_32 = 1;
3504 cfblk.throttle_enb = FALSE;
3505 cfblk.contin = TRUE;
3506 cfblk.cntrxint = FALSE;
3507 cfblk.addr_len = WAVELAN_ADDR_SIZE;
3508 cfblk.acloc = TRUE;
3509 cfblk.preamb_len = 0;
3510 cfblk.loopback = FALSE;
3511 cfblk.lin_prio = 0;
3512 cfblk.exp_prio = 5;
3513 cfblk.bof_met = 1;
3514 cfblk.ifrm_spc = 0x20 >> 4;
3515 cfblk.slottim_low = 0x20 >> 5;
3516 cfblk.slottim_hi = 0x0;
3517 cfblk.max_retr = 15;
3518 cfblk.prmisc = ((lp->promiscuous) ? TRUE: FALSE);
3519 cfblk.bc_dis = FALSE;
3520 cfblk.crs_1 = TRUE;
3521 cfblk.nocrc_ins = FALSE;
3522 cfblk.crc_1632 = FALSE;
3523 cfblk.crs_cdt = FALSE;
3524 cfblk.cs_filter = 0;
3525 cfblk.crs_src = FALSE;
3526 cfblk.cd_filter = 0;
3527 cfblk.min_fr_len = ETH_ZLEN >> 2;
3528 cfblk.lng_typ = FALSE;
3529 cfblk.lng_fld = TRUE;
3530 cfblk.rxcrc_xf = TRUE;
3531 cfblk.artx = TRUE;
3532 cfblk.sarec = TRUE;
3533 cfblk.tx_jabber = TRUE;
3534 cfblk.hash_1 = FALSE;
3535 cfblk.lbpkpol = TRUE;
3536 cfblk.fdx = FALSE;
3537 cfblk.dummy_6 = 0x3f;
3538 cfblk.mult_ia = FALSE;
3539 cfblk.dis_bof = FALSE;
3540 cfblk.dummy_1 = TRUE;
3541 cfblk.tx_ifs_retrig = 3;
3542#ifdef MULTICAST_ALL
3543 cfblk.mc_all = (lp->allmulticast ? TRUE: FALSE);
3544#else
3545 cfblk.mc_all = FALSE;
3546#endif
3547 cfblk.rcv_mon = 0;
3548 cfblk.frag_acpt = TRUE;
3549 cfblk.tstrttrs = FALSE;
3550 cfblk.fretx = TRUE;
3551 cfblk.syncrqs = FALSE;
3552 cfblk.sttlen = TRUE;
3553 cfblk.rx_eop = TRUE;
3554 cfblk.tx_eop = TRUE;
3555 cfblk.rbuf_size = RX_SIZE>>11;
3556 cfblk.rcvstop = TRUE;
3557
3558#ifdef DEBUG_I82593_SHOW
3559 print_hex_dump(KERN_DEBUG, "wavelan_cs: config block: ", DUMP_PREFIX_NONE,
3560 16, 1, &cfblk, sizeof(struct i82593_conf_block), false);
3561#endif
3562
3563
3564 outb(TX_BASE & 0xff, PIORL(base));
3565 outb(((TX_BASE >> 8) & PIORH_MASK) | PIORH_SEL_TX, PIORH(base));
3566 outb(sizeof(struct i82593_conf_block) & 0xff, PIOP(base));
3567 outb(sizeof(struct i82593_conf_block) >> 8, PIOP(base));
3568 outsb(PIOP(base), (char *) &cfblk, sizeof(struct i82593_conf_block));
3569
3570
3571 hacr_write_slow(base, HACR_PWR_STAT | HACR_TX_DMA_RESET);
3572 hacr_write(base, HACR_DEFAULT);
3573 if(!wv_82593_cmd(dev, "wv_82593_config(): configure",
3574 OP0_CONFIGURE, SR0_CONFIGURE_DONE))
3575 ret = FALSE;
3576
3577
3578 outb(TX_BASE & 0xff, PIORL(base));
3579 outb(((TX_BASE >> 8) & PIORH_MASK) | PIORH_SEL_TX, PIORH(base));
3580 outb(WAVELAN_ADDR_SIZE, PIOP(base));
3581 outb(0, PIOP(base));
3582 outsb(PIOP(base), &dev->dev_addr[0], WAVELAN_ADDR_SIZE);
3583
3584
3585 hacr_write_slow(base, HACR_PWR_STAT | HACR_TX_DMA_RESET);
3586 hacr_write(base, HACR_DEFAULT);
3587 if(!wv_82593_cmd(dev, "wv_82593_config(): ia-setup",
3588 OP0_IA_SETUP, SR0_IA_SETUP_DONE))
3589 ret = FALSE;
3590
3591#ifdef WAVELAN_ROAMING
3592
3593
3594 if(do_roaming)
3595 dev_mc_add(dev,WAVELAN_BEACON_ADDRESS, WAVELAN_ADDR_SIZE, 1);
3596#endif
3597
3598
3599 if(lp->mc_count)
3600 {
3601 struct dev_mc_list * dmi;
3602 int addrs_len = WAVELAN_ADDR_SIZE * lp->mc_count;
3603
3604#ifdef DEBUG_CONFIG_INFO
3605 printk(KERN_DEBUG "%s: wv_hw_config(): set %d multicast addresses:\n",
3606 dev->name, lp->mc_count);
3607 for(dmi=dev->mc_list; dmi; dmi=dmi->next)
3608 printk(KERN_DEBUG " %pM\n", dmi->dmi_addr);
3609#endif
3610
3611
3612 outb(TX_BASE & 0xff, PIORL(base));
3613 outb(((TX_BASE >> 8) & PIORH_MASK) | PIORH_SEL_TX, PIORH(base));
3614 outb(addrs_len & 0xff, PIOP(base));
3615 outb((addrs_len >> 8), PIOP(base));
3616 for(dmi=dev->mc_list; dmi; dmi=dmi->next)
3617 outsb(PIOP(base), dmi->dmi_addr, dmi->dmi_addrlen);
3618
3619
3620 hacr_write_slow(base, HACR_PWR_STAT | HACR_TX_DMA_RESET);
3621 hacr_write(base, HACR_DEFAULT);
3622 if(!wv_82593_cmd(dev, "wv_82593_config(): mc-setup",
3623 OP0_MC_SETUP, SR0_MC_SETUP_DONE))
3624 ret = FALSE;
3625 lp->mc_count = dev->mc_count;
3626 }
3627
3628
3629 lp->reconfig_82593 = FALSE;
3630
3631#ifdef DEBUG_CONFIG_TRACE
3632 printk(KERN_DEBUG "%s: <-wv_82593_config()\n", dev->name);
3633#endif
3634 return(ret);
3635}
3636
3637
3638
3639
3640
3641
3642
3643
3644
3645
3646static int
3647wv_pcmcia_reset(struct net_device * dev)
3648{
3649 int i;
3650 conf_reg_t reg = { 0, CS_READ, CISREG_COR, 0 };
3651 struct pcmcia_device * link = ((net_local *)netdev_priv(dev))->link;
3652
3653#ifdef DEBUG_CONFIG_TRACE
3654 printk(KERN_DEBUG "%s: ->wv_pcmcia_reset()\n", dev->name);
3655#endif
3656
3657 i = pcmcia_access_configuration_register(link, ®);
3658 if (i != 0)
3659 {
3660 cs_error(link, AccessConfigurationRegister, i);
3661 return FALSE;
3662 }
3663
3664#ifdef DEBUG_CONFIG_INFO
3665 printk(KERN_DEBUG "%s: wavelan_pcmcia_reset(): Config reg is 0x%x\n",
3666 dev->name, (u_int) reg.Value);
3667#endif
3668
3669 reg.Action = CS_WRITE;
3670 reg.Value = reg.Value | COR_SW_RESET;
3671 i = pcmcia_access_configuration_register(link, ®);
3672 if (i != 0)
3673 {
3674 cs_error(link, AccessConfigurationRegister, i);
3675 return FALSE;
3676 }
3677
3678 reg.Action = CS_WRITE;
3679 reg.Value = COR_LEVEL_IRQ | COR_CONFIG;
3680 i = pcmcia_access_configuration_register(link, ®);
3681 if (i != 0)
3682 {
3683 cs_error(link, AccessConfigurationRegister, i);
3684 return FALSE;
3685 }
3686
3687#ifdef DEBUG_CONFIG_TRACE
3688 printk(KERN_DEBUG "%s: <-wv_pcmcia_reset()\n", dev->name);
3689#endif
3690 return TRUE;
3691}
3692
3693
3694
3695
3696
3697
3698
3699
3700
3701
3702
3703
3704
3705
3706
3707
3708static int
3709wv_hw_config(struct net_device * dev)
3710{
3711 net_local * lp = netdev_priv(dev);
3712 unsigned int base = dev->base_addr;
3713 unsigned long flags;
3714 int ret = FALSE;
3715
3716#ifdef DEBUG_CONFIG_TRACE
3717 printk(KERN_DEBUG "%s: ->wv_hw_config()\n", dev->name);
3718#endif
3719
3720
3721 BUILD_BUG_ON(sizeof(psa_t) != PSA_SIZE);
3722 BUILD_BUG_ON(sizeof(mmw_t) != MMW_SIZE);
3723 BUILD_BUG_ON(sizeof(mmr_t) != MMR_SIZE);
3724
3725
3726 if(wv_pcmcia_reset(dev) == FALSE)
3727 return FALSE;
3728
3729
3730 spin_lock_irqsave(&lp->spinlock, flags);
3731
3732
3733 do
3734 {
3735
3736
3737 hacr_write_slow(base, HACR_RESET);
3738 hacr_write(base, HACR_DEFAULT);
3739
3740
3741 if(hasr_read(base) & HASR_NO_CLK)
3742 {
3743#ifdef DEBUG_CONFIG_ERRORS
3744 printk(KERN_WARNING "%s: wv_hw_config(): modem not connected or not a wavelan card\n",
3745 dev->name);
3746#endif
3747 break;
3748 }
3749
3750
3751 if(wv_mmc_init(dev) == FALSE)
3752 {
3753#ifdef DEBUG_CONFIG_ERRORS
3754 printk(KERN_WARNING "%s: wv_hw_config(): Can't configure the modem\n",
3755 dev->name);
3756#endif
3757 break;
3758 }
3759
3760
3761 outb(OP0_RESET, LCCR(base));
3762 mdelay(1);
3763
3764
3765 if(wv_82593_config(dev) == FALSE)
3766 {
3767#ifdef DEBUG_CONFIG_ERRORS
3768 printk(KERN_INFO "%s: wv_hw_config(): i82593 init failed\n",
3769 dev->name);
3770#endif
3771 break;
3772 }
3773
3774
3775 if(wv_diag(dev) == FALSE)
3776 {
3777#ifdef DEBUG_CONFIG_ERRORS
3778 printk(KERN_INFO "%s: wv_hw_config(): i82593 diagnostic failed\n",
3779 dev->name);
3780#endif
3781 break;
3782 }
3783
3784
3785
3786
3787
3788
3789 lp->configured = 1;
3790 ret = TRUE;
3791 }
3792 while(0);
3793
3794
3795 spin_unlock_irqrestore(&lp->spinlock, flags);
3796
3797#ifdef DEBUG_CONFIG_TRACE
3798 printk(KERN_DEBUG "%s: <-wv_hw_config()\n", dev->name);
3799#endif
3800 return(ret);
3801}
3802
3803
3804
3805
3806
3807
3808
3809
3810
3811static void
3812wv_hw_reset(struct net_device * dev)
3813{
3814 net_local * lp = netdev_priv(dev);
3815
3816#ifdef DEBUG_CONFIG_TRACE
3817 printk(KERN_DEBUG "%s: ->wv_hw_reset()\n", dev->name);
3818#endif
3819
3820 lp->nresets++;
3821 lp->configured = 0;
3822
3823
3824 if(wv_hw_config(dev) == FALSE)
3825 return;
3826
3827
3828 wv_ru_start(dev);
3829
3830#ifdef DEBUG_CONFIG_TRACE
3831 printk(KERN_DEBUG "%s: <-wv_hw_reset()\n", dev->name);
3832#endif
3833}
3834
3835
3836
3837
3838
3839
3840
3841
3842static int
3843wv_pcmcia_config(struct pcmcia_device * link)
3844{
3845 struct net_device * dev = (struct net_device *) link->priv;
3846 int i;
3847 win_req_t req;
3848 memreq_t mem;
3849 net_local * lp = netdev_priv(dev);
3850
3851
3852#ifdef DEBUG_CONFIG_TRACE
3853 printk(KERN_DEBUG "->wv_pcmcia_config(0x%p)\n", link);
3854#endif
3855
3856 do
3857 {
3858 i = pcmcia_request_io(link, &link->io);
3859 if (i != 0)
3860 {
3861 cs_error(link, RequestIO, i);
3862 break;
3863 }
3864
3865
3866
3867
3868
3869 i = pcmcia_request_irq(link, &link->irq);
3870 if (i != 0)
3871 {
3872 cs_error(link, RequestIRQ, i);
3873 break;
3874 }
3875
3876
3877
3878
3879
3880 link->conf.ConfigIndex = 1;
3881 i = pcmcia_request_configuration(link, &link->conf);
3882 if (i != 0)
3883 {
3884 cs_error(link, RequestConfiguration, i);
3885 break;
3886 }
3887
3888
3889
3890
3891
3892
3893
3894 req.Attributes = WIN_DATA_WIDTH_8|WIN_MEMORY_TYPE_AM|WIN_ENABLE;
3895 req.Base = req.Size = 0;
3896 req.AccessSpeed = mem_speed;
3897 i = pcmcia_request_window(&link, &req, &link->win);
3898 if (i != 0)
3899 {
3900 cs_error(link, RequestWindow, i);
3901 break;
3902 }
3903
3904 lp->mem = ioremap(req.Base, req.Size);
3905 dev->mem_start = (u_long)lp->mem;
3906 dev->mem_end = dev->mem_start + req.Size;
3907
3908 mem.CardOffset = 0; mem.Page = 0;
3909 i = pcmcia_map_mem_page(link->win, &mem);
3910 if (i != 0)
3911 {
3912 cs_error(link, MapMemPage, i);
3913 break;
3914 }
3915
3916
3917 dev->irq = link->irq.AssignedIRQ;
3918 dev->base_addr = link->io.BasePort1;
3919 netif_start_queue(dev);
3920
3921#ifdef DEBUG_CONFIG_INFO
3922 printk(KERN_DEBUG "wv_pcmcia_config: MEMSTART %p IRQ %d IOPORT 0x%x\n",
3923 lp->mem, dev->irq, (u_int) dev->base_addr);
3924#endif
3925
3926 SET_NETDEV_DEV(dev, &handle_to_dev(link));
3927 i = register_netdev(dev);
3928 if(i != 0)
3929 {
3930#ifdef DEBUG_CONFIG_ERRORS
3931 printk(KERN_INFO "wv_pcmcia_config(): register_netdev() failed\n");
3932#endif
3933 break;
3934 }
3935 }
3936 while(0);
3937
3938
3939 if(i != 0)
3940 {
3941 wv_pcmcia_release(link);
3942 return FALSE;
3943 }
3944
3945 strcpy(((net_local *) netdev_priv(dev))->node.dev_name, dev->name);
3946 link->dev_node = &((net_local *) netdev_priv(dev))->node;
3947
3948#ifdef DEBUG_CONFIG_TRACE
3949 printk(KERN_DEBUG "<-wv_pcmcia_config()\n");
3950#endif
3951 return TRUE;
3952}
3953
3954
3955
3956
3957
3958
3959
3960static void
3961wv_pcmcia_release(struct pcmcia_device *link)
3962{
3963 struct net_device * dev = (struct net_device *) link->priv;
3964 net_local * lp = netdev_priv(dev);
3965
3966#ifdef DEBUG_CONFIG_TRACE
3967 printk(KERN_DEBUG "%s: -> wv_pcmcia_release(0x%p)\n", dev->name, link);
3968#endif
3969
3970 iounmap(lp->mem);
3971 pcmcia_disable_device(link);
3972
3973#ifdef DEBUG_CONFIG_TRACE
3974 printk(KERN_DEBUG "%s: <- wv_pcmcia_release()\n", dev->name);
3975#endif
3976}
3977
3978
3979
3980
3981
3982
3983
3984
3985
3986
3987
3988static irqreturn_t
3989wavelan_interrupt(int irq,
3990 void * dev_id)
3991{
3992 struct net_device * dev = dev_id;
3993 net_local * lp;
3994 unsigned int base;
3995 int status0;
3996 u_int tx_status;
3997
3998#ifdef DEBUG_INTERRUPT_TRACE
3999 printk(KERN_DEBUG "%s: ->wavelan_interrupt()\n", dev->name);
4000#endif
4001
4002 lp = netdev_priv(dev);
4003 base = dev->base_addr;
4004
4005#ifdef DEBUG_INTERRUPT_INFO
4006
4007 if(spin_is_locked(&lp->spinlock))
4008 printk(KERN_DEBUG
4009 "%s: wavelan_interrupt(): spinlock is already locked !!!\n",
4010 dev->name);
4011#endif
4012
4013
4014
4015
4016
4017 spin_lock(&lp->spinlock);
4018
4019
4020 while(1)
4021 {
4022
4023
4024
4025
4026 outb(CR0_STATUS_0 | OP0_NOP, LCCR(base));
4027 status0 = inb(LCSR(base));
4028
4029#ifdef DEBUG_INTERRUPT_INFO
4030 printk(KERN_DEBUG "status0 0x%x [%s => 0x%x]", status0,
4031 (status0&SR0_INTERRUPT)?"int":"no int",status0&~SR0_INTERRUPT);
4032 if(status0&SR0_INTERRUPT)
4033 {
4034 printk(" [%s => %d]\n", (status0 & SR0_CHNL) ? "chnl" :
4035 ((status0 & SR0_EXECUTION) ? "cmd" :
4036 ((status0 & SR0_RECEPTION) ? "recv" : "unknown")),
4037 (status0 & SR0_EVENT_MASK));
4038 }
4039 else
4040 printk("\n");
4041#endif
4042
4043
4044 if(!(status0 & SR0_INTERRUPT))
4045 break;
4046
4047
4048
4049
4050 if(((status0 & SR0_BOTH_RX_TX) == SR0_BOTH_RX_TX) ||
4051 ((status0 & SR0_BOTH_RX_TX) == 0x0))
4052 {
4053#ifdef DEBUG_INTERRUPT_INFO
4054 printk(KERN_INFO "%s: wv_interrupt(): bogus interrupt (or from dead card) : %X\n",
4055 dev->name, status0);
4056#endif
4057
4058 outb(CR0_INT_ACK | OP0_NOP, LCCR(base));
4059 break;
4060 }
4061
4062
4063
4064
4065
4066
4067
4068 if(status0 & SR0_RECEPTION)
4069 {
4070#ifdef DEBUG_INTERRUPT_INFO
4071 printk(KERN_DEBUG "%s: wv_interrupt(): receive\n", dev->name);
4072#endif
4073
4074 if((status0 & SR0_EVENT_MASK) == SR0_STOP_REG_HIT)
4075 {
4076#ifdef DEBUG_INTERRUPT_ERROR
4077 printk(KERN_INFO "%s: wv_interrupt(): receive buffer overflow\n",
4078 dev->name);
4079#endif
4080 dev->stats.rx_over_errors++;
4081 lp->overrunning = 1;
4082 }
4083
4084
4085 wv_packet_rcv(dev);
4086 lp->overrunning = 0;
4087
4088
4089 outb(CR0_INT_ACK | OP0_NOP, LCCR(base));
4090 continue;
4091 }
4092
4093
4094
4095
4096
4097
4098
4099
4100 if((status0 & SR0_EVENT_MASK) == SR0_TRANSMIT_DONE ||
4101 (status0 & SR0_EVENT_MASK) == SR0_RETRANSMIT_DONE ||
4102 (status0 & SR0_EVENT_MASK) == SR0_TRANSMIT_NO_CRC_DONE)
4103 {
4104#ifdef DEBUG_TX_ERROR
4105 if((status0 & SR0_EVENT_MASK) == SR0_TRANSMIT_NO_CRC_DONE)
4106 printk(KERN_INFO "%s: wv_interrupt(): packet transmitted without CRC.\n",
4107 dev->name);
4108#endif
4109
4110
4111 tx_status = inb(LCSR(base));
4112 tx_status |= (inb(LCSR(base)) << 8);
4113#ifdef DEBUG_INTERRUPT_INFO
4114 printk(KERN_DEBUG "%s: wv_interrupt(): transmission done\n",
4115 dev->name);
4116 {
4117 u_int rcv_bytes;
4118 u_char status3;
4119 rcv_bytes = inb(LCSR(base));
4120 rcv_bytes |= (inb(LCSR(base)) << 8);
4121 status3 = inb(LCSR(base));
4122 printk(KERN_DEBUG "tx_status 0x%02x rcv_bytes 0x%02x status3 0x%x\n",
4123 tx_status, rcv_bytes, (u_int) status3);
4124 }
4125#endif
4126
4127 if((tx_status & TX_OK) != TX_OK)
4128 {
4129 dev->stats.tx_errors++;
4130
4131 if(tx_status & TX_FRTL)
4132 {
4133#ifdef DEBUG_TX_ERROR
4134 printk(KERN_INFO "%s: wv_interrupt(): frame too long\n",
4135 dev->name);
4136#endif
4137 }
4138 if(tx_status & TX_UND_RUN)
4139 {
4140#ifdef DEBUG_TX_FAIL
4141 printk(KERN_DEBUG "%s: wv_interrupt(): DMA underrun\n",
4142 dev->name);
4143#endif
4144 dev->stats.tx_aborted_errors++;
4145 }
4146 if(tx_status & TX_LOST_CTS)
4147 {
4148#ifdef DEBUG_TX_FAIL
4149 printk(KERN_DEBUG "%s: wv_interrupt(): no CTS\n", dev->name);
4150#endif
4151 dev->stats.tx_carrier_errors++;
4152 }
4153 if(tx_status & TX_LOST_CRS)
4154 {
4155#ifdef DEBUG_TX_FAIL
4156 printk(KERN_DEBUG "%s: wv_interrupt(): no carrier\n",
4157 dev->name);
4158#endif
4159 dev->stats.tx_carrier_errors++;
4160 }
4161 if(tx_status & TX_HRT_BEAT)
4162 {
4163#ifdef DEBUG_TX_FAIL
4164 printk(KERN_DEBUG "%s: wv_interrupt(): heart beat\n", dev->name);
4165#endif
4166 dev->stats.tx_heartbeat_errors++;
4167 }
4168 if(tx_status & TX_DEFER)
4169 {
4170#ifdef DEBUG_TX_FAIL
4171 printk(KERN_DEBUG "%s: wv_interrupt(): channel jammed\n",
4172 dev->name);
4173#endif
4174 }
4175
4176
4177
4178
4179
4180 if(tx_status & TX_COLL)
4181 {
4182 if(tx_status & TX_MAX_COL)
4183 {
4184#ifdef DEBUG_TX_FAIL
4185 printk(KERN_DEBUG "%s: wv_interrupt(): channel congestion\n",
4186 dev->name);
4187#endif
4188 if(!(tx_status & TX_NCOL_MASK))
4189 {
4190 dev->stats.collisions += 0x10;
4191 }
4192 }
4193 }
4194 }
4195
4196 dev->stats.collisions += (tx_status & TX_NCOL_MASK);
4197 dev->stats.tx_packets++;
4198
4199 netif_wake_queue(dev);
4200 outb(CR0_INT_ACK | OP0_NOP, LCCR(base));
4201 }
4202 else
4203 {
4204#ifdef DEBUG_INTERRUPT_ERROR
4205 printk(KERN_INFO "wavelan_cs: unknown interrupt, status0 = %02x\n",
4206 status0);
4207#endif
4208 outb(CR0_INT_ACK | OP0_NOP, LCCR(base));
4209 }
4210 }
4211
4212 spin_unlock(&lp->spinlock);
4213
4214#ifdef DEBUG_INTERRUPT_TRACE
4215 printk(KERN_DEBUG "%s: <-wavelan_interrupt()\n", dev->name);
4216#endif
4217
4218
4219
4220
4221
4222
4223
4224
4225
4226
4227
4228
4229
4230
4231
4232
4233
4234 return IRQ_HANDLED;
4235}
4236
4237
4238
4239
4240
4241
4242
4243
4244
4245
4246
4247
4248
4249static void
4250wavelan_watchdog(struct net_device * dev)
4251{
4252 net_local * lp = netdev_priv(dev);
4253 unsigned int base = dev->base_addr;
4254 unsigned long flags;
4255 int aborted = FALSE;
4256
4257#ifdef DEBUG_INTERRUPT_TRACE
4258 printk(KERN_DEBUG "%s: ->wavelan_watchdog()\n", dev->name);
4259#endif
4260
4261#ifdef DEBUG_INTERRUPT_ERROR
4262 printk(KERN_INFO "%s: wavelan_watchdog: watchdog timer expired\n",
4263 dev->name);
4264#endif
4265
4266 spin_lock_irqsave(&lp->spinlock, flags);
4267
4268
4269 outb(OP0_ABORT, LCCR(base));
4270
4271
4272 if(wv_82593_cmd(dev, "wavelan_watchdog(): abort",
4273 OP0_NOP | CR0_STATUS_3, SR0_EXECUTION_ABORTED))
4274 aborted = TRUE;
4275
4276
4277 spin_unlock_irqrestore(&lp->spinlock, flags);
4278
4279
4280 if(!aborted)
4281 {
4282
4283#ifdef DEBUG_INTERRUPT_ERROR
4284 printk(KERN_INFO "%s: wavelan_watchdog: abort failed, trying reset\n",
4285 dev->name);
4286#endif
4287 wv_hw_reset(dev);
4288 }
4289
4290#ifdef DEBUG_PSA_SHOW
4291 {
4292 psa_t psa;
4293 psa_read(dev, 0, (unsigned char *) &psa, sizeof(psa));
4294 wv_psa_show(&psa);
4295 }
4296#endif
4297#ifdef DEBUG_MMC_SHOW
4298 wv_mmc_show(dev);
4299#endif
4300#ifdef DEBUG_I82593_SHOW
4301 wv_ru_show(dev);
4302#endif
4303
4304
4305 netif_wake_queue(dev);
4306
4307#ifdef DEBUG_INTERRUPT_TRACE
4308 printk(KERN_DEBUG "%s: <-wavelan_watchdog()\n", dev->name);
4309#endif
4310}
4311
4312
4313
4314
4315
4316
4317
4318
4319
4320
4321
4322
4323
4324static int
4325wavelan_open(struct net_device * dev)
4326{
4327 net_local * lp = netdev_priv(dev);
4328 struct pcmcia_device * link = lp->link;
4329 unsigned int base = dev->base_addr;
4330
4331#ifdef DEBUG_CALLBACK_TRACE
4332 printk(KERN_DEBUG "%s: ->wavelan_open(dev=0x%x)\n", dev->name,
4333 (unsigned int) dev);
4334#endif
4335
4336
4337 if(hasr_read(base) & HASR_NO_CLK)
4338 {
4339
4340 hacr_write(base, HACR_DEFAULT);
4341
4342
4343 if(hasr_read(base) & HASR_NO_CLK)
4344 {
4345#ifdef DEBUG_CONFIG_ERRORS
4346 printk(KERN_WARNING "%s: wavelan_open(): modem not connected\n",
4347 dev->name);
4348#endif
4349 return FALSE;
4350 }
4351 }
4352
4353
4354 if(!lp->configured)
4355 return FALSE;
4356 if(!wv_ru_start(dev))
4357 wv_hw_reset(dev);
4358 netif_start_queue(dev);
4359
4360
4361 link->open++;
4362
4363#ifdef WAVELAN_ROAMING
4364 if(do_roaming)
4365 wv_roam_init(dev);
4366#endif
4367
4368#ifdef DEBUG_CALLBACK_TRACE
4369 printk(KERN_DEBUG "%s: <-wavelan_open()\n", dev->name);
4370#endif
4371 return 0;
4372}
4373
4374
4375
4376
4377
4378
4379static int
4380wavelan_close(struct net_device * dev)
4381{
4382 struct pcmcia_device * link = ((net_local *)netdev_priv(dev))->link;
4383 unsigned int base = dev->base_addr;
4384
4385#ifdef DEBUG_CALLBACK_TRACE
4386 printk(KERN_DEBUG "%s: ->wavelan_close(dev=0x%x)\n", dev->name,
4387 (unsigned int) dev);
4388#endif
4389
4390
4391 if(!link->open)
4392 {
4393#ifdef DEBUG_CONFIG_INFO
4394 printk(KERN_DEBUG "%s: wavelan_close(): device not open\n", dev->name);
4395#endif
4396 return 0;
4397 }
4398
4399#ifdef WAVELAN_ROAMING
4400
4401 if(do_roaming)
4402 wv_roam_cleanup(dev);
4403#endif
4404
4405 link->open--;
4406
4407
4408 if(netif_running(dev))
4409 {
4410 netif_stop_queue(dev);
4411
4412
4413 wv_ru_stop(dev);
4414
4415
4416 hacr_write(base, HACR_DEFAULT & (~HACR_PWR_STAT));
4417 }
4418
4419#ifdef DEBUG_CALLBACK_TRACE
4420 printk(KERN_DEBUG "%s: <-wavelan_close()\n", dev->name);
4421#endif
4422 return 0;
4423}
4424
4425static const struct net_device_ops wavelan_netdev_ops = {
4426 .ndo_open = wavelan_open,
4427 .ndo_stop = wavelan_close,
4428 .ndo_start_xmit = wavelan_packet_xmit,
4429 .ndo_set_multicast_list = wavelan_set_multicast_list,
4430#ifdef SET_MAC_ADDRESS
4431 .ndo_set_mac_address = wavelan_set_mac_address,
4432#endif
4433 .ndo_tx_timeout = wavelan_watchdog,
4434 .ndo_change_mtu = eth_change_mtu,
4435 .ndo_validate_addr = eth_validate_addr,
4436};
4437
4438
4439
4440
4441
4442
4443
4444
4445
4446
4447
4448static int
4449wavelan_probe(struct pcmcia_device *p_dev)
4450{
4451 struct net_device * dev;
4452 net_local * lp;
4453 int ret;
4454
4455#ifdef DEBUG_CALLBACK_TRACE
4456 printk(KERN_DEBUG "-> wavelan_attach()\n");
4457#endif
4458
4459
4460 p_dev->io.NumPorts1 = 8;
4461 p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
4462 p_dev->io.IOAddrLines = 3;
4463
4464
4465 p_dev->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING | IRQ_HANDLE_PRESENT;
4466 p_dev->irq.IRQInfo1 = IRQ_LEVEL_ID;
4467 p_dev->irq.Handler = wavelan_interrupt;
4468
4469
4470 p_dev->conf.Attributes = CONF_ENABLE_IRQ;
4471 p_dev->conf.IntType = INT_MEMORY_AND_IO;
4472
4473
4474 dev = alloc_etherdev(sizeof(net_local));
4475 if (!dev)
4476 return -ENOMEM;
4477
4478 p_dev->priv = p_dev->irq.Instance = dev;
4479
4480 lp = netdev_priv(dev);
4481
4482
4483 lp->configured = 0;
4484 lp->reconfig_82593 = FALSE;
4485 lp->nresets = 0;
4486
4487 lp->promiscuous = 0;
4488 lp->allmulticast = 0;
4489 lp->mc_count = 0;
4490
4491
4492 spin_lock_init(&lp->spinlock);
4493
4494
4495 lp->dev = dev;
4496
4497
4498 dev->netdev_ops = &wavelan_netdev_ops;
4499 dev->watchdog_timeo = WATCHDOG_JIFFIES;
4500 SET_ETHTOOL_OPS(dev, &ops);
4501
4502 dev->wireless_handlers = &wavelan_handler_def;
4503 lp->wireless_data.spy_data = &lp->spy_data;
4504 dev->wireless_data = &lp->wireless_data;
4505
4506
4507 dev->mtu = WAVELAN_MTU;
4508
4509 ret = wv_pcmcia_config(p_dev);
4510 if (ret)
4511 return ret;
4512
4513 ret = wv_hw_config(dev);
4514 if (ret) {
4515 dev->irq = 0;
4516 pcmcia_disable_device(p_dev);
4517 return ret;
4518 }
4519
4520 wv_init_info(dev);
4521
4522#ifdef DEBUG_CALLBACK_TRACE
4523 printk(KERN_DEBUG "<- wavelan_attach()\n");
4524#endif
4525
4526 return 0;
4527}
4528
4529
4530
4531
4532
4533
4534
4535
4536static void
4537wavelan_detach(struct pcmcia_device *link)
4538{
4539#ifdef DEBUG_CALLBACK_TRACE
4540 printk(KERN_DEBUG "-> wavelan_detach(0x%p)\n", link);
4541#endif
4542
4543
4544 wv_pcmcia_release(link);
4545
4546
4547 if(link->priv)
4548 {
4549 struct net_device * dev = (struct net_device *) link->priv;
4550
4551
4552
4553 if (link->dev_node)
4554 unregister_netdev(dev);
4555 link->dev_node = NULL;
4556 ((net_local *)netdev_priv(dev))->link = NULL;
4557 ((net_local *)netdev_priv(dev))->dev = NULL;
4558 free_netdev(dev);
4559 }
4560
4561#ifdef DEBUG_CALLBACK_TRACE
4562 printk(KERN_DEBUG "<- wavelan_detach()\n");
4563#endif
4564}
4565
4566static int wavelan_suspend(struct pcmcia_device *link)
4567{
4568 struct net_device * dev = (struct net_device *) link->priv;
4569
4570
4571
4572
4573
4574
4575
4576
4577 wv_ru_stop(dev);
4578
4579 if (link->open)
4580 netif_device_detach(dev);
4581
4582
4583 hacr_write(dev->base_addr, HACR_DEFAULT & (~HACR_PWR_STAT));
4584
4585 return 0;
4586}
4587
4588static int wavelan_resume(struct pcmcia_device *link)
4589{
4590 struct net_device * dev = (struct net_device *) link->priv;
4591
4592 if (link->open) {
4593 wv_hw_reset(dev);
4594 netif_device_attach(dev);
4595 }
4596
4597 return 0;
4598}
4599
4600
4601static struct pcmcia_device_id wavelan_ids[] = {
4602 PCMCIA_DEVICE_PROD_ID12("AT&T","WaveLAN/PCMCIA", 0xe7c5affd, 0x1bc50975),
4603 PCMCIA_DEVICE_PROD_ID12("Digital", "RoamAbout/DS", 0x9999ab35, 0x00d05e06),
4604 PCMCIA_DEVICE_PROD_ID12("Lucent Technologies", "WaveLAN/PCMCIA", 0x23eb9949, 0x1bc50975),
4605 PCMCIA_DEVICE_PROD_ID12("NCR", "WaveLAN/PCMCIA", 0x24358cd4, 0x1bc50975),
4606 PCMCIA_DEVICE_NULL,
4607};
4608MODULE_DEVICE_TABLE(pcmcia, wavelan_ids);
4609
4610static struct pcmcia_driver wavelan_driver = {
4611 .owner = THIS_MODULE,
4612 .drv = {
4613 .name = "wavelan_cs",
4614 },
4615 .probe = wavelan_probe,
4616 .remove = wavelan_detach,
4617 .id_table = wavelan_ids,
4618 .suspend = wavelan_suspend,
4619 .resume = wavelan_resume,
4620};
4621
4622static int __init
4623init_wavelan_cs(void)
4624{
4625 return pcmcia_register_driver(&wavelan_driver);
4626}
4627
4628static void __exit
4629exit_wavelan_cs(void)
4630{
4631 pcmcia_unregister_driver(&wavelan_driver);
4632}
4633
4634module_init(init_wavelan_cs);
4635module_exit(exit_wavelan_cs);
4636