diff options
Diffstat (limited to 'drivers/net/pcmcia/3c574_cs.c')
-rw-r--r-- | drivers/net/pcmcia/3c574_cs.c | 90 |
1 files changed, 39 insertions, 51 deletions
diff --git a/drivers/net/pcmcia/3c574_cs.c b/drivers/net/pcmcia/3c574_cs.c index b58965a2b3ae..17a27225cc98 100644 --- a/drivers/net/pcmcia/3c574_cs.c +++ b/drivers/net/pcmcia/3c574_cs.c | |||
@@ -118,14 +118,6 @@ INT_MODULE_PARM(full_duplex, 0); | |||
118 | /* Autodetect link polarity reversal? */ | 118 | /* Autodetect link polarity reversal? */ |
119 | INT_MODULE_PARM(auto_polarity, 1); | 119 | INT_MODULE_PARM(auto_polarity, 1); |
120 | 120 | ||
121 | #ifdef PCMCIA_DEBUG | ||
122 | INT_MODULE_PARM(pc_debug, PCMCIA_DEBUG); | ||
123 | #define DEBUG(n, args...) if (pc_debug>(n)) printk(KERN_DEBUG args) | ||
124 | static char *version = | ||
125 | "3c574_cs.c 1.65ac1 2003/04/07 Donald Becker/David Hinds, becker@scyld.com.\n"; | ||
126 | #else | ||
127 | #define DEBUG(n, args...) | ||
128 | #endif | ||
129 | 121 | ||
130 | /*====================================================================*/ | 122 | /*====================================================================*/ |
131 | 123 | ||
@@ -278,7 +270,7 @@ static int tc574_probe(struct pcmcia_device *link) | |||
278 | struct el3_private *lp; | 270 | struct el3_private *lp; |
279 | struct net_device *dev; | 271 | struct net_device *dev; |
280 | 272 | ||
281 | DEBUG(0, "3c574_attach()\n"); | 273 | dev_dbg(&link->dev, "3c574_attach()\n"); |
282 | 274 | ||
283 | /* Create the PC card device object. */ | 275 | /* Create the PC card device object. */ |
284 | dev = alloc_etherdev(sizeof(struct el3_private)); | 276 | dev = alloc_etherdev(sizeof(struct el3_private)); |
@@ -291,10 +283,8 @@ static int tc574_probe(struct pcmcia_device *link) | |||
291 | spin_lock_init(&lp->window_lock); | 283 | spin_lock_init(&lp->window_lock); |
292 | link->io.NumPorts1 = 32; | 284 | link->io.NumPorts1 = 32; |
293 | link->io.Attributes1 = IO_DATA_PATH_WIDTH_16; | 285 | link->io.Attributes1 = IO_DATA_PATH_WIDTH_16; |
294 | link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING|IRQ_HANDLE_PRESENT; | 286 | link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING; |
295 | link->irq.IRQInfo1 = IRQ_LEVEL_ID; | ||
296 | link->irq.Handler = &el3_interrupt; | 287 | link->irq.Handler = &el3_interrupt; |
297 | link->irq.Instance = dev; | ||
298 | link->conf.Attributes = CONF_ENABLE_IRQ; | 288 | link->conf.Attributes = CONF_ENABLE_IRQ; |
299 | link->conf.IntType = INT_MEMORY_AND_IO; | 289 | link->conf.IntType = INT_MEMORY_AND_IO; |
300 | link->conf.ConfigIndex = 1; | 290 | link->conf.ConfigIndex = 1; |
@@ -319,7 +309,7 @@ static void tc574_detach(struct pcmcia_device *link) | |||
319 | { | 309 | { |
320 | struct net_device *dev = link->priv; | 310 | struct net_device *dev = link->priv; |
321 | 311 | ||
322 | DEBUG(0, "3c574_detach(0x%p)\n", link); | 312 | dev_dbg(&link->dev, "3c574_detach()\n"); |
323 | 313 | ||
324 | if (link->dev_node) | 314 | if (link->dev_node) |
325 | unregister_netdev(dev); | 315 | unregister_netdev(dev); |
@@ -335,26 +325,23 @@ static void tc574_detach(struct pcmcia_device *link) | |||
335 | ethernet device available to the system. | 325 | ethernet device available to the system. |
336 | */ | 326 | */ |
337 | 327 | ||
338 | #define CS_CHECK(fn, ret) \ | ||
339 | do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0) | ||
340 | |||
341 | static const char *ram_split[] = {"5:3", "3:1", "1:1", "3:5"}; | 328 | static const char *ram_split[] = {"5:3", "3:1", "1:1", "3:5"}; |
342 | 329 | ||
343 | static int tc574_config(struct pcmcia_device *link) | 330 | static int tc574_config(struct pcmcia_device *link) |
344 | { | 331 | { |
345 | struct net_device *dev = link->priv; | 332 | struct net_device *dev = link->priv; |
346 | struct el3_private *lp = netdev_priv(dev); | 333 | struct el3_private *lp = netdev_priv(dev); |
347 | tuple_t tuple; | 334 | int ret, i, j; |
348 | __le16 buf[32]; | ||
349 | int last_fn, last_ret, i, j; | ||
350 | unsigned int ioaddr; | 335 | unsigned int ioaddr; |
351 | __be16 *phys_addr; | 336 | __be16 *phys_addr; |
352 | char *cardname; | 337 | char *cardname; |
353 | __u32 config; | 338 | __u32 config; |
339 | u8 *buf; | ||
340 | size_t len; | ||
354 | 341 | ||
355 | phys_addr = (__be16 *)dev->dev_addr; | 342 | phys_addr = (__be16 *)dev->dev_addr; |
356 | 343 | ||
357 | DEBUG(0, "3c574_config(0x%p)\n", link); | 344 | dev_dbg(&link->dev, "3c574_config()\n"); |
358 | 345 | ||
359 | link->io.IOAddrLines = 16; | 346 | link->io.IOAddrLines = 16; |
360 | for (i = j = 0; j < 0x400; j += 0x20) { | 347 | for (i = j = 0; j < 0x400; j += 0x20) { |
@@ -363,12 +350,16 @@ static int tc574_config(struct pcmcia_device *link) | |||
363 | if (i == 0) | 350 | if (i == 0) |
364 | break; | 351 | break; |
365 | } | 352 | } |
366 | if (i != 0) { | 353 | if (i != 0) |
367 | cs_error(link, RequestIO, i); | 354 | goto failed; |
355 | |||
356 | ret = pcmcia_request_irq(link, &link->irq); | ||
357 | if (ret) | ||
358 | goto failed; | ||
359 | |||
360 | ret = pcmcia_request_configuration(link, &link->conf); | ||
361 | if (ret) | ||
368 | goto failed; | 362 | goto failed; |
369 | } | ||
370 | CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq)); | ||
371 | CS_CHECK(RequestConfiguration, pcmcia_request_configuration(link, &link->conf)); | ||
372 | 363 | ||
373 | dev->irq = link->irq.AssignedIRQ; | 364 | dev->irq = link->irq.AssignedIRQ; |
374 | dev->base_addr = link->io.BasePort1; | 365 | dev->base_addr = link->io.BasePort1; |
@@ -378,16 +369,14 @@ static int tc574_config(struct pcmcia_device *link) | |||
378 | /* The 3c574 normally uses an EEPROM for configuration info, including | 369 | /* The 3c574 normally uses an EEPROM for configuration info, including |
379 | the hardware address. The future products may include a modem chip | 370 | the hardware address. The future products may include a modem chip |
380 | and put the address in the CIS. */ | 371 | and put the address in the CIS. */ |
381 | tuple.Attributes = 0; | 372 | |
382 | tuple.TupleData = (cisdata_t *)buf; | 373 | len = pcmcia_get_tuple(link, 0x88, &buf); |
383 | tuple.TupleDataMax = 64; | 374 | if (buf && len >= 6) { |
384 | tuple.TupleOffset = 0; | ||
385 | tuple.DesiredTuple = 0x88; | ||
386 | if (pcmcia_get_first_tuple(link, &tuple) == 0) { | ||
387 | pcmcia_get_tuple_data(link, &tuple); | ||
388 | for (i = 0; i < 3; i++) | 375 | for (i = 0; i < 3; i++) |
389 | phys_addr[i] = htons(le16_to_cpu(buf[i])); | 376 | phys_addr[i] = htons(le16_to_cpu(buf[i * 2])); |
377 | kfree(buf); | ||
390 | } else { | 378 | } else { |
379 | kfree(buf); /* 0 < len < 6 */ | ||
391 | EL3WINDOW(0); | 380 | EL3WINDOW(0); |
392 | for (i = 0; i < 3; i++) | 381 | for (i = 0; i < 3; i++) |
393 | phys_addr[i] = htons(read_eeprom(ioaddr, i + 10)); | 382 | phys_addr[i] = htons(read_eeprom(ioaddr, i + 10)); |
@@ -435,7 +424,8 @@ static int tc574_config(struct pcmcia_device *link) | |||
435 | mii_status = mdio_read(ioaddr, phy & 0x1f, 1); | 424 | mii_status = mdio_read(ioaddr, phy & 0x1f, 1); |
436 | if (mii_status != 0xffff) { | 425 | if (mii_status != 0xffff) { |
437 | lp->phys = phy & 0x1f; | 426 | lp->phys = phy & 0x1f; |
438 | DEBUG(0, " MII transceiver at index %d, status %x.\n", | 427 | dev_dbg(&link->dev, " MII transceiver at " |
428 | "index %d, status %x.\n", | ||
439 | phy, mii_status); | 429 | phy, mii_status); |
440 | if ((mii_status & 0x0040) == 0) | 430 | if ((mii_status & 0x0040) == 0) |
441 | mii_preamble_required = 1; | 431 | mii_preamble_required = 1; |
@@ -457,7 +447,7 @@ static int tc574_config(struct pcmcia_device *link) | |||
457 | } | 447 | } |
458 | 448 | ||
459 | link->dev_node = &lp->node; | 449 | link->dev_node = &lp->node; |
460 | SET_NETDEV_DEV(dev, &handle_to_dev(link)); | 450 | SET_NETDEV_DEV(dev, &link->dev); |
461 | 451 | ||
462 | if (register_netdev(dev) != 0) { | 452 | if (register_netdev(dev) != 0) { |
463 | printk(KERN_NOTICE "3c574_cs: register_netdev() failed\n"); | 453 | printk(KERN_NOTICE "3c574_cs: register_netdev() failed\n"); |
@@ -478,8 +468,6 @@ static int tc574_config(struct pcmcia_device *link) | |||
478 | 468 | ||
479 | return 0; | 469 | return 0; |
480 | 470 | ||
481 | cs_failed: | ||
482 | cs_error(link, last_fn, last_ret); | ||
483 | failed: | 471 | failed: |
484 | tc574_release(link); | 472 | tc574_release(link); |
485 | return -ENODEV; | 473 | return -ENODEV; |
@@ -738,7 +726,7 @@ static int el3_open(struct net_device *dev) | |||
738 | lp->media.expires = jiffies + HZ; | 726 | lp->media.expires = jiffies + HZ; |
739 | add_timer(&lp->media); | 727 | add_timer(&lp->media); |
740 | 728 | ||
741 | DEBUG(2, "%s: opened, status %4.4x.\n", | 729 | dev_dbg(&link->dev, "%s: opened, status %4.4x.\n", |
742 | dev->name, inw(dev->base_addr + EL3_STATUS)); | 730 | dev->name, inw(dev->base_addr + EL3_STATUS)); |
743 | 731 | ||
744 | return 0; | 732 | return 0; |
@@ -772,7 +760,7 @@ static void pop_tx_status(struct net_device *dev) | |||
772 | if (tx_status & 0x30) | 760 | if (tx_status & 0x30) |
773 | tc574_wait_for_completion(dev, TxReset); | 761 | tc574_wait_for_completion(dev, TxReset); |
774 | if (tx_status & 0x38) { | 762 | if (tx_status & 0x38) { |
775 | DEBUG(1, "%s: transmit error: status 0x%02x\n", | 763 | pr_debug("%s: transmit error: status 0x%02x\n", |
776 | dev->name, tx_status); | 764 | dev->name, tx_status); |
777 | outw(TxEnable, ioaddr + EL3_CMD); | 765 | outw(TxEnable, ioaddr + EL3_CMD); |
778 | dev->stats.tx_aborted_errors++; | 766 | dev->stats.tx_aborted_errors++; |
@@ -788,7 +776,7 @@ static netdev_tx_t el3_start_xmit(struct sk_buff *skb, | |||
788 | struct el3_private *lp = netdev_priv(dev); | 776 | struct el3_private *lp = netdev_priv(dev); |
789 | unsigned long flags; | 777 | unsigned long flags; |
790 | 778 | ||
791 | DEBUG(3, "%s: el3_start_xmit(length = %ld) called, " | 779 | pr_debug("%s: el3_start_xmit(length = %ld) called, " |
792 | "status %4.4x.\n", dev->name, (long)skb->len, | 780 | "status %4.4x.\n", dev->name, (long)skb->len, |
793 | inw(ioaddr + EL3_STATUS)); | 781 | inw(ioaddr + EL3_STATUS)); |
794 | 782 | ||
@@ -827,7 +815,7 @@ static irqreturn_t el3_interrupt(int irq, void *dev_id) | |||
827 | return IRQ_NONE; | 815 | return IRQ_NONE; |
828 | ioaddr = dev->base_addr; | 816 | ioaddr = dev->base_addr; |
829 | 817 | ||
830 | DEBUG(3, "%s: interrupt, status %4.4x.\n", | 818 | pr_debug("%s: interrupt, status %4.4x.\n", |
831 | dev->name, inw(ioaddr + EL3_STATUS)); | 819 | dev->name, inw(ioaddr + EL3_STATUS)); |
832 | 820 | ||
833 | spin_lock(&lp->window_lock); | 821 | spin_lock(&lp->window_lock); |
@@ -836,7 +824,7 @@ static irqreturn_t el3_interrupt(int irq, void *dev_id) | |||
836 | (IntLatch | RxComplete | RxEarly | StatsFull)) { | 824 | (IntLatch | RxComplete | RxEarly | StatsFull)) { |
837 | if (!netif_device_present(dev) || | 825 | if (!netif_device_present(dev) || |
838 | ((status & 0xe000) != 0x2000)) { | 826 | ((status & 0xe000) != 0x2000)) { |
839 | DEBUG(1, "%s: Interrupt from dead card\n", dev->name); | 827 | pr_debug("%s: Interrupt from dead card\n", dev->name); |
840 | break; | 828 | break; |
841 | } | 829 | } |
842 | 830 | ||
@@ -846,7 +834,7 @@ static irqreturn_t el3_interrupt(int irq, void *dev_id) | |||
846 | work_budget = el3_rx(dev, work_budget); | 834 | work_budget = el3_rx(dev, work_budget); |
847 | 835 | ||
848 | if (status & TxAvailable) { | 836 | if (status & TxAvailable) { |
849 | DEBUG(3, " TX room bit was handled.\n"); | 837 | pr_debug(" TX room bit was handled.\n"); |
850 | /* There's room in the FIFO for a full-sized packet. */ | 838 | /* There's room in the FIFO for a full-sized packet. */ |
851 | outw(AckIntr | TxAvailable, ioaddr + EL3_CMD); | 839 | outw(AckIntr | TxAvailable, ioaddr + EL3_CMD); |
852 | netif_wake_queue(dev); | 840 | netif_wake_queue(dev); |
@@ -886,7 +874,7 @@ static irqreturn_t el3_interrupt(int irq, void *dev_id) | |||
886 | } | 874 | } |
887 | 875 | ||
888 | if (--work_budget < 0) { | 876 | if (--work_budget < 0) { |
889 | DEBUG(0, "%s: Too much work in interrupt, " | 877 | pr_debug("%s: Too much work in interrupt, " |
890 | "status %4.4x.\n", dev->name, status); | 878 | "status %4.4x.\n", dev->name, status); |
891 | /* Clear all interrupts */ | 879 | /* Clear all interrupts */ |
892 | outw(AckIntr | 0xFF, ioaddr + EL3_CMD); | 880 | outw(AckIntr | 0xFF, ioaddr + EL3_CMD); |
@@ -896,7 +884,7 @@ static irqreturn_t el3_interrupt(int irq, void *dev_id) | |||
896 | outw(AckIntr | IntReq | IntLatch, ioaddr + EL3_CMD); | 884 | outw(AckIntr | IntReq | IntLatch, ioaddr + EL3_CMD); |
897 | } | 885 | } |
898 | 886 | ||
899 | DEBUG(3, "%s: exiting interrupt, status %4.4x.\n", | 887 | pr_debug("%s: exiting interrupt, status %4.4x.\n", |
900 | dev->name, inw(ioaddr + EL3_STATUS)); | 888 | dev->name, inw(ioaddr + EL3_STATUS)); |
901 | 889 | ||
902 | spin_unlock(&lp->window_lock); | 890 | spin_unlock(&lp->window_lock); |
@@ -1003,7 +991,7 @@ static void update_stats(struct net_device *dev) | |||
1003 | unsigned int ioaddr = dev->base_addr; | 991 | unsigned int ioaddr = dev->base_addr; |
1004 | u8 rx, tx, up; | 992 | u8 rx, tx, up; |
1005 | 993 | ||
1006 | DEBUG(2, "%s: updating the statistics.\n", dev->name); | 994 | pr_debug("%s: updating the statistics.\n", dev->name); |
1007 | 995 | ||
1008 | if (inw(ioaddr+EL3_STATUS) == 0xffff) /* No card. */ | 996 | if (inw(ioaddr+EL3_STATUS) == 0xffff) /* No card. */ |
1009 | return; | 997 | return; |
@@ -1039,7 +1027,7 @@ static int el3_rx(struct net_device *dev, int worklimit) | |||
1039 | unsigned int ioaddr = dev->base_addr; | 1027 | unsigned int ioaddr = dev->base_addr; |
1040 | short rx_status; | 1028 | short rx_status; |
1041 | 1029 | ||
1042 | DEBUG(3, "%s: in rx_packet(), status %4.4x, rx_status %4.4x.\n", | 1030 | pr_debug("%s: in rx_packet(), status %4.4x, rx_status %4.4x.\n", |
1043 | dev->name, inw(ioaddr+EL3_STATUS), inw(ioaddr+RxStatus)); | 1031 | dev->name, inw(ioaddr+EL3_STATUS), inw(ioaddr+RxStatus)); |
1044 | while (!((rx_status = inw(ioaddr + RxStatus)) & 0x8000) && | 1032 | while (!((rx_status = inw(ioaddr + RxStatus)) & 0x8000) && |
1045 | worklimit > 0) { | 1033 | worklimit > 0) { |
@@ -1061,7 +1049,7 @@ static int el3_rx(struct net_device *dev, int worklimit) | |||
1061 | 1049 | ||
1062 | skb = dev_alloc_skb(pkt_len+5); | 1050 | skb = dev_alloc_skb(pkt_len+5); |
1063 | 1051 | ||
1064 | DEBUG(3, " Receiving packet size %d status %4.4x.\n", | 1052 | pr_debug(" Receiving packet size %d status %4.4x.\n", |
1065 | pkt_len, rx_status); | 1053 | pkt_len, rx_status); |
1066 | if (skb != NULL) { | 1054 | if (skb != NULL) { |
1067 | skb_reserve(skb, 2); | 1055 | skb_reserve(skb, 2); |
@@ -1072,7 +1060,7 @@ static int el3_rx(struct net_device *dev, int worklimit) | |||
1072 | dev->stats.rx_packets++; | 1060 | dev->stats.rx_packets++; |
1073 | dev->stats.rx_bytes += pkt_len; | 1061 | dev->stats.rx_bytes += pkt_len; |
1074 | } else { | 1062 | } else { |
1075 | DEBUG(1, "%s: couldn't allocate a sk_buff of" | 1063 | pr_debug("%s: couldn't allocate a sk_buff of" |
1076 | " size %d.\n", dev->name, pkt_len); | 1064 | " size %d.\n", dev->name, pkt_len); |
1077 | dev->stats.rx_dropped++; | 1065 | dev->stats.rx_dropped++; |
1078 | } | 1066 | } |
@@ -1101,7 +1089,7 @@ static int el3_ioctl(struct net_device *dev, struct ifreq *rq, int cmd) | |||
1101 | struct mii_ioctl_data *data = if_mii(rq); | 1089 | struct mii_ioctl_data *data = if_mii(rq); |
1102 | int phy = lp->phys & 0x1f; | 1090 | int phy = lp->phys & 0x1f; |
1103 | 1091 | ||
1104 | DEBUG(2, "%s: In ioct(%-.6s, %#4.4x) %4.4x %4.4x %4.4x %4.4x.\n", | 1092 | pr_debug("%s: In ioct(%-.6s, %#4.4x) %4.4x %4.4x %4.4x %4.4x.\n", |
1105 | dev->name, rq->ifr_ifrn.ifrn_name, cmd, | 1093 | dev->name, rq->ifr_ifrn.ifrn_name, cmd, |
1106 | data->phy_id, data->reg_num, data->val_in, data->val_out); | 1094 | data->phy_id, data->reg_num, data->val_in, data->val_out); |
1107 | 1095 | ||
@@ -1178,7 +1166,7 @@ static int el3_close(struct net_device *dev) | |||
1178 | struct el3_private *lp = netdev_priv(dev); | 1166 | struct el3_private *lp = netdev_priv(dev); |
1179 | struct pcmcia_device *link = lp->p_dev; | 1167 | struct pcmcia_device *link = lp->p_dev; |
1180 | 1168 | ||
1181 | DEBUG(2, "%s: shutting down ethercard.\n", dev->name); | 1169 | dev_dbg(&link->dev, "%s: shutting down ethercard.\n", dev->name); |
1182 | 1170 | ||
1183 | if (pcmcia_dev_present(link)) { | 1171 | if (pcmcia_dev_present(link)) { |
1184 | unsigned long flags; | 1172 | unsigned long flags; |