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
61
62
63
64
65
66
67
68
69
70
71
72#include <linux/module.h>
73#include <linux/kernel.h>
74#include <linux/init.h>
75#include <linux/slab.h>
76#include <linux/string.h>
77#include <linux/timer.h>
78#include <linux/interrupt.h>
79#include <linux/in.h>
80#include <linux/delay.h>
81#include <linux/netdevice.h>
82#include <linux/etherdevice.h>
83#include <linux/skbuff.h>
84#include <linux/if_arp.h>
85#include <linux/ioport.h>
86#include <linux/ethtool.h>
87
88#include <pcmcia/version.h>
89#include <pcmcia/cs_types.h>
90#include <pcmcia/cs.h>
91#include <pcmcia/cistpl.h>
92#include <pcmcia/cisreg.h>
93#include <pcmcia/ciscode.h>
94#include <pcmcia/ds.h>
95#include <pcmcia/mem_op.h>
96
97#include <asm/uaccess.h>
98#include <asm/io.h>
99#include <asm/system.h>
100#include <asm/bitops.h>
101
102
103
104
105
106MODULE_AUTHOR("David Hinds <dahinds@users.sourceforge.net>");
107MODULE_DESCRIPTION("3Com 3c574 series PCMCIA ethernet driver");
108MODULE_LICENSE("GPL");
109
110#define INT_MODULE_PARM(n, v) static int n = v; MODULE_PARM(n, "i")
111
112
113INT_MODULE_PARM(irq_mask, 0xdeb8);
114static int irq_list[4] = { -1 };
115MODULE_PARM(irq_list, "1-4i");
116
117
118INT_MODULE_PARM(max_interrupt_work, 32);
119
120
121INT_MODULE_PARM(full_duplex, 0);
122
123
124INT_MODULE_PARM(auto_polarity, 1);
125
126#ifdef PCMCIA_DEBUG
127INT_MODULE_PARM(pc_debug, PCMCIA_DEBUG);
128#define DEBUG(n, args...) if (pc_debug>(n)) printk(KERN_DEBUG args)
129static char *version =
130"3c574_cs.c 1.65ac1 2003/04/07 Donald Becker/David Hinds, becker@scyld.com.\n";
131#else
132#define DEBUG(n, args...)
133#endif
134
135
136
137
138#define TX_TIMEOUT ((800*HZ)/1000)
139
140
141
142
143
144#define EL3_DATA 0x00
145#define EL3_CMD 0x0e
146#define EL3_STATUS 0x0e
147
148#define EL3WINDOW(win_num) outw(SelectWindow + (win_num), ioaddr + EL3_CMD)
149
150
151
152enum el3_cmds {
153 TotalReset = 0<<11, SelectWindow = 1<<11, StartCoax = 2<<11,
154 RxDisable = 3<<11, RxEnable = 4<<11, RxReset = 5<<11, RxDiscard = 8<<11,
155 TxEnable = 9<<11, TxDisable = 10<<11, TxReset = 11<<11,
156 FakeIntr = 12<<11, AckIntr = 13<<11, SetIntrEnb = 14<<11,
157 SetStatusEnb = 15<<11, SetRxFilter = 16<<11, SetRxThreshold = 17<<11,
158 SetTxThreshold = 18<<11, SetTxStart = 19<<11, StatsEnable = 21<<11,
159 StatsDisable = 22<<11, StopCoax = 23<<11,
160};
161
162enum elxl_status {
163 IntLatch = 0x0001, AdapterFailure = 0x0002, TxComplete = 0x0004,
164 TxAvailable = 0x0008, RxComplete = 0x0010, RxEarly = 0x0020,
165 IntReq = 0x0040, StatsFull = 0x0080, CmdBusy = 0x1000 };
166
167
168enum RxFilter {
169 RxStation = 1, RxMulticast = 2, RxBroadcast = 4, RxProm = 8
170};
171
172enum Window0 {
173 Wn0EepromCmd = 10, Wn0EepromData = 12,
174 IntrStatus=0x0E,
175};
176
177enum Win0_EEPROM_cmds {
178 EEPROM_Read = 0x200, EEPROM_WRITE = 0x100, EEPROM_ERASE = 0x300,
179 EEPROM_EWENB = 0x30,
180 EEPROM_EWDIS = 0x00,
181};
182
183
184
185
186enum Window1 {
187 TX_FIFO = 0x10, RX_FIFO = 0x10, RxErrors = 0x14,
188 RxStatus = 0x18, Timer=0x1A, TxStatus = 0x1B,
189 TxFree = 0x0C,
190 RunnerRdCtrl = 0x16, RunnerWrCtrl = 0x1c,
191};
192
193enum Window3 {
194 Wn3_Config=0, Wn3_MAC_Ctrl=6, Wn3_Options=8,
195};
196union wn3_config {
197 int i;
198 struct w3_config_fields {
199 unsigned int ram_size:3, ram_width:1, ram_speed:2, rom_size:2;
200 int pad8:8;
201 unsigned int ram_split:2, pad18:2, xcvr:3, pad21:1, autoselect:1;
202 int pad24:7;
203 } u;
204};
205
206enum Window4 {
207 Wn4_FIFODiag = 4, Wn4_NetDiag = 6, Wn4_PhysicalMgmt=8, Wn4_Media = 10,
208};
209
210#define MEDIA_TP 0x00C0
211
212struct el3_private {
213 dev_link_t link;
214 dev_node_t node;
215 struct net_device_stats stats;
216 u16 advertising, partner;
217 unsigned char phys;
218 unsigned int autoselect:1, default_media:3;
219
220 struct timer_list media;
221 unsigned short media_status;
222 unsigned short fast_poll;
223 unsigned long last_irq;
224 spinlock_t window_lock;
225};
226
227
228
229
230static char mii_preamble_required = 0;
231
232
233
234static void tc574_config(dev_link_t *link);
235static void tc574_release(dev_link_t *link);
236static int tc574_event(event_t event, int priority,
237 event_callback_args_t *args);
238
239static void mdio_sync(ioaddr_t ioaddr, int bits);
240static int mdio_read(ioaddr_t ioaddr, int phy_id, int location);
241static void mdio_write(ioaddr_t ioaddr, int phy_id, int location, int value);
242static unsigned short read_eeprom(ioaddr_t ioaddr, int index);
243static void tc574_wait_for_completion(struct net_device *dev, int cmd);
244
245static void tc574_reset(struct net_device *dev);
246static void media_check(unsigned long arg);
247static int el3_open(struct net_device *dev);
248static int el3_start_xmit(struct sk_buff *skb, struct net_device *dev);
249static irqreturn_t el3_interrupt(int irq, void *dev_id, struct pt_regs *regs);
250static void update_stats(struct net_device *dev);
251static struct net_device_stats *el3_get_stats(struct net_device *dev);
252static int el3_rx(struct net_device *dev, int worklimit);
253static int el3_close(struct net_device *dev);
254static void el3_tx_timeout(struct net_device *dev);
255static int el3_ioctl(struct net_device *dev, struct ifreq *rq, int cmd);
256static struct ethtool_ops netdev_ethtool_ops;
257static void set_rx_mode(struct net_device *dev);
258
259static dev_info_t dev_info = "3c574_cs";
260
261static dev_link_t *tc574_attach(void);
262static void tc574_detach(dev_link_t *);
263
264static dev_link_t *dev_list;
265
266
267
268
269
270
271
272static dev_link_t *tc574_attach(void)
273{
274 struct el3_private *lp;
275 client_reg_t client_reg;
276 dev_link_t *link;
277 struct net_device *dev;
278 int i, ret;
279
280 DEBUG(0, "3c574_attach()\n");
281
282
283 dev = alloc_etherdev(sizeof(struct el3_private));
284 if (!dev)
285 return NULL;
286 lp = dev->priv;
287 link = &lp->link;
288 link->priv = dev;
289
290 spin_lock_init(&lp->window_lock);
291 link->io.NumPorts1 = 32;
292 link->io.Attributes1 = IO_DATA_PATH_WIDTH_16;
293 link->irq.Attributes = IRQ_TYPE_EXCLUSIVE | IRQ_HANDLE_PRESENT;
294 link->irq.IRQInfo1 = IRQ_INFO2_VALID|IRQ_LEVEL_ID;
295 if (irq_list[0] == -1)
296 link->irq.IRQInfo2 = irq_mask;
297 else
298 for (i = 0; i < 4; i++)
299 link->irq.IRQInfo2 |= 1 << irq_list[i];
300 link->irq.Handler = &el3_interrupt;
301 link->irq.Instance = dev;
302 link->conf.Attributes = CONF_ENABLE_IRQ;
303 link->conf.Vcc = 50;
304 link->conf.IntType = INT_MEMORY_AND_IO;
305 link->conf.ConfigIndex = 1;
306 link->conf.Present = PRESENT_OPTION;
307
308
309 dev->hard_start_xmit = &el3_start_xmit;
310 dev->get_stats = &el3_get_stats;
311 dev->do_ioctl = &el3_ioctl;
312 SET_ETHTOOL_OPS(dev, &netdev_ethtool_ops);
313 dev->set_multicast_list = &set_rx_mode;
314 dev->open = &el3_open;
315 dev->stop = &el3_close;
316#ifdef HAVE_TX_TIMEOUT
317 dev->tx_timeout = el3_tx_timeout;
318 dev->watchdog_timeo = TX_TIMEOUT;
319#endif
320
321
322 link->next = dev_list;
323 dev_list = link;
324 client_reg.dev_info = &dev_info;
325 client_reg.Attributes = INFO_IO_CLIENT | INFO_CARD_SHARE;
326 client_reg.EventMask =
327 CS_EVENT_CARD_INSERTION | CS_EVENT_CARD_REMOVAL |
328 CS_EVENT_RESET_PHYSICAL | CS_EVENT_CARD_RESET |
329 CS_EVENT_PM_SUSPEND | CS_EVENT_PM_RESUME;
330 client_reg.event_handler = &tc574_event;
331 client_reg.Version = 0x0210;
332 client_reg.event_callback_args.client_data = link;
333 ret = CardServices(RegisterClient, &link->handle, &client_reg);
334 if (ret != 0) {
335 cs_error(link->handle, RegisterClient, ret);
336 tc574_detach(link);
337 return NULL;
338 }
339
340 return link;
341}
342
343
344
345
346
347
348
349
350
351
352static void tc574_detach(dev_link_t *link)
353{
354 struct net_device *dev = link->priv;
355 dev_link_t **linkp;
356
357 DEBUG(0, "3c574_detach(0x%p)\n", link);
358
359
360 for (linkp = &dev_list; *linkp; linkp = &(*linkp)->next)
361 if (*linkp == link) break;
362 if (*linkp == NULL)
363 return;
364
365 if (link->state & DEV_CONFIG) {
366 tc574_release(link);
367 if (link->state & DEV_STALE_CONFIG)
368 return;
369 }
370
371 if (link->handle)
372 CardServices(DeregisterClient, link->handle);
373
374
375 *linkp = link->next;
376 if (link->dev) {
377 unregister_netdev(dev);
378 free_netdev(dev);
379 } else
380 kfree(dev);
381
382}
383
384
385
386
387
388
389
390#define CS_CHECK(fn, args...) \
391while ((last_ret=CardServices(last_fn=(fn), args))!=0) goto cs_failed
392
393static void tc574_config(dev_link_t *link)
394{
395 client_handle_t handle = link->handle;
396 struct net_device *dev = link->priv;
397 struct el3_private *lp = dev->priv;
398 tuple_t tuple;
399 cisparse_t parse;
400 unsigned short buf[32];
401 int last_fn, last_ret, i, j;
402 ioaddr_t ioaddr;
403 u16 *phys_addr;
404 char *cardname;
405
406 phys_addr = (u16 *)dev->dev_addr;
407
408 DEBUG(0, "3c574_config(0x%p)\n", link);
409
410 tuple.Attributes = 0;
411 tuple.DesiredTuple = CISTPL_CONFIG;
412 CS_CHECK(GetFirstTuple, handle, &tuple);
413 tuple.TupleData = (cisdata_t *)buf;
414 tuple.TupleDataMax = 64;
415 tuple.TupleOffset = 0;
416 CS_CHECK(GetTupleData, handle, &tuple);
417 CS_CHECK(ParseTuple, handle, &tuple, &parse);
418 link->conf.ConfigBase = parse.config.base;
419 link->conf.Present = parse.config.rmask[0];
420
421
422 link->state |= DEV_CONFIG;
423
424 link->io.IOAddrLines = 16;
425 for (i = j = 0; j < 0x400; j += 0x20) {
426 link->io.BasePort1 = j ^ 0x300;
427 i = CardServices(RequestIO, link->handle, &link->io);
428 if (i == CS_SUCCESS) break;
429 }
430 if (i != CS_SUCCESS) {
431 cs_error(link->handle, RequestIO, i);
432 goto failed;
433 }
434 CS_CHECK(RequestIRQ, link->handle, &link->irq);
435 CS_CHECK(RequestConfiguration, link->handle, &link->conf);
436
437 dev->irq = link->irq.AssignedIRQ;
438 dev->base_addr = link->io.BasePort1;
439
440 if (register_netdev(dev) != 0) {
441 printk(KERN_NOTICE "3c574_cs: register_netdev() failed\n");
442 goto failed;
443 }
444
445 ioaddr = dev->base_addr;
446 strcpy(lp->node.dev_name, dev->name);
447 link->dev = &lp->node;
448 link->state &= ~DEV_CONFIG_PENDING;
449
450
451
452
453 tuple.DesiredTuple = 0x88;
454 if (CardServices(GetFirstTuple, handle, &tuple) == CS_SUCCESS) {
455 CardServices(GetTupleData, handle, &tuple);
456 for (i = 0; i < 3; i++)
457 phys_addr[i] = htons(buf[i]);
458 } else {
459 EL3WINDOW(0);
460 for (i = 0; i < 3; i++)
461 phys_addr[i] = htons(read_eeprom(ioaddr, i + 10));
462 if (phys_addr[0] == 0x6060) {
463 printk(KERN_NOTICE "3c574_cs: IO port conflict at 0x%03lx"
464 "-0x%03lx\n", dev->base_addr, dev->base_addr+15);
465 goto failed;
466 }
467 }
468 tuple.DesiredTuple = CISTPL_VERS_1;
469 if (CardServices(GetFirstTuple, handle, &tuple) == CS_SUCCESS &&
470 CardServices(GetTupleData, handle, &tuple) == CS_SUCCESS &&
471 CardServices(ParseTuple, handle, &tuple, &parse) == CS_SUCCESS) {
472 cardname = parse.version_1.str + parse.version_1.ofs[1];
473 } else
474 cardname = "3Com 3c574";
475
476 printk(KERN_INFO "%s: %s at io %#3lx, irq %d, hw_addr ",
477 dev->name, cardname, dev->base_addr, dev->irq);
478
479 for (i = 0; i < 6; i++)
480 printk("%02X%s", dev->dev_addr[i], ((i<5) ? ":" : ".\n"));
481
482 {
483 u_char mcr, *ram_split[] = {"5:3", "3:1", "1:1", "3:5"};
484 union wn3_config config;
485 outw(2<<11, ioaddr + RunnerRdCtrl);
486 mcr = inb(ioaddr + 2);
487 outw(0<<11, ioaddr + RunnerRdCtrl);
488 printk(KERN_INFO " ASIC rev %d,", mcr>>3);
489 EL3WINDOW(3);
490 config.i = inl(ioaddr + Wn3_Config);
491 printk(" %dK FIFO split %s Rx:Tx, %sMII interface.\n",
492 8 << config.u.ram_size, ram_split[config.u.ram_split],
493 config.u.autoselect ? "autoselect " : "");
494 lp->default_media = config.u.xcvr;
495 lp->autoselect = config.u.autoselect;
496 }
497
498 init_timer(&lp->media);
499
500 {
501 int phy;
502
503
504 outw(0x8040, ioaddr + Wn3_Options);
505 mdelay(1);
506 outw(0xc040, ioaddr + Wn3_Options);
507 tc574_wait_for_completion(dev, TxReset);
508 tc574_wait_for_completion(dev, RxReset);
509 mdelay(1);
510 outw(0x8040, ioaddr + Wn3_Options);
511
512 EL3WINDOW(4);
513 for (phy = 1; phy <= 32; phy++) {
514 int mii_status;
515 mdio_sync(ioaddr, 32);
516 mii_status = mdio_read(ioaddr, phy & 0x1f, 1);
517 if (mii_status != 0xffff) {
518 lp->phys = phy & 0x1f;
519 DEBUG(0, " MII transceiver at index %d, status %x.\n",
520 phy, mii_status);
521 if ((mii_status & 0x0040) == 0)
522 mii_preamble_required = 1;
523 break;
524 }
525 }
526 if (phy > 32) {
527 printk(KERN_NOTICE " No MII transceivers found!\n");
528 goto failed;
529 }
530 i = mdio_read(ioaddr, lp->phys, 16) | 0x40;
531 mdio_write(ioaddr, lp->phys, 16, i);
532 lp->advertising = mdio_read(ioaddr, lp->phys, 4);
533 if (full_duplex) {
534
535 lp->advertising &= ~0x02a0;
536 mdio_write(ioaddr, lp->phys, 4, lp->advertising);
537 }
538 }
539
540 return;
541
542cs_failed:
543 cs_error(link->handle, last_fn, last_ret);
544failed:
545 tc574_release(link);
546 return;
547
548}
549
550
551
552
553
554
555
556static void tc574_release(dev_link_t *link)
557{
558 DEBUG(0, "3c574_release(0x%p)\n", link);
559
560 if (link->open) {
561 DEBUG(1, "3c574_cs: release postponed, '%s' still open\n",
562 link->dev->dev_name);
563 link->state |= DEV_STALE_CONFIG;
564 return;
565 }
566
567 CardServices(ReleaseConfiguration, link->handle);
568 CardServices(ReleaseIO, link->handle, &link->io);
569 CardServices(ReleaseIRQ, link->handle, &link->irq);
570
571 link->state &= ~DEV_CONFIG;
572
573 if (link->state & DEV_STALE_CONFIG)
574 tc574_detach(link);
575}
576
577
578
579
580
581
582
583
584static int tc574_event(event_t event, int priority,
585 event_callback_args_t *args)
586{
587 dev_link_t *link = args->client_data;
588 struct net_device *dev = link->priv;
589
590 DEBUG(1, "3c574_event(0x%06x)\n", event);
591
592 switch (event) {
593 case CS_EVENT_CARD_REMOVAL:
594 link->state &= ~DEV_PRESENT;
595 if (link->state & DEV_CONFIG) {
596 netif_device_detach(dev);
597 tc574_release(link);
598 }
599 break;
600 case CS_EVENT_CARD_INSERTION:
601 link->state |= DEV_PRESENT | DEV_CONFIG_PENDING;
602 tc574_config(link);
603 break;
604 case CS_EVENT_PM_SUSPEND:
605 link->state |= DEV_SUSPEND;
606
607 case CS_EVENT_RESET_PHYSICAL:
608 if (link->state & DEV_CONFIG) {
609 if (link->open)
610 netif_device_detach(dev);
611 CardServices(ReleaseConfiguration, link->handle);
612 }
613 break;
614 case CS_EVENT_PM_RESUME:
615 link->state &= ~DEV_SUSPEND;
616
617 case CS_EVENT_CARD_RESET:
618 if (link->state & DEV_CONFIG) {
619 CardServices(RequestConfiguration, link->handle, &link->conf);
620 if (link->open) {
621 tc574_reset(dev);
622 netif_device_attach(dev);
623 }
624 }
625 break;
626 }
627 return 0;
628}
629
630static void dump_status(struct net_device *dev)
631{
632 ioaddr_t ioaddr = dev->base_addr;
633 EL3WINDOW(1);
634 printk(KERN_INFO " irq status %04x, rx status %04x, tx status "
635 "%02x, tx free %04x\n", inw(ioaddr+EL3_STATUS),
636 inw(ioaddr+RxStatus), inb(ioaddr+TxStatus),
637 inw(ioaddr+TxFree));
638 EL3WINDOW(4);
639 printk(KERN_INFO " diagnostics: fifo %04x net %04x ethernet %04x"
640 " media %04x\n", inw(ioaddr+0x04), inw(ioaddr+0x06),
641 inw(ioaddr+0x08), inw(ioaddr+0x0a));
642 EL3WINDOW(1);
643}
644
645
646
647
648static void tc574_wait_for_completion(struct net_device *dev, int cmd)
649{
650 int i = 1500;
651 outw(cmd, dev->base_addr + EL3_CMD);
652 while (--i > 0)
653 if (!(inw(dev->base_addr + EL3_STATUS) & 0x1000)) break;
654 if (i == 0)
655 printk(KERN_NOTICE "%s: command 0x%04x did not complete!\n", dev->name, cmd);
656}
657
658
659
660
661static unsigned short read_eeprom(ioaddr_t ioaddr, int index)
662{
663 int timer;
664 outw(EEPROM_Read + index, ioaddr + Wn0EepromCmd);
665
666 for (timer = 1620; timer >= 0; timer--) {
667 if ((inw(ioaddr + Wn0EepromCmd) & 0x8000) == 0)
668 break;
669 }
670 return inw(ioaddr + Wn0EepromData);
671}
672
673
674
675
676
677
678
679
680#define MDIO_SHIFT_CLK 0x01
681#define MDIO_DIR_WRITE 0x04
682#define MDIO_DATA_WRITE0 (0x00 | MDIO_DIR_WRITE)
683#define MDIO_DATA_WRITE1 (0x02 | MDIO_DIR_WRITE)
684#define MDIO_DATA_READ 0x02
685#define MDIO_ENB_IN 0x00
686
687
688
689static void mdio_sync(ioaddr_t ioaddr, int bits)
690{
691 int mdio_addr = ioaddr + Wn4_PhysicalMgmt;
692
693
694 while (-- bits >= 0) {
695 outw(MDIO_DATA_WRITE1, mdio_addr);
696 outw(MDIO_DATA_WRITE1 | MDIO_SHIFT_CLK, mdio_addr);
697 }
698}
699
700static int mdio_read(ioaddr_t ioaddr, int phy_id, int location)
701{
702 int i;
703 int read_cmd = (0xf6 << 10) | (phy_id << 5) | location;
704 unsigned int retval = 0;
705 int mdio_addr = ioaddr + Wn4_PhysicalMgmt;
706
707 if (mii_preamble_required)
708 mdio_sync(ioaddr, 32);
709
710
711 for (i = 14; i >= 0; i--) {
712 int dataval = (read_cmd&(1<<i)) ? MDIO_DATA_WRITE1 : MDIO_DATA_WRITE0;
713 outw(dataval, mdio_addr);
714 outw(dataval | MDIO_SHIFT_CLK, mdio_addr);
715 }
716
717 for (i = 19; i > 0; i--) {
718 outw(MDIO_ENB_IN, mdio_addr);
719 retval = (retval << 1) | ((inw(mdio_addr) & MDIO_DATA_READ) ? 1 : 0);
720 outw(MDIO_ENB_IN | MDIO_SHIFT_CLK, mdio_addr);
721 }
722 return (retval>>1) & 0xffff;
723}
724
725static void mdio_write(ioaddr_t ioaddr, int phy_id, int location, int value)
726{
727 int write_cmd = 0x50020000 | (phy_id << 23) | (location << 18) | value;
728 int mdio_addr = ioaddr + Wn4_PhysicalMgmt;
729 int i;
730
731 if (mii_preamble_required)
732 mdio_sync(ioaddr, 32);
733
734
735 for (i = 31; i >= 0; i--) {
736 int dataval = (write_cmd&(1<<i)) ? MDIO_DATA_WRITE1 : MDIO_DATA_WRITE0;
737 outw(dataval, mdio_addr);
738 outw(dataval | MDIO_SHIFT_CLK, mdio_addr);
739 }
740
741 for (i = 1; i >= 0; i--) {
742 outw(MDIO_ENB_IN, mdio_addr);
743 outw(MDIO_ENB_IN | MDIO_SHIFT_CLK, mdio_addr);
744 }
745
746 return;
747}
748
749
750static void tc574_reset(struct net_device *dev)
751{
752 struct el3_private *lp = (struct el3_private *)dev->priv;
753 int i, ioaddr = dev->base_addr;
754 unsigned long flags;
755
756 tc574_wait_for_completion(dev, TotalReset|0x10);
757
758 spin_lock_irqsave(&lp->window_lock, flags);
759
760 outw(0, ioaddr + RunnerWrCtrl);
761 outw(0, ioaddr + RunnerRdCtrl);
762
763
764 EL3WINDOW(2);
765 for (i = 0; i < 6; i++)
766 outb(dev->dev_addr[i], ioaddr + i);
767 for (; i < 12; i+=2)
768 outw(0, ioaddr + i);
769
770
771 EL3WINDOW(3);
772 outb((dev->mtu > 1500 ? 0x40 : 0), ioaddr + Wn3_MAC_Ctrl);
773 outl((lp->autoselect ? 0x01000000 : 0) | 0x0062001b,
774 ioaddr + Wn3_Config);
775
776 outw(0x8040, ioaddr + Wn3_Options);
777 mdelay(1);
778 outw(0xc040, ioaddr + Wn3_Options);
779 EL3WINDOW(1);
780 spin_unlock_irqrestore(&lp->window_lock, flags);
781
782 tc574_wait_for_completion(dev, TxReset);
783 tc574_wait_for_completion(dev, RxReset);
784 mdelay(1);
785 spin_lock_irqsave(&lp->window_lock, flags);
786 EL3WINDOW(3);
787 outw(0x8040, ioaddr + Wn3_Options);
788
789
790 outw(StatsDisable, ioaddr + EL3_CMD);
791 EL3WINDOW(6);
792 for (i = 0; i < 10; i++)
793 inb(ioaddr + i);
794 inw(ioaddr + 10);
795 inw(ioaddr + 12);
796 EL3WINDOW(4);
797 inb(ioaddr + 12);
798 inb(ioaddr + 13);
799
800
801 outw(0x0040, ioaddr + Wn4_NetDiag);
802
803 EL3WINDOW(1);
804 spin_unlock_irqrestore(&lp->window_lock, flags);
805
806
807 mdio_sync(ioaddr, 32);
808 mdio_write(ioaddr, lp->phys, 4, lp->advertising);
809 if (!auto_polarity) {
810
811 int i = mdio_read(ioaddr, lp->phys, 16) | 0x20;
812 mdio_write(ioaddr, lp->phys, 16, i);
813 }
814
815 spin_lock_irqsave(&lp->window_lock, flags);
816
817 set_rx_mode(dev);
818 spin_unlock_irqrestore(&lp->window_lock, flags);
819 outw(StatsEnable, ioaddr + EL3_CMD);
820 outw(RxEnable, ioaddr + EL3_CMD);
821 outw(TxEnable, ioaddr + EL3_CMD);
822
823 outw(SetStatusEnb | 0xff, ioaddr + EL3_CMD);
824
825 outw(AckIntr | IntLatch | TxAvailable | RxEarly | IntReq,
826 ioaddr + EL3_CMD);
827 outw(SetIntrEnb | IntLatch | TxAvailable | RxComplete | StatsFull
828 | AdapterFailure | RxEarly, ioaddr + EL3_CMD);
829}
830
831static int el3_open(struct net_device *dev)
832{
833 struct el3_private *lp = (struct el3_private *)dev->priv;
834 dev_link_t *link = &lp->link;
835
836 if (!DEV_OK(link))
837 return -ENODEV;
838
839 link->open++;
840 netif_start_queue(dev);
841
842 tc574_reset(dev);
843 lp->media.function = &media_check;
844 lp->media.data = (unsigned long) dev;
845 lp->media.expires = jiffies + HZ;
846 add_timer(&lp->media);
847
848 DEBUG(2, "%s: opened, status %4.4x.\n",
849 dev->name, inw(dev->base_addr + EL3_STATUS));
850
851 return 0;
852}
853
854static void el3_tx_timeout(struct net_device *dev)
855{
856 struct el3_private *lp = (struct el3_private *)dev->priv;
857 ioaddr_t ioaddr = dev->base_addr;
858
859 printk(KERN_NOTICE "%s: Transmit timed out!\n", dev->name);
860 dump_status(dev);
861 lp->stats.tx_errors++;
862 dev->trans_start = jiffies;
863
864 tc574_wait_for_completion(dev, TxReset);
865 outw(TxEnable, ioaddr + EL3_CMD);
866 netif_wake_queue(dev);
867}
868
869static void pop_tx_status(struct net_device *dev)
870{
871 struct el3_private *lp = (struct el3_private *)dev->priv;
872 ioaddr_t ioaddr = dev->base_addr;
873 int i;
874
875
876 for (i = 32; i > 0; i--) {
877 u_char tx_status = inb(ioaddr + TxStatus);
878 if (!(tx_status & 0x84))
879 break;
880
881 if (tx_status & 0x30)
882 tc574_wait_for_completion(dev, TxReset);
883 if (tx_status & 0x38) {
884 DEBUG(1, "%s: transmit error: status 0x%02x\n",
885 dev->name, tx_status);
886 outw(TxEnable, ioaddr + EL3_CMD);
887 lp->stats.tx_aborted_errors++;
888 }
889 outb(0x00, ioaddr + TxStatus);
890 }
891}
892
893static int el3_start_xmit(struct sk_buff *skb, struct net_device *dev)
894{
895 ioaddr_t ioaddr = dev->base_addr;
896 struct el3_private *lp = (struct el3_private *)dev->priv;
897 unsigned long flags;
898
899 DEBUG(3, "%s: el3_start_xmit(length = %ld) called, "
900 "status %4.4x.\n", dev->name, (long)skb->len,
901 inw(ioaddr + EL3_STATUS));
902
903 spin_lock_irqsave(&lp->window_lock, flags);
904 outw(skb->len, ioaddr + TX_FIFO);
905 outw(0, ioaddr + TX_FIFO);
906 outsl(ioaddr + TX_FIFO, skb->data, (skb->len+3)>>2);
907
908 dev->trans_start = jiffies;
909
910
911 if (inw(ioaddr + TxFree) <= 1536) {
912 netif_stop_queue(dev);
913
914
915 outw(SetTxThreshold + (1536>>2), ioaddr + EL3_CMD);
916 }
917
918 pop_tx_status(dev);
919 spin_unlock_irqrestore(&lp->window_lock, flags);
920 dev_kfree_skb(skb);
921 return 0;
922}
923
924
925static irqreturn_t el3_interrupt(int irq, void *dev_id, struct pt_regs *regs)
926{
927 struct net_device *dev = (struct net_device *) dev_id;
928 struct el3_private *lp = dev->priv;
929 ioaddr_t ioaddr, status;
930 int work_budget = max_interrupt_work;
931 int handled = 0;
932
933 if (!netif_device_present(dev))
934 return IRQ_NONE;
935 ioaddr = dev->base_addr;
936
937 DEBUG(3, "%s: interrupt, status %4.4x.\n",
938 dev->name, inw(ioaddr + EL3_STATUS));
939
940 spin_lock(&lp->window_lock);
941
942 while ((status = inw(ioaddr + EL3_STATUS)) &
943 (IntLatch | RxComplete | RxEarly | StatsFull)) {
944 if (!netif_device_present(dev) ||
945 ((status & 0xe000) != 0x2000)) {
946 DEBUG(1, "%s: Interrupt from dead card\n", dev->name);
947 break;
948 }
949
950 handled = 1;
951
952 if (status & RxComplete)
953 work_budget = el3_rx(dev, work_budget);
954
955 if (status & TxAvailable) {
956 DEBUG(3, " TX room bit was handled.\n");
957
958 outw(AckIntr | TxAvailable, ioaddr + EL3_CMD);
959 netif_wake_queue(dev);
960 }
961
962 if (status & TxComplete)
963 pop_tx_status(dev);
964
965 if (status & (AdapterFailure | RxEarly | StatsFull)) {
966
967 if (status & StatsFull)
968 update_stats(dev);
969 if (status & RxEarly) {
970 work_budget = el3_rx(dev, work_budget);
971 outw(AckIntr | RxEarly, ioaddr + EL3_CMD);
972 }
973 if (status & AdapterFailure) {
974 u16 fifo_diag;
975 EL3WINDOW(4);
976 fifo_diag = inw(ioaddr + Wn4_FIFODiag);
977 EL3WINDOW(1);
978 printk(KERN_NOTICE "%s: adapter failure, FIFO diagnostic"
979 " register %04x.\n", dev->name, fifo_diag);
980 if (fifo_diag & 0x0400) {
981
982 tc574_wait_for_completion(dev, TxReset);
983 outw(TxEnable, ioaddr + EL3_CMD);
984 }
985 if (fifo_diag & 0x2000) {
986
987 tc574_wait_for_completion(dev, RxReset);
988 set_rx_mode(dev);
989 outw(RxEnable, ioaddr + EL3_CMD);
990 }
991 outw(AckIntr | AdapterFailure, ioaddr + EL3_CMD);
992 }
993 }
994
995 if (--work_budget < 0) {
996 DEBUG(0, "%s: Too much work in interrupt, "
997 "status %4.4x.\n", dev->name, status);
998
999 outw(AckIntr | 0xFF, ioaddr + EL3_CMD);
1000 break;
1001 }
1002
1003 outw(AckIntr | IntReq | IntLatch, ioaddr + EL3_CMD);
1004 }
1005
1006 DEBUG(3, "%s: exiting interrupt, status %4.4x.\n",
1007 dev->name, inw(ioaddr + EL3_STATUS));
1008
1009 spin_unlock(&lp->window_lock);
1010 return IRQ_RETVAL(handled);
1011}
1012
1013
1014
1015
1016
1017
1018static void media_check(unsigned long arg)
1019{
1020 struct net_device *dev = (struct net_device *) arg;
1021 struct el3_private *lp = dev->priv;
1022 ioaddr_t ioaddr = dev->base_addr;
1023 unsigned long flags;
1024 unsigned short media, partner;
1025
1026 if (!netif_device_present(dev))
1027 goto reschedule;
1028
1029
1030
1031 if ((inw(ioaddr + EL3_STATUS) & IntLatch) && (inb(ioaddr + Timer) == 0xff)) {
1032 if (!lp->fast_poll)
1033 printk(KERN_INFO "%s: interrupt(s) dropped!\n", dev->name);
1034 el3_interrupt(dev->irq, lp, NULL);
1035 lp->fast_poll = HZ;
1036 }
1037 if (lp->fast_poll) {
1038 lp->fast_poll--;
1039 lp->media.expires = jiffies + 2*HZ/100;
1040 add_timer(&lp->media);
1041 return;
1042 }
1043
1044 spin_lock_irqsave(&lp->window_lock, flags);
1045 EL3WINDOW(4);
1046 media = mdio_read(ioaddr, lp->phys, 1);
1047 partner = mdio_read(ioaddr, lp->phys, 5);
1048 EL3WINDOW(1);
1049
1050 if (media != lp->media_status) {
1051 if ((media ^ lp->media_status) & 0x0004)
1052 printk(KERN_INFO "%s: %s link beat\n", dev->name,
1053 (lp->media_status & 0x0004) ? "lost" : "found");
1054 if ((media ^ lp->media_status) & 0x0020) {
1055 lp->partner = 0;
1056 if (lp->media_status & 0x0020) {
1057 printk(KERN_INFO "%s: autonegotiation restarted\n",
1058 dev->name);
1059 } else if (partner) {
1060 partner &= lp->advertising;
1061 lp->partner = partner;
1062 printk(KERN_INFO "%s: autonegotiation complete: "
1063 "%sbaseT-%cD selected\n", dev->name,
1064 ((partner & 0x0180) ? "100" : "10"),
1065 ((partner & 0x0140) ? 'F' : 'H'));
1066 } else {
1067 printk(KERN_INFO "%s: link partner did not autonegotiate\n",
1068 dev->name);
1069 }
1070
1071 EL3WINDOW(3);
1072 outb((partner & 0x0140 ? 0x20 : 0) |
1073 (dev->mtu > 1500 ? 0x40 : 0), ioaddr + Wn3_MAC_Ctrl);
1074 EL3WINDOW(1);
1075
1076 }
1077 if (media & 0x0010)
1078 printk(KERN_INFO "%s: remote fault detected\n",
1079 dev->name);
1080 if (media & 0x0002)
1081 printk(KERN_INFO "%s: jabber detected\n", dev->name);
1082 lp->media_status = media;
1083 }
1084 spin_unlock_irqrestore(&lp->window_lock, flags);
1085
1086reschedule:
1087 lp->media.expires = jiffies + HZ;
1088 add_timer(&lp->media);
1089}
1090
1091static struct net_device_stats *el3_get_stats(struct net_device *dev)
1092{
1093 struct el3_private *lp = (struct el3_private *)dev->priv;
1094
1095 if (netif_device_present(dev))
1096 update_stats(dev);
1097 return &lp->stats;
1098}
1099
1100
1101
1102
1103
1104static void update_stats(struct net_device *dev)
1105{
1106 struct el3_private *lp = (struct el3_private *)dev->priv;
1107 ioaddr_t ioaddr = dev->base_addr;
1108 unsigned long flags;
1109 u8 rx, tx, up;
1110
1111 DEBUG(2, "%s: updating the statistics.\n", dev->name);
1112
1113 if (inw(ioaddr+EL3_STATUS) == 0xffff)
1114 return;
1115
1116 spin_lock_irqsave(&lp->window_lock, flags);
1117
1118
1119
1120 EL3WINDOW(6);
1121 lp->stats.tx_carrier_errors += inb(ioaddr + 0);
1122 lp->stats.tx_heartbeat_errors += inb(ioaddr + 1);
1123 inb(ioaddr + 2);
1124 lp->stats.collisions += inb(ioaddr + 3);
1125 lp->stats.tx_window_errors += inb(ioaddr + 4);
1126 lp->stats.rx_fifo_errors += inb(ioaddr + 5);
1127 lp->stats.tx_packets += inb(ioaddr + 6);
1128 up = inb(ioaddr + 9);
1129 lp->stats.tx_packets += (up&0x30) << 4;
1130 inb(ioaddr + 7);
1131 inb(ioaddr + 8);
1132 rx = inw(ioaddr + 10);
1133 tx = inw(ioaddr + 12);
1134
1135 EL3WINDOW(4);
1136 inb(ioaddr + 12);
1137 up = inb(ioaddr + 13);
1138
1139 lp->stats.tx_bytes += tx + ((up & 0xf0) << 12);
1140
1141 EL3WINDOW(1);
1142 spin_unlock_irqrestore(&lp->window_lock, flags);
1143}
1144
1145static int el3_rx(struct net_device *dev, int worklimit)
1146{
1147 struct el3_private *lp = (struct el3_private *)dev->priv;
1148 ioaddr_t ioaddr = dev->base_addr;
1149 short rx_status;
1150
1151 DEBUG(3, "%s: in rx_packet(), status %4.4x, rx_status %4.4x.\n",
1152 dev->name, inw(ioaddr+EL3_STATUS), inw(ioaddr+RxStatus));
1153 while (!((rx_status = inw(ioaddr + RxStatus)) & 0x8000) &&
1154 (--worklimit >= 0)) {
1155 if (rx_status & 0x4000) {
1156 short error = rx_status & 0x3800;
1157 lp->stats.rx_errors++;
1158 switch (error) {
1159 case 0x0000: lp->stats.rx_over_errors++; break;
1160 case 0x0800: lp->stats.rx_length_errors++; break;
1161 case 0x1000: lp->stats.rx_frame_errors++; break;
1162 case 0x1800: lp->stats.rx_length_errors++; break;
1163 case 0x2000: lp->stats.rx_frame_errors++; break;
1164 case 0x2800: lp->stats.rx_crc_errors++; break;
1165 }
1166 } else {
1167 short pkt_len = rx_status & 0x7ff;
1168 struct sk_buff *skb;
1169
1170 skb = dev_alloc_skb(pkt_len+5);
1171
1172 DEBUG(3, " Receiving packet size %d status %4.4x.\n",
1173 pkt_len, rx_status);
1174 if (skb != NULL) {
1175 skb->dev = dev;
1176 skb_reserve(skb, 2);
1177 insl(ioaddr+RX_FIFO, skb_put(skb, pkt_len),
1178 ((pkt_len+3)>>2));
1179 skb->protocol = eth_type_trans(skb, dev);
1180 netif_rx(skb);
1181 dev->last_rx = jiffies;
1182 lp->stats.rx_packets++;
1183 lp->stats.rx_bytes += pkt_len;
1184 } else {
1185 DEBUG(1, "%s: couldn't allocate a sk_buff of"
1186 " size %d.\n", dev->name, pkt_len);
1187 lp->stats.rx_dropped++;
1188 }
1189 }
1190 tc574_wait_for_completion(dev, RxDiscard);
1191 }
1192
1193 return worklimit;
1194}
1195
1196static void netdev_get_drvinfo(struct net_device *dev,
1197 struct ethtool_drvinfo *info)
1198{
1199 strcpy(info->driver, "3c574_cs");
1200}
1201
1202static struct ethtool_ops netdev_ethtool_ops = {
1203 .get_drvinfo = netdev_get_drvinfo,
1204};
1205
1206
1207static int el3_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
1208{
1209 struct el3_private *lp = (struct el3_private *)dev->priv;
1210 ioaddr_t ioaddr = dev->base_addr;
1211 u16 *data = (u16 *)&rq->ifr_data;
1212 int phy = lp->phys & 0x1f;
1213
1214 DEBUG(2, "%s: In ioct(%-.6s, %#4.4x) %4.4x %4.4x %4.4x %4.4x.\n",
1215 dev->name, rq->ifr_ifrn.ifrn_name, cmd,
1216 data[0], data[1], data[2], data[3]);
1217
1218 switch(cmd) {
1219 case SIOCGMIIPHY:
1220 data[0] = phy;
1221 case SIOCGMIIREG:
1222 {
1223 int saved_window;
1224 unsigned long flags;
1225
1226 spin_lock_irqsave(&lp->window_lock, flags);
1227 saved_window = inw(ioaddr + EL3_CMD) >> 13;
1228 EL3WINDOW(4);
1229 data[3] = mdio_read(ioaddr, data[0] & 0x1f, data[1] & 0x1f);
1230 EL3WINDOW(saved_window);
1231 spin_unlock_irqrestore(&lp->window_lock, flags);
1232 return 0;
1233 }
1234 case SIOCSMIIREG:
1235 {
1236 int saved_window;
1237 unsigned long flags;
1238
1239 if (!capable(CAP_NET_ADMIN))
1240 return -EPERM;
1241 spin_lock_irqsave(&lp->window_lock, flags);
1242 saved_window = inw(ioaddr + EL3_CMD) >> 13;
1243 EL3WINDOW(4);
1244 mdio_write(ioaddr, data[0] & 0x1f, data[1] & 0x1f, data[2]);
1245 EL3WINDOW(saved_window);
1246 spin_unlock_irqrestore(&lp->window_lock, flags);
1247 return 0;
1248 }
1249 default:
1250 return -EOPNOTSUPP;
1251 }
1252}
1253
1254
1255
1256
1257
1258
1259
1260
1261
1262static void set_rx_mode(struct net_device *dev)
1263{
1264 ioaddr_t ioaddr = dev->base_addr;
1265
1266 if (dev->flags & IFF_PROMISC)
1267 outw(SetRxFilter | RxStation | RxMulticast | RxBroadcast | RxProm,
1268 ioaddr + EL3_CMD);
1269 else if (dev->mc_count || (dev->flags & IFF_ALLMULTI))
1270 outw(SetRxFilter|RxStation|RxMulticast|RxBroadcast, ioaddr + EL3_CMD);
1271 else
1272 outw(SetRxFilter | RxStation | RxBroadcast, ioaddr + EL3_CMD);
1273}
1274
1275static int el3_close(struct net_device *dev)
1276{
1277 ioaddr_t ioaddr = dev->base_addr;
1278 struct el3_private *lp = dev->priv;
1279 dev_link_t *link = &lp->link;
1280
1281 DEBUG(2, "%s: shutting down ethercard.\n", dev->name);
1282
1283 if (DEV_OK(link)) {
1284
1285 outw(StatsDisable, ioaddr + EL3_CMD);
1286
1287
1288 outw(RxDisable, ioaddr + EL3_CMD);
1289 outw(TxDisable, ioaddr + EL3_CMD);
1290
1291
1292 EL3WINDOW(0);
1293
1294 update_stats(dev);
1295 }
1296
1297 link->open--;
1298 netif_stop_queue(dev);
1299 del_timer_sync(&lp->media);
1300 if (link->state & DEV_STALE_CONFIG)
1301 tc574_release(link);
1302 return 0;
1303}
1304
1305static struct pcmcia_driver tc574_driver = {
1306 .owner = THIS_MODULE,
1307 .drv = {
1308 .name = "3c574_cs",
1309 },
1310 .attach = tc574_attach,
1311 .detach = tc574_detach,
1312};
1313
1314static int __init init_tc574(void)
1315{
1316 return pcmcia_register_driver(&tc574_driver);
1317}
1318
1319static void __exit exit_tc574(void)
1320{
1321 pcmcia_unregister_driver(&tc574_driver);
1322 while (dev_list != NULL)
1323 tc574_detach(dev_list);
1324}
1325
1326module_init(init_tc574);
1327module_exit(exit_tc574);
1328