Messages in this thread Patch in this message | ![/](/images/icornerl.gif) | | Date | Tue, 8 Apr 2003 01:25:09 +0100 | From | Alan Cox <> | Subject | PATCH: Update lp486e for 2.5 |
| |
diff -u --new-file --recursive --exclude-from /usr/src/exclude linux-2.5.67/drivers/net/lp486e.c linux-2.5.67-ac1/drivers/net/lp486e.c --- linux-2.5.67/drivers/net/lp486e.c 2003-02-10 18:38:11.000000000 +0000 +++ linux-2.5.67-ac1/drivers/net/lp486e.c 2003-04-07 19:14:53.000000000 +0100 @@ -56,7 +56,7 @@ All other communication is through memory! */ -#define SLOW_DOWN_IO udelay(5); +#define SLOW_DOWN_IO udelay(5) #include <linux/module.h> #include <linux/init.h> @@ -195,7 +195,7 @@ typedef u32 phys_addr; static inline phys_addr -va_to_pa(volatile void *x) { +va_to_pa(void *x) { return x ? virt_to_bus(x) : I596_NULL; } @@ -341,14 +341,15 @@ unsigned long tdr_stat; /* directly follows tdr */ int last_restart; - volatile struct i596_rbd *rbd_list; - volatile struct i596_rbd *rbd_tail; - volatile struct i596_rfd *rx_tail; - volatile struct i596_cmd *cmd_tail; - volatile struct i596_cmd *cmd_head; + struct i596_rbd *rbd_list; + struct i596_rbd *rbd_tail; + struct i596_rfd *rx_tail; + struct i596_cmd *cmd_tail; + struct i596_cmd *cmd_head; int cmd_backlog; unsigned long last_cmd; struct net_device_stats stats; + spinlock_t cmd_lock; }; static char init_setup[14] = { @@ -386,7 +387,7 @@ static int i596_timeout(struct net_device *dev, char *msg, int ct) { - volatile struct i596_private *lp; + struct i596_private *lp; int boguscnt = ct; lp = (struct i596_private *) dev->priv; @@ -398,13 +399,14 @@ return 1; } udelay(5); + barrier(); } return 0; } static inline int init_rx_bufs(struct net_device *dev, int num) { - volatile struct i596_private *lp; + struct i596_private *lp; struct i596_rfd *rfd; int i; // struct i596_rbd *rbd; @@ -517,8 +519,8 @@ /* selftest or dump */ static void i596_port_do(struct net_device *dev, int portcmd, char *cmdname) { - volatile struct i596_private *lp = dev->priv; - volatile u16 *outp; + struct i596_private *lp = dev->priv; + u16 *outp; int i, m; memset((void *)&(lp->dump), 0, sizeof(struct i596_dump)); @@ -541,7 +543,7 @@ static int i596_scp_setup(struct net_device *dev) { - volatile struct i596_private *lp = dev->priv; + struct i596_private *lp = dev->priv; int boguscnt; /* Setup SCP, ISCP, SCB */ @@ -608,6 +610,7 @@ return 1; } udelay(5); + barrier(); } /* I find here boguscnt==100, so no delay was required. */ @@ -616,7 +619,7 @@ static int init_i596(struct net_device *dev) { - volatile struct i596_private *lp; + struct i596_private *lp; if (i596_scp_setup(dev)) return 1; @@ -641,6 +644,8 @@ lp->scb.command = RX_START; CA(); + barrier(); + if (lp->scb.command && i596_timeout(dev, "Receive Unit start", 100)) return 1; @@ -649,7 +654,7 @@ /* Receive a single frame */ static inline int -i596_rx_one(struct net_device *dev, volatile struct i596_private *lp, +i596_rx_one(struct net_device *dev, struct i596_private *lp, struct i596_rfd *rfd, int *frames) { if (rfd->stat & RFD_STAT_OK) { @@ -703,14 +708,14 @@ static int i596_rx(struct net_device *dev) { - volatile struct i596_private *lp = (struct i596_private *) dev->priv; + struct i596_private *lp = (struct i596_private *) dev->priv; struct i596_rfd *rfd; int frames = 0; while (1) { rfd = pa_to_va(lp->scb.pa_rfd); if (!rfd) { - printk("i596_rx: NULL rfd?\n"); + printk(KERN_ERR "i596_rx: NULL rfd?\n"); return 0; } #if 1 @@ -725,6 +730,7 @@ lp->rx_tail->cmd = 0; lp->rx_tail = rfd; lp->scb.pa_rfd = rfd->pa_next; + barrier(); } return frames; @@ -732,7 +738,7 @@ static void i596_cleanup_cmd(struct net_device *dev) { - volatile struct i596_private *lp; + struct i596_private *lp; struct i596_cmd *cmd; lp = (struct i596_private *) dev->priv; @@ -770,6 +776,7 @@ break; } } + barrier(); } if (lp->scb.command && i596_timeout(dev, "i596_cleanup_cmd", 100)) @@ -778,9 +785,7 @@ lp->scb.pa_cmd = va_to_pa(lp->cmd_head); } -static inline void -i596_reset(struct net_device *dev, - volatile struct i596_private *lp, int ioaddr) { +static void i596_reset(struct net_device *dev, struct i596_private *lp, int ioaddr) { if (lp->scb.command && i596_timeout(dev, "i596_reset", 100)) ; @@ -789,7 +794,8 @@ lp->scb.command = CUC_ABORT | RX_ABORT; CA(); - + barrier(); + /* wait for shutdown */ if (lp->scb.command && i596_timeout(dev, "i596_reset(2)", 400)) ; @@ -803,7 +809,7 @@ } static void i596_add_cmd(struct net_device *dev, struct i596_cmd *cmd) { - volatile struct i596_private *lp = dev->priv; + struct i596_private *lp = dev->priv; int ioaddr = dev->base_addr; unsigned long flags; @@ -811,8 +817,8 @@ cmd->command |= (CMD_EOL | CMD_INTR); cmd->pa_next = I596_NULL; - save_flags(flags); - cli(); + spin_lock_irqsave(&lp->cmd_lock, flags); + if (lp->cmd_head) { lp->cmd_tail->pa_next = va_to_pa(cmd); } else { @@ -827,64 +833,45 @@ lp->cmd_backlog++; lp->cmd_head = pa_to_va(lp->scb.pa_cmd); - restore_flags(flags); + spin_unlock_irqrestore(&lp->cmd_lock, flags); if (lp->cmd_backlog > 16) { int tickssofar = jiffies - lp->last_cmd; - if (tickssofar < 25) return; + if (tickssofar < HZ/4) + return; - printk("%s: command unit timed out, status resetting.\n", - dev->name); + printk(KERN_WARNING "%s: command unit timed out, status resetting.\n", dev->name); i596_reset(dev, lp, ioaddr); } } -static int -i596_open(struct net_device *dev) { +static int i596_open(struct net_device *dev) +{ int i; i = request_irq(dev->irq, &i596_interrupt, SA_SHIRQ, dev->name, dev); if (i) { - printk("%s: IRQ %d not free\n", dev->name, dev->irq); + printk(KERN_ERR "%s: IRQ %d not free\n", dev->name, dev->irq); return i; } if ((i = init_rx_bufs(dev, RX_RING_SIZE)) < RX_RING_SIZE) - printk("%s: only able to allocate %d receive buffers\n", - dev->name, i); + printk(KERN_ERR "%s: only able to allocate %d receive buffers\n", dev->name, i); if (i < 4) { -// release buffers free_irq(dev->irq, dev); return -EAGAIN; } - netif_start_queue(dev); - init_i596(dev); - return 0; /* Always succeed */ } -static int -i596_start_xmit (struct sk_buff *skb, struct net_device *dev) { - volatile struct i596_private *lp = dev->priv; +static int i596_start_xmit (struct sk_buff *skb, struct net_device *dev) { + struct i596_private *lp = dev->priv; struct tx_cmd *tx_cmd; short length; - /* If some higher level thinks we've missed a tx-done interrupt - we are passed NULL. n.b. dev_tint handles the cli()/sti() - itself. */ - if (skb == NULL) { - printk ("What about dev_tint\n"); - /* dev_tint(dev); */ - return 0; - } - - /* shouldn't happen */ - if (skb->len <= 0) - return 0; - length = skb->len; if (length < ETH_ZLEN) { @@ -896,14 +883,10 @@ dev->trans_start = jiffies; - tx_cmd = (struct tx_cmd *) - kmalloc ((sizeof (struct tx_cmd) - + sizeof (struct i596_tbd)), GFP_ATOMIC); + tx_cmd = (struct tx_cmd *) kmalloc ((sizeof (struct tx_cmd) + sizeof (struct i596_tbd)), GFP_ATOMIC); if (tx_cmd == NULL) { - printk ("%s: i596_xmit Memory squeeze, dropping packet.\n", - dev->name); + printk(KERN_WARNING "%s: i596_xmit Memory squeeze, dropping packet.\n", dev->name); lp->stats.tx_dropped++; - dev_kfree_skb (skb); } else { struct i596_tbd *tx_cmd_tbd; @@ -934,11 +917,11 @@ static void i596_tx_timeout (struct net_device *dev) { - volatile struct i596_private *lp = dev->priv; + struct i596_private *lp = dev->priv; int ioaddr = dev->base_addr; /* Transmitter timeout, serious problems. */ - printk ("%s: transmit timed out, status resetting.\n", dev->name); + printk(KERN_WARNING "%s: transmit timed out, status resetting.\n", dev->name); lp->stats.tx_errors++; /* Try to restart the adaptor */ @@ -957,8 +940,8 @@ netif_wake_queue(dev); } -static void -print_eth(char *add) { +static void print_eth(char *add) +{ int i; printk ("Dest "); @@ -975,9 +958,8 @@ (unsigned char) add[12], (unsigned char) add[13]); } -int __init -lp486e_probe(struct net_device *dev) { - volatile struct i596_private *lp; +int __init lp486e_probe(struct net_device *dev) { + struct i596_private *lp; unsigned char eth_addr[6] = { 0, 0xaa, 0, 0, 0, 0 }; unsigned char *bios; int i, j; @@ -996,14 +978,14 @@ /* * Allocate working memory, 16-byte aligned */ - dev->mem_start = (unsigned long) - kmalloc(sizeof(struct i596_private) + 0x0f, GFP_KERNEL); + dev->mem_start = (unsigned long) kmalloc(sizeof(struct i596_private) + 0x0f, GFP_KERNEL); if (!dev->mem_start) goto err_out; dev->priv = (void *)((dev->mem_start + 0xf) & 0xfffffff0); lp = (struct i596_private *) dev->priv; memset((void *)lp, 0, sizeof(struct i596_private)); - + spin_lock_init(&lp->cmd_lock); + /* * Do we really have this thing? */ @@ -1071,14 +1053,16 @@ static inline void i596_handle_CU_completion(struct net_device *dev, - volatile struct i596_private *lp, + struct i596_private *lp, unsigned short status, unsigned short *ack_cmdp) { - volatile struct i596_cmd *cmd; + struct i596_cmd *cmd; int frames_out = 0; int commands_done = 0; int cmd_val; + unsigned long flags; + spin_lock_irqsave(&lp->cmd_lock, flags); cmd = lp->cmd_head; while (lp->cmd_head && (lp->cmd_head->status & CMD_STAT_C)) { @@ -1160,31 +1144,29 @@ lp->last_cmd = jiffies; } + barrier(); } cmd = lp->cmd_head; while (cmd && (cmd != lp->cmd_tail)) { cmd->command &= 0x1fff; cmd = pa_to_va(cmd->pa_next); + barrier(); } if (lp->cmd_head) *ack_cmdp |= CUC_START; lp->scb.pa_cmd = va_to_pa(lp->cmd_head); + spin_unlock_irqrestore(&lp->cmd_lock, flags); } static void i596_interrupt (int irq, void *dev_instance, struct pt_regs *regs) { struct net_device *dev = (struct net_device *) dev_instance; - volatile struct i596_private *lp; + struct i596_private *lp; unsigned short status, ack_cmd = 0; int frames_in = 0; - if (dev == NULL) { - printk ("i596_interrupt(): irq %d for unknown device.\n", irq); - return; - } - lp = (struct i596_private *) dev->priv; /* @@ -1251,7 +1233,7 @@ } static int i596_close(struct net_device *dev) { - volatile struct i596_private *lp = dev->priv; + struct i596_private *lp = dev->priv; netif_stop_queue(dev); @@ -1284,7 +1266,7 @@ */ static void set_multicast_list(struct net_device *dev) { - volatile struct i596_private *lp = dev->priv; + struct i596_private *lp = dev->priv; struct i596_cmd *cmd; if (i596_debug > 1) @@ -1294,12 +1276,9 @@ if (dev->mc_count > 0) { struct dev_mc_list *dmi; char *cp; - cmd = (struct i596_cmd *) - kmalloc(sizeof(struct i596_cmd)+2+dev->mc_count*6, - GFP_ATOMIC); + cmd = (struct i596_cmd *)kmalloc(sizeof(struct i596_cmd)+2+dev->mc_count*6, GFP_ATOMIC); if (cmd == NULL) { - printk ("%s: set_multicast Memory squeeze.\n", - dev->name); + printk (KERN_ERR "%s: set_multicast Memory squeeze.\n", dev->name); return; } cmd->command = CmdMulticastList; @@ -1316,8 +1295,7 @@ if (lp->set_conf.pa_next != I596_NULL) { return; } - if (dev->mc_count == 0 && - !(dev->flags & (IFF_PROMISC | IFF_ALLMULTI))) { + if (dev->mc_count == 0 && !(dev->flags & (IFF_PROMISC | IFF_ALLMULTI))) { if (dev->flags & IFF_ALLMULTI) dev->flags |= IFF_PROMISC; lp->i596_config[8] &= ~0x01; - To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
| ![\](/images/icornerr.gif) |