root/drivers/net/seeq8005.c

/* [previous][next][first][last][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. seeq8005_probe
  2. seeq8005_probe1
  3. seeq8005_open
  4. seeq8005_send_packet
  5. seeq8005_interrupt
  6. seeq8005_rx
  7. seeq8005_close
  8. seeq8005_get_stats
  9. set_multicast_list
  10. seeq8005_init
  11. hardware_send_packet
  12. wait_for_buffer

   1 /* seeq8005.c: A network driver for linux. */
   2 /*
   3         Based on skeleton.c,
   4         Written 1993-94 by Donald Becker.
   5         See the skeleton.c file for further copyright information.
   6 
   7         This software may be used and distributed according to the terms
   8         of the GNU Public License, incorporated herein by reference.
   9 
  10         The author may be reached as hamish@zot.apana.org.au
  11 
  12         This file is a network device driver for the SEEQ 8005 chipset and
  13         the Linux operating system.
  14 
  15 */
  16 
  17 static const char *version =
  18         "seeq8005.c:v1.00 8/07/95 Hamish Coleman (hamish@zot.apana.org.au)\n";
  19 
  20 /* Always include 'config.h' first in case the user wants to turn on
  21    or override something. */
  22 #include <linux/config.h>
  23 
  24 /*
  25   Sources:
  26         SEEQ 8005 databook
  27         
  28   Version history:
  29         1.00    Public release. cosmetic changes (no warnings now)
  30         0.68    Turning per- packet,interrupt debug messages off - testing for release.
  31         0.67    timing problems/bad buffer reads seem to be fixed now
  32         0.63    *!@$ protocol=eth_type_trans -- now packets flow
  33         0.56    Send working
  34         0.48    Receive working
  35 */
  36 
  37 #include <linux/kernel.h>
  38 #include <linux/sched.h>
  39 #include <linux/types.h>
  40 #include <linux/fcntl.h>
  41 #include <linux/interrupt.h>
  42 #include <linux/ptrace.h>
  43 #include <linux/ioport.h>
  44 #include <linux/in.h>
  45 #include <linux/malloc.h>
  46 #include <linux/string.h>
  47 #include <asm/system.h>
  48 #include <asm/bitops.h>
  49 #include <asm/io.h>
  50 #include <asm/dma.h>
  51 #include <linux/errno.h>
  52 
  53 #include <linux/netdevice.h>
  54 #include <linux/etherdevice.h>
  55 #include <linux/skbuff.h>
  56 #include "seeq8005.h"
  57 extern struct device *init_etherdev(struct device *dev, int sizeof_private,
  58                                                                         unsigned long *mem_startp);
  59 
  60 /* First, a few definitions that the brave might change. */
  61 /* A zero-terminated list of I/O addresses to be probed. */
  62 static unsigned int seeq8005_portlist[] =
  63    { 0x300, 0x320, 0x340, 0x360, 0};
  64 
  65 /* use 0 for production, 1 for verification, >2 for debug */
  66 #ifndef NET_DEBUG
  67 #define NET_DEBUG 1
  68 #endif
  69 static unsigned int net_debug = NET_DEBUG;
  70 
  71 /* Information that need to be kept for each board. */
  72 struct net_local {
  73         struct enet_statistics stats;
  74         unsigned short receive_ptr;             /* What address in packet memory do we expect a recv_pkt_header? */
  75         long open_time;                         /* Useless example local info. */
  76 };
  77 
  78 /* The station (ethernet) address prefix, used for IDing the board. */
  79 #define SA_ADDR0 0x00
  80 #define SA_ADDR1 0x80
  81 #define SA_ADDR2 0x4b
  82 
  83 /* Index to functions, as function prototypes. */
  84 
  85 extern int seeq8005_probe(struct device *dev);
  86 
  87 static int seeq8005_probe1(struct device *dev, int ioaddr);
  88 static int seeq8005_open(struct device *dev);
  89 static int seeq8005_send_packet(struct sk_buff *skb, struct device *dev);
  90 static void seeq8005_interrupt(int irq, struct pt_regs *regs);
  91 static void seeq8005_rx(struct device *dev);
  92 static int seeq8005_close(struct device *dev);
  93 static struct enet_statistics *seeq8005_get_stats(struct device *dev);
  94 static void set_multicast_list(struct device *dev, int num_addrs, void *addrs);
  95 
  96 /* Example routines you must write ;->. */
  97 #define tx_done(dev)    (inw(SEEQ_STATUS) & SEEQSTAT_TX_ON)
  98 extern void hardware_send_packet(struct device *dev, char *buf, int length);
  99 extern void seeq8005_init(struct device *dev, int startp);
 100 inline void wait_for_buffer(struct device *dev);
 101 
 102 
 103 /* Check for a network adaptor of this type, and return '0' iff one exists.
 104    If dev->base_addr == 0, probe all likely locations.
 105    If dev->base_addr == 1, always return failure.
 106    If dev->base_addr == 2, allocate space for the device and return success
 107    (detachable devices only).
 108    */
 109 #ifdef HAVE_DEVLIST
 110 /* Support for a alternate probe manager, which will eliminate the
 111    boilerplate below. */
 112 struct netdev_entry seeq8005_drv =
 113 {"seeq8005", seeq8005_probe1, SEEQ8005_IO_EXTENT, seeq8005_portlist};
 114 #else
 115 int
 116 seeq8005_probe(struct device *dev)
     /* [previous][next][first][last][top][bottom][index][help] */
 117 {
 118         int i;
 119         int base_addr = dev ? dev->base_addr : 0;
 120 
 121         if (base_addr > 0x1ff)          /* Check a single specified location. */
 122                 return seeq8005_probe1(dev, base_addr);
 123         else if (base_addr != 0)        /* Don't probe at all. */
 124                 return ENXIO;
 125 
 126         for (i = 0; seeq8005_portlist[i]; i++) {
 127                 int ioaddr = seeq8005_portlist[i];
 128                 if (check_region(ioaddr, SEEQ8005_IO_EXTENT))
 129                         continue;
 130                 if (seeq8005_probe1(dev, ioaddr) == 0)
 131                         return 0;
 132         }
 133 
 134         return ENODEV;
 135 }
 136 #endif
 137 
 138 /* This is the real probe routine.  Linux has a history of friendly device
 139    probes on the ISA bus.  A good device probes avoids doing writes, and
 140    verifies that the correct device exists and functions.  */
 141 
 142 static int seeq8005_probe1(struct device *dev, int ioaddr)
     /* [previous][next][first][last][top][bottom][index][help] */
 143 {
 144         static unsigned version_printed = 0;
 145         int i,j;
 146         unsigned char SA_prom[32];
 147         int old_cfg1;
 148         int old_cfg2;
 149         int old_stat;
 150         int old_dmaar;
 151         int old_rear;
 152 
 153         if (net_debug>1)
 154                 printk("seeq8005: probing at 0x%x\n",ioaddr);
 155 
 156         old_stat = inw(SEEQ_STATUS);                                    /* read status register */
 157         if (old_stat == 0xffff)
 158                 return ENODEV;                                          /* assume that 0xffff == no device */
 159         if ( (old_stat & 0x1800) != 0x1800 ) {                          /* assume that unused bits are 1, as my manual says */
 160                 if (net_debug>1) {
 161                         printk("seeq8005: reserved stat bits != 0x1800\n");
 162                         printk("          == 0x%04x\n",old_stat);
 163                 }
 164                 return ENODEV;
 165         }
 166 
 167         old_rear = inw(SEEQ_REA);
 168         if (old_rear == 0xffff) {
 169                 outw(0,SEEQ_REA);
 170                 if (inw(SEEQ_REA) == 0xffff) {                          /* assume that 0xffff == no device */
 171                         return ENODEV;
 172                 }
 173         } else if ((old_rear & 0xff00) != 0xff00) {                     /* assume that unused bits are 1 */
 174                 if (net_debug>1) {
 175                         printk("seeq8005: unused rear bits != 0xff00\n");
 176                         printk("          == 0x%04x\n",old_rear);
 177                 }
 178                 return ENODEV;
 179         }
 180         
 181         old_cfg2 = inw(SEEQ_CFG2);                                      /* read CFG2 register */
 182         old_cfg1 = inw(SEEQ_CFG1);
 183         old_dmaar = inw(SEEQ_DMAAR);
 184         
 185         if (net_debug>4) {
 186                 printk("seeq8005: stat = 0x%04x\n",old_stat);
 187                 printk("seeq8005: cfg1 = 0x%04x\n",old_cfg1);
 188                 printk("seeq8005: cfg2 = 0x%04x\n",old_cfg2);
 189                 printk("seeq8005: raer = 0x%04x\n",old_rear);
 190                 printk("seeq8005: dmaar= 0x%04x\n",old_dmaar);
 191         }
 192         
 193         outw( SEEQCMD_FIFO_WRITE | SEEQCMD_SET_ALL_OFF, SEEQ_CMD);      /* setup for reading PROM */
 194         outw( 0, SEEQ_DMAAR);                                           /* set starting PROM address */
 195         outw( SEEQCFG1_BUFFER_PROM, SEEQ_CFG1);                         /* set buffer to look at PROM */
 196         
 197         
 198         j=0;
 199         for(i=0; i <32; i++) {
 200                 j+= SA_prom[i] = inw(SEEQ_BUFFER) & 0xff;
 201         }
 202 
 203 #if 0
 204         /* untested because I only have the one card */
 205         if ( (j&0xff) != 0 ) {                                          /* checksum appears to be 8bit = 0 */
 206                 if (net_debug>1) {                                      /* check this before deciding that we have a card */
 207                         printk("seeq8005: prom sum error\n");
 208                 }
 209                 outw( old_stat, SEEQ_STATUS);
 210                 outw( old_dmaar, SEEQ_DMAAR);
 211                 outw( old_cfg1, SEEQ_CFG1);
 212                 return ENODEV;
 213         }
 214 #endif
 215 
 216         outw( SEEQCFG2_RESET, SEEQ_CFG2);                               /* reset the card */
 217         SLOW_DOWN_IO;                                                   /* have to wait 4us after a reset - should be fixed */
 218         SLOW_DOWN_IO;
 219         SLOW_DOWN_IO;
 220         SLOW_DOWN_IO;
 221         outw( SEEQCMD_SET_ALL_OFF, SEEQ_CMD);
 222         
 223         if (net_debug) {
 224                 printk("seeq8005: prom sum = 0x%08x\n",j);
 225                 for(j=0; j<32; j+=16) {
 226                         printk("seeq8005: prom %02x: ",j);
 227                         for(i=0;i<16;i++) {
 228                                 printk("%02x ",SA_prom[j|i]);
 229                         }
 230                         printk(" ");
 231                         for(i=0;i<16;i++) {
 232                                 if ((SA_prom[j|i]>31)&&(SA_prom[j|i]<127)) {
 233                                         printk("%c", SA_prom[j|i]);
 234                                 } else {
 235                                         printk(" ");
 236                                 }
 237                         }
 238                         printk("\n");
 239                 }
 240         }
 241 
 242 #if 0   
 243         /* 
 244          * testing the packet buffer memory doesnt work yet
 245          * but all other buffer accesses do 
 246          *                      - fixing is not a priority
 247          */
 248         if (net_debug>1) {                                      /* test packet buffer memory */
 249                 printk("seeq8005: testing packet buffer ... ");
 250                 outw( SEEQCFG1_BUFFER_BUFFER, SEEQ_CFG1);
 251                 outw( SEEQCMD_FIFO_WRITE | SEEQCMD_SET_ALL_OFF, SEEQ_CMD);
 252                 outw( 0 , SEEQ_DMAAR);
 253                 for(i=0;i<32768;i++) {
 254                         outw(0x5a5a, SEEQ_BUFFER);
 255                 }
 256                 j=jiffies+HZ;
 257                 while ( ((inw(SEEQ_STATUS) & SEEQSTAT_FIFO_EMPTY) != SEEQSTAT_FIFO_EMPTY) && jiffies < j )
 258                         mb();
 259                 outw( 0 , SEEQ_DMAAR);
 260                 while ( ((inw(SEEQ_STATUS) & SEEQSTAT_WINDOW_INT) != SEEQSTAT_WINDOW_INT) && jiffies < j+HZ)
 261                         mb();
 262                 if ( (inw(SEEQ_STATUS) & SEEQSTAT_WINDOW_INT) == SEEQSTAT_WINDOW_INT)
 263                         outw( SEEQCMD_WINDOW_INT_ACK | (inw(SEEQ_STATUS)& SEEQCMD_INT_MASK), SEEQ_CMD);
 264                 outw( SEEQCMD_FIFO_READ | SEEQCMD_SET_ALL_OFF, SEEQ_CMD);
 265                 j=0;
 266                 for(i=0;i<32768;i++) {
 267                         if (inw(SEEQ_BUFFER) != 0x5a5a)
 268                                 j++;
 269                 }
 270                 if (j) {
 271                         printk("%i\n",j);
 272                 } else {
 273                         printk("ok.\n");
 274                 }
 275         }
 276 #endif
 277 
 278         /* Allocate a new 'dev' if needed. */
 279         if (dev == NULL)
 280                 dev = init_etherdev(0, sizeof(struct net_local), 0);
 281 
 282         if (net_debug  &&  version_printed++ == 0)
 283                 printk(version);
 284 
 285         printk("%s: %s found at %#3x, ", dev->name, "seeq8005", ioaddr);
 286 
 287         /* Fill in the 'dev' fields. */
 288         dev->base_addr = ioaddr;
 289 
 290         /* Retrieve and print the ethernet address. */
 291         for (i = 0; i < 6; i++)
 292                 printk(" %2.2x", dev->dev_addr[i] = SA_prom[i+6]);
 293 
 294         if (dev->irq == 0xff)
 295                 ;                       /* Do nothing: a user-level program will set it. */
 296         else if (dev->irq < 2) {        /* "Auto-IRQ" */
 297                 autoirq_setup(0);
 298                 
 299                 outw( SEEQCMD_RX_INT_EN | SEEQCMD_SET_RX_ON | SEEQCMD_SET_RX_OFF, SEEQ_CMD );
 300 
 301                 dev->irq = autoirq_report(0);
 302                 
 303                 if (net_debug >= 2)
 304                         printk(" autoirq is %d\n", dev->irq);
 305         } else if (dev->irq == 2)
 306           /* Fixup for users that don't know that IRQ 2 is really IRQ 9,
 307            * or don't know which one to set. 
 308            */
 309           dev->irq = 9;
 310 
 311 #if 0
 312         {
 313                  int irqval = request_irq(dev->irq, &seeq8005_interrupt, 0, "seeq8005");
 314                  if (irqval) {
 315                          printk ("%s: unable to get IRQ %d (irqval=%d).\n", dev->name,
 316                                          dev->irq, irqval);
 317                          return EAGAIN;
 318                  }
 319         }
 320 #endif
 321 
 322         /* Grab the region so we can find another board if autoIRQ fails. */
 323         request_region(ioaddr, SEEQ8005_IO_EXTENT,"seeq8005");
 324 
 325         /* Initialize the device structure. */
 326         if (dev->priv == NULL)
 327                 dev->priv = kmalloc(sizeof(struct net_local), GFP_KERNEL);
 328         memset(dev->priv, 0, sizeof(struct net_local));
 329 
 330         dev->open               = seeq8005_open;
 331         dev->stop               = seeq8005_close;
 332         dev->hard_start_xmit = seeq8005_send_packet;
 333         dev->get_stats  = seeq8005_get_stats;
 334         dev->set_multicast_list = &set_multicast_list;
 335 
 336         /* Fill in the fields of the device structure with ethernet values. */
 337         ether_setup(dev);
 338 
 339         return 0;
 340 }
 341 
 342 
 343 /* Open/initialize the board.  This is called (in the current kernel)
 344    sometime after booting when the 'ifconfig' program is run.
 345 
 346    This routine should set everything up anew at each open, even
 347    registers that "should" only need to be set once at boot, so that
 348    there is non-reboot way to recover if something goes wrong.
 349    */
 350 static int
 351 seeq8005_open(struct device *dev)
     /* [previous][next][first][last][top][bottom][index][help] */
 352 {
 353         struct net_local *lp = (struct net_local *)dev->priv;
 354 
 355         {
 356                  int irqval = request_irq(dev->irq, &seeq8005_interrupt, 0, "seeq8005");
 357                  if (irqval) {
 358                          printk ("%s: unable to get IRQ %d (irqval=%d).\n", dev->name,
 359                                          dev->irq, irqval);
 360                          return EAGAIN;
 361                  }
 362         }
 363         irq2dev_map[dev->irq] = dev;
 364 
 365         /* Reset the hardware here.  Don't forget to set the station address. */
 366         seeq8005_init(dev, 1);
 367 
 368         lp->open_time = jiffies;
 369 
 370         dev->tbusy = 0;
 371         dev->interrupt = 0;
 372         dev->start = 1;
 373         return 0;
 374 }
 375 
 376 static int
 377 seeq8005_send_packet(struct sk_buff *skb, struct device *dev)
     /* [previous][next][first][last][top][bottom][index][help] */
 378 {
 379         int ioaddr = dev->base_addr;
 380 
 381         if (dev->tbusy) {
 382                 /* If we get here, some higher level has decided we are broken.
 383                    There should really be a "kick me" function call instead. */
 384                 int tickssofar = jiffies - dev->trans_start;
 385                 if (tickssofar < 5)
 386                         return 1;
 387                 printk("%s: transmit timed out, %s?\n", dev->name,
 388                            tx_done(dev) ? "IRQ conflict" : "network cable problem");
 389                 /* Try to restart the adaptor. */
 390                 seeq8005_init(dev, 1);
 391                 dev->tbusy=0;
 392                 dev->trans_start = jiffies;
 393         }
 394 
 395         /* If some higher layer thinks we've missed an tx-done interrupt
 396            we are passed NULL. Caution: dev_tint() handles the cli()/sti()
 397            itself. */
 398         if (skb == NULL) {
 399                 dev_tint(dev);
 400                 return 0;
 401         }
 402 
 403         /* Block a timer-based transmit from overlapping.  This could better be
 404            done with atomic_swap(1, dev->tbusy), but set_bit() works as well. */
 405         if (set_bit(0, (void*)&dev->tbusy) != 0)
 406                 printk("%s: Transmitter access conflict.\n", dev->name);
 407         else {
 408                 short length = ETH_ZLEN < skb->len ? skb->len : ETH_ZLEN;
 409                 unsigned char *buf = skb->data;
 410 
 411                 hardware_send_packet(dev, buf, length); 
 412                 dev->trans_start = jiffies;
 413         }
 414         dev_kfree_skb (skb, FREE_WRITE);
 415 
 416         /* You might need to clean up and record Tx statistics here. */
 417 
 418         return 0;
 419 }
 420 
 421 /* The typical workload of the driver:
 422    Handle the network interface interrupts. */
 423 static void
 424 seeq8005_interrupt(int irq, struct pt_regs * regs)
     /* [previous][next][first][last][top][bottom][index][help] */
 425 {
 426         struct device *dev = (struct device *)(irq2dev_map[irq]);
 427         struct net_local *lp;
 428         int ioaddr, status, boguscount = 0;
 429 
 430         if (dev == NULL) {
 431                 printk ("net_interrupt(): irq %d for unknown device.\n", irq);
 432                 return;
 433         }
 434         
 435         if (dev->interrupt)
 436                 printk ("%s: Re-entering the interrupt handler.\n", dev->name);
 437         dev->interrupt = 1;
 438 
 439         ioaddr = dev->base_addr;
 440         lp = (struct net_local *)dev->priv;
 441 
 442         status = inw(SEEQ_STATUS);
 443         do {
 444                 if (net_debug >2) {
 445                         printk("%s: int, status=0x%04x\n",dev->name,status);
 446                 }
 447                 
 448                 if (status & SEEQSTAT_WINDOW_INT) {
 449                         outw( SEEQCMD_WINDOW_INT_ACK | (status & SEEQCMD_INT_MASK), SEEQ_CMD);
 450                         if (net_debug) {
 451                                 printk("%s: window int!\n",dev->name);
 452                         }
 453                 }
 454                 if (status & SEEQSTAT_TX_INT) {
 455                         outw( SEEQCMD_TX_INT_ACK | (status & SEEQCMD_INT_MASK), SEEQ_CMD);
 456                         lp->stats.tx_packets++;
 457                         dev->tbusy = 0;
 458                         mark_bh(NET_BH);        /* Inform upper layers. */
 459                 }
 460                 if (status & SEEQSTAT_RX_INT) {
 461                         /* Got a packet(s). */
 462                         seeq8005_rx(dev);
 463                 }
 464                 status = inw(SEEQ_STATUS);
 465         } while ( (++boguscount < 10) && (status & SEEQSTAT_ANY_INT)) ;
 466 
 467         if(net_debug>2) {
 468                 printk("%s: eoi\n",dev->name);
 469         }
 470         dev->interrupt = 0;
 471         return;
 472 }
 473 
 474 /* We have a good packet(s), get it/them out of the buffers. */
 475 static void
 476 seeq8005_rx(struct device *dev)
     /* [previous][next][first][last][top][bottom][index][help] */
 477 {
 478         struct net_local *lp = (struct net_local *)dev->priv;
 479         int boguscount = 10;
 480         int pkt_hdr;
 481         int ioaddr = dev->base_addr;
 482 
 483         do {
 484                 int next_packet;
 485                 int pkt_len;
 486                 int i;
 487                 int status;
 488 
 489                 status = inw(SEEQ_STATUS);
 490                 outw( lp->receive_ptr, SEEQ_DMAAR);
 491                 outw(SEEQCMD_FIFO_READ | SEEQCMD_RX_INT_ACK | (status & SEEQCMD_INT_MASK), SEEQ_CMD);
 492                 wait_for_buffer(dev);
 493                 next_packet = ntohs(inw(SEEQ_BUFFER));
 494                 pkt_hdr = inw(SEEQ_BUFFER);
 495                 
 496                 if (net_debug>2) {
 497                         printk("%s: 0x%04x recv next=0x%04x, hdr=0x%04x\n",dev->name,lp->receive_ptr,next_packet,pkt_hdr);
 498                 }
 499                         
 500                 if ((next_packet == 0) || ((pkt_hdr & SEEQPKTH_CHAIN)==0)) {    /* Read all the frames? */
 501                         return;                                                 /* Done for now */
 502                 }
 503                         
 504                 if ((pkt_hdr & SEEQPKTS_DONE)==0)
 505                         break;
 506                         
 507                 if (next_packet < lp->receive_ptr) {
 508                         pkt_len = (next_packet + 0x10000 - ((DEFAULT_TEA+1)<<8)) - lp->receive_ptr - 4;
 509                 } else {
 510                         pkt_len = next_packet - lp->receive_ptr - 4;
 511                 }
 512                 
 513                 if (next_packet < ((DEFAULT_TEA+1)<<8)) {                       /* is the next_packet address sane? */
 514                         printk("%s: recv packet ring corrupt, resetting board\n",dev->name);
 515                         seeq8005_init(dev,1);
 516                         return;
 517                 }
 518                 
 519                 lp->receive_ptr = next_packet;
 520                 
 521                 if (net_debug>2) {
 522                         printk("%s: recv len=0x%04x\n",dev->name,pkt_len);
 523                 }
 524 
 525                 if (pkt_hdr & SEEQPKTS_ANY_ERROR) {                             /* There was an error. */
 526                         lp->stats.rx_errors++;
 527                         if (pkt_hdr & SEEQPKTS_SHORT) lp->stats.rx_frame_errors++;
 528                         if (pkt_hdr & SEEQPKTS_DRIB) lp->stats.rx_frame_errors++;
 529                         if (pkt_hdr & SEEQPKTS_OVERSIZE) lp->stats.rx_over_errors++;
 530                         if (pkt_hdr & SEEQPKTS_CRC_ERR) lp->stats.rx_crc_errors++;
 531                         /* skip over this packet */
 532                         outw( SEEQCMD_FIFO_WRITE | SEEQCMD_DMA_INT_ACK | (status & SEEQCMD_INT_MASK), SEEQ_CMD);
 533                         outw( (lp->receive_ptr & 0xff00)>>8, SEEQ_REA);
 534                 } else {
 535                         /* Malloc up new buffer. */
 536                         struct sk_buff *skb;
 537                         unsigned char *buf;
 538 
 539                         skb = dev_alloc_skb(pkt_len);
 540                         if (skb == NULL) {
 541                                 printk("%s: Memory squeeze, dropping packet.\n", dev->name);
 542                                 lp->stats.rx_dropped++;
 543                                 break;
 544                         }
 545                         skb->dev = dev;
 546                         skb_reserve(skb, 2);    /* align data on 16 byte */
 547                         buf = skb_put(skb,pkt_len);
 548                         
 549                         insw(SEEQ_BUFFER, buf, (pkt_len + 1) >> 1);
 550                         
 551                         if (net_debug>2) {
 552                                 char * p = buf;
 553                                 printk("%s: recv ",dev->name);
 554                                 for(i=0;i<14;i++) {
 555                                         printk("%02x ",*(p++)&0xff);
 556                                 }
 557                                 printk("\n");
 558                         }
 559 
 560                         skb->protocol=eth_type_trans(skb,dev);
 561                         netif_rx(skb);
 562                         lp->stats.rx_packets++;
 563                 }
 564         } while ((--boguscount) && (pkt_hdr & SEEQPKTH_CHAIN));
 565 
 566         /* If any worth-while packets have been received, netif_rx()
 567            has done a mark_bh(NET_BH) for us and will work on them
 568            when we get to the bottom-half routine. */
 569         return;
 570 }
 571 
 572 /* The inverse routine to net_open(). */
 573 static int
 574 seeq8005_close(struct device *dev)
     /* [previous][next][first][last][top][bottom][index][help] */
 575 {
 576         struct net_local *lp = (struct net_local *)dev->priv;
 577         int ioaddr = dev->base_addr;
 578 
 579         lp->open_time = 0;
 580 
 581         dev->tbusy = 1;
 582         dev->start = 0;
 583 
 584         /* Flush the Tx and disable Rx here. */
 585         outw( SEEQCMD_SET_ALL_OFF, SEEQ_CMD);
 586 
 587         free_irq(dev->irq);
 588 
 589         irq2dev_map[dev->irq] = 0;
 590 
 591         /* Update the statistics here. */
 592 
 593         return 0;
 594 
 595 }
 596 
 597 /* Get the current statistics.  This may be called with the card open or
 598    closed. */
 599 static struct enet_statistics *
 600 seeq8005_get_stats(struct device *dev)
     /* [previous][next][first][last][top][bottom][index][help] */
 601 {
 602         struct net_local *lp = (struct net_local *)dev->priv;
 603 
 604         return &lp->stats;
 605 }
 606 
 607 /* Set or clear the multicast filter for this adaptor.
 608    num_addrs == -1      Promiscuous mode, receive all packets
 609    num_addrs == 0       Normal mode, clear multicast list
 610    num_addrs > 0        Multicast mode, receive normal and MC packets, and do
 611                         best-effort filtering.
 612  */
 613 static void
 614 set_multicast_list(struct device *dev, int num_addrs, void *addrs)
     /* [previous][next][first][last][top][bottom][index][help] */
 615 {
 616 /*
 617  * I _could_ do upto 6 addresses here, but wont (yet?)
 618  */
 619 
 620 #if 0
 621         int ioaddr = dev->base_addr;
 622 /*
 623  * hmm, not even sure if my matching works _anyway_ - seem to be receiving
 624  * _everything_ . . .
 625  */
 626  
 627         if (num_addrs) {                        /* Enable promiscuous mode */
 628                 outw( (inw(SEEQ_CFG1) & ~SEEQCFG1_MATCH_MASK)| SEEQCFG1_MATCH_ALL,  SEEQ_CFG1);
 629         } else {                                /* Disable promiscuous mode, use normal mode */
 630                 outw( (inw(SEEQ_CFG1) & ~SEEQCFG1_MATCH_MASK)| SEEQCFG1_MATCH_BROAD, SEEQ_CFG1);
 631         }
 632 #endif
 633 }
 634 
 635 void seeq8005_init(struct device *dev, int startp)
     /* [previous][next][first][last][top][bottom][index][help] */
 636 {
 637         struct net_local *lp = (struct net_local *)dev->priv;
 638         int ioaddr = dev->base_addr;
 639         int i;
 640         
 641         outw(SEEQCFG2_RESET, SEEQ_CFG2);        /* reset device */
 642         SLOW_DOWN_IO;                           /* have to wait 4us after a reset - should be fixed */
 643         SLOW_DOWN_IO;
 644         SLOW_DOWN_IO;
 645         SLOW_DOWN_IO;
 646         
 647         outw( SEEQCMD_FIFO_WRITE | SEEQCMD_SET_ALL_OFF, SEEQ_CMD);
 648         outw( 0, SEEQ_DMAAR);                   /* load start address into both low and high byte */
 649 /*      wait_for_buffer(dev); */                /* I think that you only need a wait for memory buffer */
 650         outw( SEEQCFG1_BUFFER_MAC0, SEEQ_CFG1);
 651         
 652         for(i=0;i<6;i++) {                      /* set Station address */
 653                 outb(dev->dev_addr[i], SEEQ_BUFFER);
 654                 SLOW_DOWN_IO;
 655         }
 656         
 657         outw( SEEQCFG1_BUFFER_TEA, SEEQ_CFG1);  /* set xmit end area pointer to 16K */
 658         outb( DEFAULT_TEA, SEEQ_BUFFER);        /* this gives us 16K of send buffer and 48K of recv buffer */
 659         
 660         lp->receive_ptr = (DEFAULT_TEA+1)<<8;   /* so we can find our packet_header */
 661         outw( lp->receive_ptr, SEEQ_RPR);       /* Receive Pointer Register is set to recv buffer memory */
 662         
 663         outw( 0x00ff, SEEQ_REA);                /* Receive Area End */
 664 
 665         if (net_debug>4) {
 666                 printk("%s: SA0 = ",dev->name);
 667 
 668                 outw( SEEQCMD_FIFO_READ | SEEQCMD_SET_ALL_OFF, SEEQ_CMD);
 669                 outw( 0, SEEQ_DMAAR);
 670                 outw( SEEQCFG1_BUFFER_MAC0, SEEQ_CFG1);
 671                 
 672                 for(i=0;i<6;i++) {
 673                         printk("%02x ",inb(SEEQ_BUFFER));
 674                 }
 675                 printk("\n");
 676         }
 677         
 678         outw( SEEQCFG1_MAC0_EN | SEEQCFG1_MATCH_BROAD | SEEQCFG1_BUFFER_BUFFER, SEEQ_CFG1);
 679         outw( SEEQCFG2_AUTO_REA | SEEQCFG2_CTRLO, SEEQ_CFG2);
 680         outw( SEEQCMD_SET_RX_ON | SEEQCMD_TX_INT_EN | SEEQCMD_RX_INT_EN, SEEQ_CMD);
 681 
 682         if (net_debug>4) {
 683                 int old_cfg1;
 684                 old_cfg1 = inw(SEEQ_CFG1);
 685                 printk("%s: stat = 0x%04x\n",dev->name,inw(SEEQ_STATUS));
 686                 printk("%s: cfg1 = 0x%04x\n",dev->name,old_cfg1);
 687                 printk("%s: cfg2 = 0x%04x\n",dev->name,inw(SEEQ_CFG2));
 688                 printk("%s: raer = 0x%04x\n",dev->name,inw(SEEQ_REA));
 689                 printk("%s: dmaar= 0x%04x\n",dev->name,inw(SEEQ_DMAAR));
 690                 
 691         }
 692 }       
 693 
 694 
 695 void hardware_send_packet(struct device * dev, char *buf, int length)
     /* [previous][next][first][last][top][bottom][index][help] */
 696 {
 697         int ioaddr = dev->base_addr;
 698         int status = inw(SEEQ_STATUS);
 699         int transmit_ptr = 0;
 700         int tmp;
 701 
 702         if (net_debug>4) {
 703                 printk("%s: send 0x%04x\n",dev->name,length);
 704         }
 705         
 706         /* Set FIFO to writemode and set packet-buffer address */
 707         outw( SEEQCMD_FIFO_WRITE | (status & SEEQCMD_INT_MASK), SEEQ_CMD);
 708         outw( transmit_ptr, SEEQ_DMAAR);
 709         
 710         /* output SEEQ Packet header barfage */
 711         outw( htons(length + 4), SEEQ_BUFFER);
 712         outw( SEEQPKTH_XMIT | SEEQPKTH_DATA_FOLLOWS | SEEQPKTH_XMIT_INT_EN, SEEQ_BUFFER );
 713         
 714         /* blat the buffer */
 715         outsw( SEEQ_BUFFER, buf, (length +1) >> 1);
 716         /* paranoia !! */
 717         outw( 0, SEEQ_BUFFER);
 718         outw( 0, SEEQ_BUFFER);
 719         
 720         /* set address of start of transmit chain */
 721         outw( transmit_ptr, SEEQ_TPR);
 722         
 723         /* drain FIFO */
 724         tmp = jiffies;
 725         while ( (((status=inw(SEEQ_STATUS)) & SEEQSTAT_FIFO_EMPTY) == 0) && (jiffies < tmp + HZ))
 726                 mb();
 727         
 728         /* doit ! */
 729         outw( SEEQCMD_WINDOW_INT_ACK | SEEQCMD_SET_TX_ON | (status & SEEQCMD_INT_MASK), SEEQ_CMD);
 730         
 731 }
 732 
 733 
 734 /*
 735  * wait_for_buffer
 736  *
 737  * This routine waits for the SEEQ chip to assert that the FIFO is ready
 738  * by checking for a window interrupt, and then clearing it
 739  */
 740 inline void wait_for_buffer(struct device * dev)
     /* [previous][next][first][last][top][bottom][index][help] */
 741 {
 742         int ioaddr = dev->base_addr;
 743         int tmp;
 744         int status;
 745         
 746         tmp = jiffies + HZ;
 747         while ( ( ((status=inw(SEEQ_STATUS)) & SEEQSTAT_WINDOW_INT) != SEEQSTAT_WINDOW_INT) && jiffies < tmp)
 748                 mb();
 749                 
 750         if ( (status & SEEQSTAT_WINDOW_INT) == SEEQSTAT_WINDOW_INT)
 751                 outw( SEEQCMD_WINDOW_INT_ACK | (status & SEEQCMD_INT_MASK), SEEQ_CMD);
 752 }
 753         
 754 
 755 /*
 756  * Local variables:
 757  *  compile-command: "gcc -D__KERNEL__ -I/usr/src/linux/net/inet -Wall -Wstrict-prototypes -O6 -m486 -c skeleton.c"
 758  *  version-control: t
 759  *  kept-new-versions: 5
 760  *  tab-width: 4
 761  * End:
 762  */

/* [previous][next][first][last][top][bottom][index][help] */