diff options
author | Linus Torvalds <torvalds@ppc970.osdl.org> | 2005-04-16 18:20:36 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@ppc970.osdl.org> | 2005-04-16 18:20:36 -0400 |
commit | 1da177e4c3f41524e886b7f1b8a0c1fc7321cac2 (patch) | |
tree | 0bba044c4ce775e45a88a51686b5d9f90697ea9d /drivers/net/smc9194.c |
Linux-2.6.12-rc2v2.6.12-rc2
Initial git repository build. I'm not bothering with the full history,
even though we have it. We can create a separate "historical" git
archive of that later if we want to, and in the meantime it's about
3.2GB when imported into git - space that would just make the early
git days unnecessarily complicated, when we don't have a lot of good
infrastructure for it.
Let it rip!
Diffstat (limited to 'drivers/net/smc9194.c')
-rw-r--r-- | drivers/net/smc9194.c | 1631 |
1 files changed, 1631 insertions, 0 deletions
diff --git a/drivers/net/smc9194.c b/drivers/net/smc9194.c new file mode 100644 index 000000000000..f86697da04d6 --- /dev/null +++ b/drivers/net/smc9194.c | |||
@@ -0,0 +1,1631 @@ | |||
1 | /*------------------------------------------------------------------------ | ||
2 | . smc9194.c | ||
3 | . This is a driver for SMC's 9000 series of Ethernet cards. | ||
4 | . | ||
5 | . Copyright (C) 1996 by Erik Stahlman | ||
6 | . This software may be used and distributed according to the terms | ||
7 | . of the GNU General Public License, incorporated herein by reference. | ||
8 | . | ||
9 | . "Features" of the SMC chip: | ||
10 | . 4608 byte packet memory. ( for the 91C92. Others have more ) | ||
11 | . EEPROM for configuration | ||
12 | . AUI/TP selection ( mine has 10Base2/10BaseT select ) | ||
13 | . | ||
14 | . Arguments: | ||
15 | . io = for the base address | ||
16 | . irq = for the IRQ | ||
17 | . ifport = 0 for autodetect, 1 for TP, 2 for AUI ( or 10base2 ) | ||
18 | . | ||
19 | . author: | ||
20 | . Erik Stahlman ( erik@vt.edu ) | ||
21 | . contributors: | ||
22 | . Arnaldo Carvalho de Melo <acme@conectiva.com.br> | ||
23 | . | ||
24 | . Hardware multicast code from Peter Cammaert ( pc@denkart.be ) | ||
25 | . | ||
26 | . Sources: | ||
27 | . o SMC databook | ||
28 | . o skeleton.c by Donald Becker ( becker@scyld.com ) | ||
29 | . o ( a LOT of advice from Becker as well ) | ||
30 | . | ||
31 | . History: | ||
32 | . 12/07/95 Erik Stahlman written, got receive/xmit handled | ||
33 | . 01/03/96 Erik Stahlman worked out some bugs, actually usable!!! :-) | ||
34 | . 01/06/96 Erik Stahlman cleaned up some, better testing, etc | ||
35 | . 01/29/96 Erik Stahlman fixed autoirq, added multicast | ||
36 | . 02/01/96 Erik Stahlman 1. disabled all interrupts in smc_reset | ||
37 | . 2. got rid of post-decrementing bug -- UGH. | ||
38 | . 02/13/96 Erik Stahlman Tried to fix autoirq failure. Added more | ||
39 | . descriptive error messages. | ||
40 | . 02/15/96 Erik Stahlman Fixed typo that caused detection failure | ||
41 | . 02/23/96 Erik Stahlman Modified it to fit into kernel tree | ||
42 | . Added support to change hardware address | ||
43 | . Cleared stats on opens | ||
44 | . 02/26/96 Erik Stahlman Trial support for Kernel 1.2.13 | ||
45 | . Kludge for automatic IRQ detection | ||
46 | . 03/04/96 Erik Stahlman Fixed kernel 1.3.70 + | ||
47 | . Fixed bug reported by Gardner Buchanan in | ||
48 | . smc_enable, with outw instead of outb | ||
49 | . 03/06/96 Erik Stahlman Added hardware multicast from Peter Cammaert | ||
50 | . 04/14/00 Heiko Pruessing (SMA Regelsysteme) Fixed bug in chip memory | ||
51 | . allocation | ||
52 | . 08/20/00 Arnaldo Melo fix kfree(skb) in smc_hardware_send_packet | ||
53 | . 12/15/00 Christian Jullien fix "Warning: kfree_skb on hard IRQ" | ||
54 | . 11/08/01 Matt Domsch Use common crc32 function | ||
55 | ----------------------------------------------------------------------------*/ | ||
56 | |||
57 | static const char version[] = | ||
58 | "smc9194.c:v0.14 12/15/00 by Erik Stahlman (erik@vt.edu)\n"; | ||
59 | |||
60 | #include <linux/module.h> | ||
61 | #include <linux/kernel.h> | ||
62 | #include <linux/types.h> | ||
63 | #include <linux/fcntl.h> | ||
64 | #include <linux/interrupt.h> | ||
65 | #include <linux/ioport.h> | ||
66 | #include <linux/in.h> | ||
67 | #include <linux/slab.h> | ||
68 | #include <linux/string.h> | ||
69 | #include <linux/init.h> | ||
70 | #include <linux/crc32.h> | ||
71 | #include <linux/errno.h> | ||
72 | #include <linux/netdevice.h> | ||
73 | #include <linux/etherdevice.h> | ||
74 | #include <linux/skbuff.h> | ||
75 | #include <linux/bitops.h> | ||
76 | |||
77 | #include <asm/io.h> | ||
78 | |||
79 | #include "smc9194.h" | ||
80 | |||
81 | #define DRV_NAME "smc9194" | ||
82 | |||
83 | /*------------------------------------------------------------------------ | ||
84 | . | ||
85 | . Configuration options, for the experienced user to change. | ||
86 | . | ||
87 | -------------------------------------------------------------------------*/ | ||
88 | |||
89 | /* | ||
90 | . Do you want to use 32 bit xfers? This should work on all chips, as | ||
91 | . the chipset is designed to accommodate them. | ||
92 | */ | ||
93 | #ifdef __sh__ | ||
94 | #undef USE_32_BIT | ||
95 | #else | ||
96 | #define USE_32_BIT 1 | ||
97 | #endif | ||
98 | |||
99 | #if defined(__H8300H__) || defined(__H8300S__) | ||
100 | #define NO_AUTOPROBE | ||
101 | #undef insl | ||
102 | #undef outsl | ||
103 | #define insl(a,b,l) io_insl_noswap(a,b,l) | ||
104 | #define outsl(a,b,l) io_outsl_noswap(a,b,l) | ||
105 | #endif | ||
106 | |||
107 | /* | ||
108 | .the SMC9194 can be at any of the following port addresses. To change, | ||
109 | .for a slightly different card, you can add it to the array. Keep in | ||
110 | .mind that the array must end in zero. | ||
111 | */ | ||
112 | |||
113 | struct devlist { | ||
114 | unsigned int port; | ||
115 | unsigned int irq; | ||
116 | }; | ||
117 | |||
118 | #if defined(CONFIG_H8S_EDOSK2674) | ||
119 | static struct devlist smc_devlist[] __initdata = { | ||
120 | {.port = 0xf80000, .irq = 16}, | ||
121 | {.port = 0, .irq = 0 }, | ||
122 | }; | ||
123 | #else | ||
124 | static struct devlist smc_devlist[] __initdata = { | ||
125 | {.port = 0x200, .irq = 0}, | ||
126 | {.port = 0x220, .irq = 0}, | ||
127 | {.port = 0x240, .irq = 0}, | ||
128 | {.port = 0x260, .irq = 0}, | ||
129 | {.port = 0x280, .irq = 0}, | ||
130 | {.port = 0x2A0, .irq = 0}, | ||
131 | {.port = 0x2C0, .irq = 0}, | ||
132 | {.port = 0x2E0, .irq = 0}, | ||
133 | {.port = 0x300, .irq = 0}, | ||
134 | {.port = 0x320, .irq = 0}, | ||
135 | {.port = 0x340, .irq = 0}, | ||
136 | {.port = 0x360, .irq = 0}, | ||
137 | {.port = 0x380, .irq = 0}, | ||
138 | {.port = 0x3A0, .irq = 0}, | ||
139 | {.port = 0x3C0, .irq = 0}, | ||
140 | {.port = 0x3E0, .irq = 0}, | ||
141 | {.port = 0, .irq = 0}, | ||
142 | }; | ||
143 | #endif | ||
144 | /* | ||
145 | . Wait time for memory to be free. This probably shouldn't be | ||
146 | . tuned that much, as waiting for this means nothing else happens | ||
147 | . in the system | ||
148 | */ | ||
149 | #define MEMORY_WAIT_TIME 16 | ||
150 | |||
151 | /* | ||
152 | . DEBUGGING LEVELS | ||
153 | . | ||
154 | . 0 for normal operation | ||
155 | . 1 for slightly more details | ||
156 | . >2 for various levels of increasingly useless information | ||
157 | . 2 for interrupt tracking, status flags | ||
158 | . 3 for packet dumps, etc. | ||
159 | */ | ||
160 | #define SMC_DEBUG 0 | ||
161 | |||
162 | #if (SMC_DEBUG > 2 ) | ||
163 | #define PRINTK3(x) printk x | ||
164 | #else | ||
165 | #define PRINTK3(x) | ||
166 | #endif | ||
167 | |||
168 | #if SMC_DEBUG > 1 | ||
169 | #define PRINTK2(x) printk x | ||
170 | #else | ||
171 | #define PRINTK2(x) | ||
172 | #endif | ||
173 | |||
174 | #ifdef SMC_DEBUG | ||
175 | #define PRINTK(x) printk x | ||
176 | #else | ||
177 | #define PRINTK(x) | ||
178 | #endif | ||
179 | |||
180 | |||
181 | /*------------------------------------------------------------------------ | ||
182 | . | ||
183 | . The internal workings of the driver. If you are changing anything | ||
184 | . here with the SMC stuff, you should have the datasheet and known | ||
185 | . what you are doing. | ||
186 | . | ||
187 | -------------------------------------------------------------------------*/ | ||
188 | #define CARDNAME "SMC9194" | ||
189 | |||
190 | |||
191 | /* store this information for the driver.. */ | ||
192 | struct smc_local { | ||
193 | /* | ||
194 | these are things that the kernel wants me to keep, so users | ||
195 | can find out semi-useless statistics of how well the card is | ||
196 | performing | ||
197 | */ | ||
198 | struct net_device_stats stats; | ||
199 | |||
200 | /* | ||
201 | If I have to wait until memory is available to send | ||
202 | a packet, I will store the skbuff here, until I get the | ||
203 | desired memory. Then, I'll send it out and free it. | ||
204 | */ | ||
205 | struct sk_buff * saved_skb; | ||
206 | |||
207 | /* | ||
208 | . This keeps track of how many packets that I have | ||
209 | . sent out. When an TX_EMPTY interrupt comes, I know | ||
210 | . that all of these have been sent. | ||
211 | */ | ||
212 | int packets_waiting; | ||
213 | }; | ||
214 | |||
215 | |||
216 | /*----------------------------------------------------------------- | ||
217 | . | ||
218 | . The driver can be entered at any of the following entry points. | ||
219 | . | ||
220 | .------------------------------------------------------------------ */ | ||
221 | |||
222 | /* | ||
223 | . This is called by register_netdev(). It is responsible for | ||
224 | . checking the portlist for the SMC9000 series chipset. If it finds | ||
225 | . one, then it will initialize the device, find the hardware information, | ||
226 | . and sets up the appropriate device parameters. | ||
227 | . NOTE: Interrupts are *OFF* when this procedure is called. | ||
228 | . | ||
229 | . NB:This shouldn't be static since it is referred to externally. | ||
230 | */ | ||
231 | struct net_device *smc_init(int unit); | ||
232 | |||
233 | /* | ||
234 | . The kernel calls this function when someone wants to use the device, | ||
235 | . typically 'ifconfig ethX up'. | ||
236 | */ | ||
237 | static int smc_open(struct net_device *dev); | ||
238 | |||
239 | /* | ||
240 | . Our watchdog timed out. Called by the networking layer | ||
241 | */ | ||
242 | static void smc_timeout(struct net_device *dev); | ||
243 | |||
244 | /* | ||
245 | . This is called by the kernel in response to 'ifconfig ethX down'. It | ||
246 | . is responsible for cleaning up everything that the open routine | ||
247 | . does, and maybe putting the card into a powerdown state. | ||
248 | */ | ||
249 | static int smc_close(struct net_device *dev); | ||
250 | |||
251 | /* | ||
252 | . This routine allows the proc file system to query the driver's | ||
253 | . statistics. | ||
254 | */ | ||
255 | static struct net_device_stats * smc_query_statistics( struct net_device *dev); | ||
256 | |||
257 | /* | ||
258 | . Finally, a call to set promiscuous mode ( for TCPDUMP and related | ||
259 | . programs ) and multicast modes. | ||
260 | */ | ||
261 | static void smc_set_multicast_list(struct net_device *dev); | ||
262 | |||
263 | |||
264 | /*--------------------------------------------------------------- | ||
265 | . | ||
266 | . Interrupt level calls.. | ||
267 | . | ||
268 | ----------------------------------------------------------------*/ | ||
269 | |||
270 | /* | ||
271 | . Handles the actual interrupt | ||
272 | */ | ||
273 | static irqreturn_t smc_interrupt(int irq, void *, struct pt_regs *regs); | ||
274 | /* | ||
275 | . This is a separate procedure to handle the receipt of a packet, to | ||
276 | . leave the interrupt code looking slightly cleaner | ||
277 | */ | ||
278 | static inline void smc_rcv( struct net_device *dev ); | ||
279 | /* | ||
280 | . This handles a TX interrupt, which is only called when an error | ||
281 | . relating to a packet is sent. | ||
282 | */ | ||
283 | static inline void smc_tx( struct net_device * dev ); | ||
284 | |||
285 | /* | ||
286 | ------------------------------------------------------------ | ||
287 | . | ||
288 | . Internal routines | ||
289 | . | ||
290 | ------------------------------------------------------------ | ||
291 | */ | ||
292 | |||
293 | /* | ||
294 | . Test if a given location contains a chip, trying to cause as | ||
295 | . little damage as possible if it's not a SMC chip. | ||
296 | */ | ||
297 | static int smc_probe(struct net_device *dev, int ioaddr); | ||
298 | |||
299 | /* | ||
300 | . A rather simple routine to print out a packet for debugging purposes. | ||
301 | */ | ||
302 | #if SMC_DEBUG > 2 | ||
303 | static void print_packet( byte *, int ); | ||
304 | #endif | ||
305 | |||
306 | #define tx_done(dev) 1 | ||
307 | |||
308 | /* this is called to actually send the packet to the chip */ | ||
309 | static void smc_hardware_send_packet( struct net_device * dev ); | ||
310 | |||
311 | /* Since I am not sure if I will have enough room in the chip's ram | ||
312 | . to store the packet, I call this routine, which either sends it | ||
313 | . now, or generates an interrupt when the card is ready for the | ||
314 | . packet */ | ||
315 | static int smc_wait_to_send_packet( struct sk_buff * skb, struct net_device *dev ); | ||
316 | |||
317 | /* this does a soft reset on the device */ | ||
318 | static void smc_reset( int ioaddr ); | ||
319 | |||
320 | /* Enable Interrupts, Receive, and Transmit */ | ||
321 | static void smc_enable( int ioaddr ); | ||
322 | |||
323 | /* this puts the device in an inactive state */ | ||
324 | static void smc_shutdown( int ioaddr ); | ||
325 | |||
326 | /* This routine will find the IRQ of the driver if one is not | ||
327 | . specified in the input to the device. */ | ||
328 | static int smc_findirq( int ioaddr ); | ||
329 | |||
330 | /* | ||
331 | . Function: smc_reset( int ioaddr ) | ||
332 | . Purpose: | ||
333 | . This sets the SMC91xx chip to its normal state, hopefully from whatever | ||
334 | . mess that any other DOS driver has put it in. | ||
335 | . | ||
336 | . Maybe I should reset more registers to defaults in here? SOFTRESET should | ||
337 | . do that for me. | ||
338 | . | ||
339 | . Method: | ||
340 | . 1. send a SOFT RESET | ||
341 | . 2. wait for it to finish | ||
342 | . 3. enable autorelease mode | ||
343 | . 4. reset the memory management unit | ||
344 | . 5. clear all interrupts | ||
345 | . | ||
346 | */ | ||
347 | static void smc_reset( int ioaddr ) | ||
348 | { | ||
349 | /* This resets the registers mostly to defaults, but doesn't | ||
350 | affect EEPROM. That seems unnecessary */ | ||
351 | SMC_SELECT_BANK( 0 ); | ||
352 | outw( RCR_SOFTRESET, ioaddr + RCR ); | ||
353 | |||
354 | /* this should pause enough for the chip to be happy */ | ||
355 | SMC_DELAY( ); | ||
356 | |||
357 | /* Set the transmit and receive configuration registers to | ||
358 | default values */ | ||
359 | outw( RCR_CLEAR, ioaddr + RCR ); | ||
360 | outw( TCR_CLEAR, ioaddr + TCR ); | ||
361 | |||
362 | /* set the control register to automatically | ||
363 | release successfully transmitted packets, to make the best | ||
364 | use out of our limited memory */ | ||
365 | SMC_SELECT_BANK( 1 ); | ||
366 | outw( inw( ioaddr + CONTROL ) | CTL_AUTO_RELEASE , ioaddr + CONTROL ); | ||
367 | |||
368 | /* Reset the MMU */ | ||
369 | SMC_SELECT_BANK( 2 ); | ||
370 | outw( MC_RESET, ioaddr + MMU_CMD ); | ||
371 | |||
372 | /* Note: It doesn't seem that waiting for the MMU busy is needed here, | ||
373 | but this is a place where future chipsets _COULD_ break. Be wary | ||
374 | of issuing another MMU command right after this */ | ||
375 | |||
376 | outb( 0, ioaddr + INT_MASK ); | ||
377 | } | ||
378 | |||
379 | /* | ||
380 | . Function: smc_enable | ||
381 | . Purpose: let the chip talk to the outside work | ||
382 | . Method: | ||
383 | . 1. Enable the transmitter | ||
384 | . 2. Enable the receiver | ||
385 | . 3. Enable interrupts | ||
386 | */ | ||
387 | static void smc_enable( int ioaddr ) | ||
388 | { | ||
389 | SMC_SELECT_BANK( 0 ); | ||
390 | /* see the header file for options in TCR/RCR NORMAL*/ | ||
391 | outw( TCR_NORMAL, ioaddr + TCR ); | ||
392 | outw( RCR_NORMAL, ioaddr + RCR ); | ||
393 | |||
394 | /* now, enable interrupts */ | ||
395 | SMC_SELECT_BANK( 2 ); | ||
396 | outb( SMC_INTERRUPT_MASK, ioaddr + INT_MASK ); | ||
397 | } | ||
398 | |||
399 | /* | ||
400 | . Function: smc_shutdown | ||
401 | . Purpose: closes down the SMC91xxx chip. | ||
402 | . Method: | ||
403 | . 1. zero the interrupt mask | ||
404 | . 2. clear the enable receive flag | ||
405 | . 3. clear the enable xmit flags | ||
406 | . | ||
407 | . TODO: | ||
408 | . (1) maybe utilize power down mode. | ||
409 | . Why not yet? Because while the chip will go into power down mode, | ||
410 | . the manual says that it will wake up in response to any I/O requests | ||
411 | . in the register space. Empirical results do not show this working. | ||
412 | */ | ||
413 | static void smc_shutdown( int ioaddr ) | ||
414 | { | ||
415 | /* no more interrupts for me */ | ||
416 | SMC_SELECT_BANK( 2 ); | ||
417 | outb( 0, ioaddr + INT_MASK ); | ||
418 | |||
419 | /* and tell the card to stay away from that nasty outside world */ | ||
420 | SMC_SELECT_BANK( 0 ); | ||
421 | outb( RCR_CLEAR, ioaddr + RCR ); | ||
422 | outb( TCR_CLEAR, ioaddr + TCR ); | ||
423 | #if 0 | ||
424 | /* finally, shut the chip down */ | ||
425 | SMC_SELECT_BANK( 1 ); | ||
426 | outw( inw( ioaddr + CONTROL ), CTL_POWERDOWN, ioaddr + CONTROL ); | ||
427 | #endif | ||
428 | } | ||
429 | |||
430 | |||
431 | /* | ||
432 | . Function: smc_setmulticast( int ioaddr, int count, dev_mc_list * adds ) | ||
433 | . Purpose: | ||
434 | . This sets the internal hardware table to filter out unwanted multicast | ||
435 | . packets before they take up memory. | ||
436 | . | ||
437 | . The SMC chip uses a hash table where the high 6 bits of the CRC of | ||
438 | . address are the offset into the table. If that bit is 1, then the | ||
439 | . multicast packet is accepted. Otherwise, it's dropped silently. | ||
440 | . | ||
441 | . To use the 6 bits as an offset into the table, the high 3 bits are the | ||
442 | . number of the 8 bit register, while the low 3 bits are the bit within | ||
443 | . that register. | ||
444 | . | ||
445 | . This routine is based very heavily on the one provided by Peter Cammaert. | ||
446 | */ | ||
447 | |||
448 | |||
449 | static void smc_setmulticast( int ioaddr, int count, struct dev_mc_list * addrs ) { | ||
450 | int i; | ||
451 | unsigned char multicast_table[ 8 ]; | ||
452 | struct dev_mc_list * cur_addr; | ||
453 | /* table for flipping the order of 3 bits */ | ||
454 | unsigned char invert3[] = { 0, 4, 2, 6, 1, 5, 3, 7 }; | ||
455 | |||
456 | /* start with a table of all zeros: reject all */ | ||
457 | memset( multicast_table, 0, sizeof( multicast_table ) ); | ||
458 | |||
459 | cur_addr = addrs; | ||
460 | for ( i = 0; i < count ; i ++, cur_addr = cur_addr->next ) { | ||
461 | int position; | ||
462 | |||
463 | /* do we have a pointer here? */ | ||
464 | if ( !cur_addr ) | ||
465 | break; | ||
466 | /* make sure this is a multicast address - shouldn't this | ||
467 | be a given if we have it here ? */ | ||
468 | if ( !( *cur_addr->dmi_addr & 1 ) ) | ||
469 | continue; | ||
470 | |||
471 | /* only use the low order bits */ | ||
472 | position = ether_crc_le(6, cur_addr->dmi_addr) & 0x3f; | ||
473 | |||
474 | /* do some messy swapping to put the bit in the right spot */ | ||
475 | multicast_table[invert3[position&7]] |= | ||
476 | (1<<invert3[(position>>3)&7]); | ||
477 | |||
478 | } | ||
479 | /* now, the table can be loaded into the chipset */ | ||
480 | SMC_SELECT_BANK( 3 ); | ||
481 | |||
482 | for ( i = 0; i < 8 ; i++ ) { | ||
483 | outb( multicast_table[i], ioaddr + MULTICAST1 + i ); | ||
484 | } | ||
485 | } | ||
486 | |||
487 | /* | ||
488 | . Function: smc_wait_to_send_packet( struct sk_buff * skb, struct net_device * ) | ||
489 | . Purpose: | ||
490 | . Attempt to allocate memory for a packet, if chip-memory is not | ||
491 | . available, then tell the card to generate an interrupt when it | ||
492 | . is available. | ||
493 | . | ||
494 | . Algorithm: | ||
495 | . | ||
496 | . o if the saved_skb is not currently null, then drop this packet | ||
497 | . on the floor. This should never happen, because of TBUSY. | ||
498 | . o if the saved_skb is null, then replace it with the current packet, | ||
499 | . o See if I can sending it now. | ||
500 | . o (NO): Enable interrupts and let the interrupt handler deal with it. | ||
501 | . o (YES):Send it now. | ||
502 | */ | ||
503 | static int smc_wait_to_send_packet( struct sk_buff * skb, struct net_device * dev ) | ||
504 | { | ||
505 | struct smc_local *lp = netdev_priv(dev); | ||
506 | unsigned int ioaddr = dev->base_addr; | ||
507 | word length; | ||
508 | unsigned short numPages; | ||
509 | word time_out; | ||
510 | |||
511 | netif_stop_queue(dev); | ||
512 | /* Well, I want to send the packet.. but I don't know | ||
513 | if I can send it right now... */ | ||
514 | |||
515 | if ( lp->saved_skb) { | ||
516 | /* THIS SHOULD NEVER HAPPEN. */ | ||
517 | lp->stats.tx_aborted_errors++; | ||
518 | printk(CARDNAME": Bad Craziness - sent packet while busy.\n" ); | ||
519 | return 1; | ||
520 | } | ||
521 | lp->saved_skb = skb; | ||
522 | |||
523 | length = skb->len; | ||
524 | |||
525 | if (length < ETH_ZLEN) { | ||
526 | skb = skb_padto(skb, ETH_ZLEN); | ||
527 | if (skb == NULL) { | ||
528 | netif_wake_queue(dev); | ||
529 | return 0; | ||
530 | } | ||
531 | length = ETH_ZLEN; | ||
532 | } | ||
533 | |||
534 | /* | ||
535 | ** The MMU wants the number of pages to be the number of 256 bytes | ||
536 | ** 'pages', minus 1 ( since a packet can't ever have 0 pages :) ) | ||
537 | ** | ||
538 | ** Pkt size for allocating is data length +6 (for additional status words, | ||
539 | ** length and ctl!) If odd size last byte is included in this header. | ||
540 | */ | ||
541 | numPages = ((length & 0xfffe) + 6) / 256; | ||
542 | |||
543 | if (numPages > 7 ) { | ||
544 | printk(CARDNAME": Far too big packet error. \n"); | ||
545 | /* freeing the packet is a good thing here... but should | ||
546 | . any packets of this size get down here? */ | ||
547 | dev_kfree_skb (skb); | ||
548 | lp->saved_skb = NULL; | ||
549 | /* this IS an error, but, i don't want the skb saved */ | ||
550 | netif_wake_queue(dev); | ||
551 | return 0; | ||
552 | } | ||
553 | /* either way, a packet is waiting now */ | ||
554 | lp->packets_waiting++; | ||
555 | |||
556 | /* now, try to allocate the memory */ | ||
557 | SMC_SELECT_BANK( 2 ); | ||
558 | outw( MC_ALLOC | numPages, ioaddr + MMU_CMD ); | ||
559 | /* | ||
560 | . Performance Hack | ||
561 | . | ||
562 | . wait a short amount of time.. if I can send a packet now, I send | ||
563 | . it now. Otherwise, I enable an interrupt and wait for one to be | ||
564 | . available. | ||
565 | . | ||
566 | . I could have handled this a slightly different way, by checking to | ||
567 | . see if any memory was available in the FREE MEMORY register. However, | ||
568 | . either way, I need to generate an allocation, and the allocation works | ||
569 | . no matter what, so I saw no point in checking free memory. | ||
570 | */ | ||
571 | time_out = MEMORY_WAIT_TIME; | ||
572 | do { | ||
573 | word status; | ||
574 | |||
575 | status = inb( ioaddr + INTERRUPT ); | ||
576 | if ( status & IM_ALLOC_INT ) { | ||
577 | /* acknowledge the interrupt */ | ||
578 | outb( IM_ALLOC_INT, ioaddr + INTERRUPT ); | ||
579 | break; | ||
580 | } | ||
581 | } while ( -- time_out ); | ||
582 | |||
583 | if ( !time_out ) { | ||
584 | /* oh well, wait until the chip finds memory later */ | ||
585 | SMC_ENABLE_INT( IM_ALLOC_INT ); | ||
586 | PRINTK2((CARDNAME": memory allocation deferred. \n")); | ||
587 | /* it's deferred, but I'll handle it later */ | ||
588 | return 0; | ||
589 | } | ||
590 | /* or YES! I can send the packet now.. */ | ||
591 | smc_hardware_send_packet(dev); | ||
592 | netif_wake_queue(dev); | ||
593 | return 0; | ||
594 | } | ||
595 | |||
596 | /* | ||
597 | . Function: smc_hardware_send_packet(struct net_device * ) | ||
598 | . Purpose: | ||
599 | . This sends the actual packet to the SMC9xxx chip. | ||
600 | . | ||
601 | . Algorithm: | ||
602 | . First, see if a saved_skb is available. | ||
603 | . ( this should NOT be called if there is no 'saved_skb' | ||
604 | . Now, find the packet number that the chip allocated | ||
605 | . Point the data pointers at it in memory | ||
606 | . Set the length word in the chip's memory | ||
607 | . Dump the packet to chip memory | ||
608 | . Check if a last byte is needed ( odd length packet ) | ||
609 | . if so, set the control flag right | ||
610 | . Tell the card to send it | ||
611 | . Enable the transmit interrupt, so I know if it failed | ||
612 | . Free the kernel data if I actually sent it. | ||
613 | */ | ||
614 | static void smc_hardware_send_packet( struct net_device * dev ) | ||
615 | { | ||
616 | struct smc_local *lp = netdev_priv(dev); | ||
617 | byte packet_no; | ||
618 | struct sk_buff * skb = lp->saved_skb; | ||
619 | word length; | ||
620 | unsigned int ioaddr; | ||
621 | byte * buf; | ||
622 | |||
623 | ioaddr = dev->base_addr; | ||
624 | |||
625 | if ( !skb ) { | ||
626 | PRINTK((CARDNAME": In XMIT with no packet to send \n")); | ||
627 | return; | ||
628 | } | ||
629 | length = ETH_ZLEN < skb->len ? skb->len : ETH_ZLEN; | ||
630 | buf = skb->data; | ||
631 | |||
632 | /* If I get here, I _know_ there is a packet slot waiting for me */ | ||
633 | packet_no = inb( ioaddr + PNR_ARR + 1 ); | ||
634 | if ( packet_no & 0x80 ) { | ||
635 | /* or isn't there? BAD CHIP! */ | ||
636 | printk(KERN_DEBUG CARDNAME": Memory allocation failed. \n"); | ||
637 | dev_kfree_skb_any(skb); | ||
638 | lp->saved_skb = NULL; | ||
639 | netif_wake_queue(dev); | ||
640 | return; | ||
641 | } | ||
642 | |||
643 | /* we have a packet address, so tell the card to use it */ | ||
644 | outb( packet_no, ioaddr + PNR_ARR ); | ||
645 | |||
646 | /* point to the beginning of the packet */ | ||
647 | outw( PTR_AUTOINC , ioaddr + POINTER ); | ||
648 | |||
649 | PRINTK3((CARDNAME": Trying to xmit packet of length %x\n", length )); | ||
650 | #if SMC_DEBUG > 2 | ||
651 | print_packet( buf, length ); | ||
652 | #endif | ||
653 | |||
654 | /* send the packet length ( +6 for status, length and ctl byte ) | ||
655 | and the status word ( set to zeros ) */ | ||
656 | #ifdef USE_32_BIT | ||
657 | outl( (length +6 ) << 16 , ioaddr + DATA_1 ); | ||
658 | #else | ||
659 | outw( 0, ioaddr + DATA_1 ); | ||
660 | /* send the packet length ( +6 for status words, length, and ctl*/ | ||
661 | outb( (length+6) & 0xFF,ioaddr + DATA_1 ); | ||
662 | outb( (length+6) >> 8 , ioaddr + DATA_1 ); | ||
663 | #endif | ||
664 | |||
665 | /* send the actual data | ||
666 | . I _think_ it's faster to send the longs first, and then | ||
667 | . mop up by sending the last word. It depends heavily | ||
668 | . on alignment, at least on the 486. Maybe it would be | ||
669 | . a good idea to check which is optimal? But that could take | ||
670 | . almost as much time as is saved? | ||
671 | */ | ||
672 | #ifdef USE_32_BIT | ||
673 | if ( length & 0x2 ) { | ||
674 | outsl(ioaddr + DATA_1, buf, length >> 2 ); | ||
675 | #if !defined(__H8300H__) && !defined(__H8300S__) | ||
676 | outw( *((word *)(buf + (length & 0xFFFFFFFC))),ioaddr +DATA_1); | ||
677 | #else | ||
678 | ctrl_outw( *((word *)(buf + (length & 0xFFFFFFFC))),ioaddr +DATA_1); | ||
679 | #endif | ||
680 | } | ||
681 | else | ||
682 | outsl(ioaddr + DATA_1, buf, length >> 2 ); | ||
683 | #else | ||
684 | outsw(ioaddr + DATA_1 , buf, (length ) >> 1); | ||
685 | #endif | ||
686 | /* Send the last byte, if there is one. */ | ||
687 | |||
688 | if ( (length & 1) == 0 ) { | ||
689 | outw( 0, ioaddr + DATA_1 ); | ||
690 | } else { | ||
691 | outb( buf[length -1 ], ioaddr + DATA_1 ); | ||
692 | outb( 0x20, ioaddr + DATA_1); | ||
693 | } | ||
694 | |||
695 | /* enable the interrupts */ | ||
696 | SMC_ENABLE_INT( (IM_TX_INT | IM_TX_EMPTY_INT) ); | ||
697 | |||
698 | /* and let the chipset deal with it */ | ||
699 | outw( MC_ENQUEUE , ioaddr + MMU_CMD ); | ||
700 | |||
701 | PRINTK2((CARDNAME": Sent packet of length %d \n",length)); | ||
702 | |||
703 | lp->saved_skb = NULL; | ||
704 | dev_kfree_skb_any (skb); | ||
705 | |||
706 | dev->trans_start = jiffies; | ||
707 | |||
708 | /* we can send another packet */ | ||
709 | netif_wake_queue(dev); | ||
710 | |||
711 | return; | ||
712 | } | ||
713 | |||
714 | /*------------------------------------------------------------------------- | ||
715 | | | ||
716 | | smc_init(int unit) | ||
717 | | Input parameters: | ||
718 | | dev->base_addr == 0, try to find all possible locations | ||
719 | | dev->base_addr == 1, return failure code | ||
720 | | dev->base_addr == 2, always allocate space, and return success | ||
721 | | dev->base_addr == <anything else> this is the address to check | ||
722 | | | ||
723 | | Output: | ||
724 | | pointer to net_device or ERR_PTR(error) | ||
725 | | | ||
726 | --------------------------------------------------------------------------- | ||
727 | */ | ||
728 | static int io; | ||
729 | static int irq; | ||
730 | static int ifport; | ||
731 | |||
732 | struct net_device * __init smc_init(int unit) | ||
733 | { | ||
734 | struct net_device *dev = alloc_etherdev(sizeof(struct smc_local)); | ||
735 | static struct devlist *smcdev = smc_devlist; | ||
736 | int err = 0; | ||
737 | |||
738 | #ifndef NO_AUTOPROBE | ||
739 | smcdev = smc_devlist; | ||
740 | #endif | ||
741 | if (!dev) | ||
742 | return ERR_PTR(-ENODEV); | ||
743 | |||
744 | if (unit >= 0) { | ||
745 | sprintf(dev->name, "eth%d", unit); | ||
746 | netdev_boot_setup_check(dev); | ||
747 | io = dev->base_addr; | ||
748 | irq = dev->irq; | ||
749 | } | ||
750 | |||
751 | SET_MODULE_OWNER(dev); | ||
752 | |||
753 | if (io > 0x1ff) { /* Check a single specified location. */ | ||
754 | err = smc_probe(dev, io); | ||
755 | } else if (io != 0) { /* Don't probe at all. */ | ||
756 | err = -ENXIO; | ||
757 | } else { | ||
758 | for (;smcdev->port; smcdev++) { | ||
759 | if (smc_probe(dev, smcdev->port) == 0) | ||
760 | break; | ||
761 | } | ||
762 | if (!smcdev->port) | ||
763 | err = -ENODEV; | ||
764 | } | ||
765 | if (err) | ||
766 | goto out; | ||
767 | err = register_netdev(dev); | ||
768 | if (err) | ||
769 | goto out1; | ||
770 | return dev; | ||
771 | out1: | ||
772 | free_irq(dev->irq, dev); | ||
773 | release_region(dev->base_addr, SMC_IO_EXTENT); | ||
774 | out: | ||
775 | free_netdev(dev); | ||
776 | return ERR_PTR(err); | ||
777 | } | ||
778 | |||
779 | /*---------------------------------------------------------------------- | ||
780 | . smc_findirq | ||
781 | . | ||
782 | . This routine has a simple purpose -- make the SMC chip generate an | ||
783 | . interrupt, so an auto-detect routine can detect it, and find the IRQ, | ||
784 | ------------------------------------------------------------------------ | ||
785 | */ | ||
786 | int __init smc_findirq( int ioaddr ) | ||
787 | { | ||
788 | #ifndef NO_AUTOPROBE | ||
789 | int timeout = 20; | ||
790 | unsigned long cookie; | ||
791 | |||
792 | |||
793 | cookie = probe_irq_on(); | ||
794 | |||
795 | /* | ||
796 | * What I try to do here is trigger an ALLOC_INT. This is done | ||
797 | * by allocating a small chunk of memory, which will give an interrupt | ||
798 | * when done. | ||
799 | */ | ||
800 | |||
801 | |||
802 | SMC_SELECT_BANK(2); | ||
803 | /* enable ALLOCation interrupts ONLY */ | ||
804 | outb( IM_ALLOC_INT, ioaddr + INT_MASK ); | ||
805 | |||
806 | /* | ||
807 | . Allocate 512 bytes of memory. Note that the chip was just | ||
808 | . reset so all the memory is available | ||
809 | */ | ||
810 | outw( MC_ALLOC | 1, ioaddr + MMU_CMD ); | ||
811 | |||
812 | /* | ||
813 | . Wait until positive that the interrupt has been generated | ||
814 | */ | ||
815 | while ( timeout ) { | ||
816 | byte int_status; | ||
817 | |||
818 | int_status = inb( ioaddr + INTERRUPT ); | ||
819 | |||
820 | if ( int_status & IM_ALLOC_INT ) | ||
821 | break; /* got the interrupt */ | ||
822 | timeout--; | ||
823 | } | ||
824 | /* there is really nothing that I can do here if timeout fails, | ||
825 | as probe_irq_off will return a 0 anyway, which is what I | ||
826 | want in this case. Plus, the clean up is needed in both | ||
827 | cases. */ | ||
828 | |||
829 | /* DELAY HERE! | ||
830 | On a fast machine, the status might change before the interrupt | ||
831 | is given to the processor. This means that the interrupt was | ||
832 | never detected, and probe_irq_off fails to report anything. | ||
833 | This should fix probe_irq_* problems. | ||
834 | */ | ||
835 | SMC_DELAY(); | ||
836 | SMC_DELAY(); | ||
837 | |||
838 | /* and disable all interrupts again */ | ||
839 | outb( 0, ioaddr + INT_MASK ); | ||
840 | |||
841 | /* and return what I found */ | ||
842 | return probe_irq_off(cookie); | ||
843 | #else /* NO_AUTOPROBE */ | ||
844 | struct devlist *smcdev; | ||
845 | for (smcdev = smc_devlist; smcdev->port; smcdev++) { | ||
846 | if (smcdev->port == ioaddr) | ||
847 | return smcdev->irq; | ||
848 | } | ||
849 | return 0; | ||
850 | #endif | ||
851 | } | ||
852 | |||
853 | /*---------------------------------------------------------------------- | ||
854 | . Function: smc_probe( int ioaddr ) | ||
855 | . | ||
856 | . Purpose: | ||
857 | . Tests to see if a given ioaddr points to an SMC9xxx chip. | ||
858 | . Returns a 0 on success | ||
859 | . | ||
860 | . Algorithm: | ||
861 | . (1) see if the high byte of BANK_SELECT is 0x33 | ||
862 | . (2) compare the ioaddr with the base register's address | ||
863 | . (3) see if I recognize the chip ID in the appropriate register | ||
864 | . | ||
865 | .--------------------------------------------------------------------- | ||
866 | */ | ||
867 | |||
868 | /*--------------------------------------------------------------- | ||
869 | . Here I do typical initialization tasks. | ||
870 | . | ||
871 | . o Initialize the structure if needed | ||
872 | . o print out my vanity message if not done so already | ||
873 | . o print out what type of hardware is detected | ||
874 | . o print out the ethernet address | ||
875 | . o find the IRQ | ||
876 | . o set up my private data | ||
877 | . o configure the dev structure with my subroutines | ||
878 | . o actually GRAB the irq. | ||
879 | . o GRAB the region | ||
880 | .----------------------------------------------------------------- | ||
881 | */ | ||
882 | static int __init smc_probe(struct net_device *dev, int ioaddr) | ||
883 | { | ||
884 | int i, memory, retval; | ||
885 | static unsigned version_printed; | ||
886 | unsigned int bank; | ||
887 | |||
888 | const char *version_string; | ||
889 | const char *if_string; | ||
890 | |||
891 | /* registers */ | ||
892 | word revision_register; | ||
893 | word base_address_register; | ||
894 | word configuration_register; | ||
895 | word memory_info_register; | ||
896 | word memory_cfg_register; | ||
897 | |||
898 | /* Grab the region so that no one else tries to probe our ioports. */ | ||
899 | if (!request_region(ioaddr, SMC_IO_EXTENT, DRV_NAME)) | ||
900 | return -EBUSY; | ||
901 | |||
902 | dev->irq = irq; | ||
903 | dev->if_port = ifport; | ||
904 | |||
905 | /* First, see if the high byte is 0x33 */ | ||
906 | bank = inw( ioaddr + BANK_SELECT ); | ||
907 | if ( (bank & 0xFF00) != 0x3300 ) { | ||
908 | retval = -ENODEV; | ||
909 | goto err_out; | ||
910 | } | ||
911 | /* The above MIGHT indicate a device, but I need to write to further | ||
912 | test this. */ | ||
913 | outw( 0x0, ioaddr + BANK_SELECT ); | ||
914 | bank = inw( ioaddr + BANK_SELECT ); | ||
915 | if ( (bank & 0xFF00 ) != 0x3300 ) { | ||
916 | retval = -ENODEV; | ||
917 | goto err_out; | ||
918 | } | ||
919 | #if !defined(CONFIG_H8S_EDOSK2674) | ||
920 | /* well, we've already written once, so hopefully another time won't | ||
921 | hurt. This time, I need to switch the bank register to bank 1, | ||
922 | so I can access the base address register */ | ||
923 | SMC_SELECT_BANK(1); | ||
924 | base_address_register = inw( ioaddr + BASE ); | ||
925 | if ( ioaddr != ( base_address_register >> 3 & 0x3E0 ) ) { | ||
926 | printk(CARDNAME ": IOADDR %x doesn't match configuration (%x)." | ||
927 | "Probably not a SMC chip\n", | ||
928 | ioaddr, base_address_register >> 3 & 0x3E0 ); | ||
929 | /* well, the base address register didn't match. Must not have | ||
930 | been a SMC chip after all. */ | ||
931 | retval = -ENODEV; | ||
932 | goto err_out; | ||
933 | } | ||
934 | #else | ||
935 | (void)base_address_register; /* Warning suppression */ | ||
936 | #endif | ||
937 | |||
938 | |||
939 | /* check if the revision register is something that I recognize. | ||
940 | These might need to be added to later, as future revisions | ||
941 | could be added. */ | ||
942 | SMC_SELECT_BANK(3); | ||
943 | revision_register = inw( ioaddr + REVISION ); | ||
944 | if ( !chip_ids[ ( revision_register >> 4 ) & 0xF ] ) { | ||
945 | /* I don't recognize this chip, so... */ | ||
946 | printk(CARDNAME ": IO %x: Unrecognized revision register:" | ||
947 | " %x, Contact author. \n", ioaddr, revision_register ); | ||
948 | |||
949 | retval = -ENODEV; | ||
950 | goto err_out; | ||
951 | } | ||
952 | |||
953 | /* at this point I'll assume that the chip is an SMC9xxx. | ||
954 | It might be prudent to check a listing of MAC addresses | ||
955 | against the hardware address, or do some other tests. */ | ||
956 | |||
957 | if (version_printed++ == 0) | ||
958 | printk("%s", version); | ||
959 | |||
960 | /* fill in some of the fields */ | ||
961 | dev->base_addr = ioaddr; | ||
962 | |||
963 | /* | ||
964 | . Get the MAC address ( bank 1, regs 4 - 9 ) | ||
965 | */ | ||
966 | SMC_SELECT_BANK( 1 ); | ||
967 | for ( i = 0; i < 6; i += 2 ) { | ||
968 | word address; | ||
969 | |||
970 | address = inw( ioaddr + ADDR0 + i ); | ||
971 | dev->dev_addr[ i + 1] = address >> 8; | ||
972 | dev->dev_addr[ i ] = address & 0xFF; | ||
973 | } | ||
974 | |||
975 | /* get the memory information */ | ||
976 | |||
977 | SMC_SELECT_BANK( 0 ); | ||
978 | memory_info_register = inw( ioaddr + MIR ); | ||
979 | memory_cfg_register = inw( ioaddr + MCR ); | ||
980 | memory = ( memory_cfg_register >> 9 ) & 0x7; /* multiplier */ | ||
981 | memory *= 256 * ( memory_info_register & 0xFF ); | ||
982 | |||
983 | /* | ||
984 | Now, I want to find out more about the chip. This is sort of | ||
985 | redundant, but it's cleaner to have it in both, rather than having | ||
986 | one VERY long probe procedure. | ||
987 | */ | ||
988 | SMC_SELECT_BANK(3); | ||
989 | revision_register = inw( ioaddr + REVISION ); | ||
990 | version_string = chip_ids[ ( revision_register >> 4 ) & 0xF ]; | ||
991 | if ( !version_string ) { | ||
992 | /* I shouldn't get here because this call was done before.... */ | ||
993 | retval = -ENODEV; | ||
994 | goto err_out; | ||
995 | } | ||
996 | |||
997 | /* is it using AUI or 10BaseT ? */ | ||
998 | if ( dev->if_port == 0 ) { | ||
999 | SMC_SELECT_BANK(1); | ||
1000 | configuration_register = inw( ioaddr + CONFIG ); | ||
1001 | if ( configuration_register & CFG_AUI_SELECT ) | ||
1002 | dev->if_port = 2; | ||
1003 | else | ||
1004 | dev->if_port = 1; | ||
1005 | } | ||
1006 | if_string = interfaces[ dev->if_port - 1 ]; | ||
1007 | |||
1008 | /* now, reset the chip, and put it into a known state */ | ||
1009 | smc_reset( ioaddr ); | ||
1010 | |||
1011 | /* | ||
1012 | . If dev->irq is 0, then the device has to be banged on to see | ||
1013 | . what the IRQ is. | ||
1014 | . | ||
1015 | . This banging doesn't always detect the IRQ, for unknown reasons. | ||
1016 | . a workaround is to reset the chip and try again. | ||
1017 | . | ||
1018 | . Interestingly, the DOS packet driver *SETS* the IRQ on the card to | ||
1019 | . be what is requested on the command line. I don't do that, mostly | ||
1020 | . because the card that I have uses a non-standard method of accessing | ||
1021 | . the IRQs, and because this _should_ work in most configurations. | ||
1022 | . | ||
1023 | . Specifying an IRQ is done with the assumption that the user knows | ||
1024 | . what (s)he is doing. No checking is done!!!! | ||
1025 | . | ||
1026 | */ | ||
1027 | if ( dev->irq < 2 ) { | ||
1028 | int trials; | ||
1029 | |||
1030 | trials = 3; | ||
1031 | while ( trials-- ) { | ||
1032 | dev->irq = smc_findirq( ioaddr ); | ||
1033 | if ( dev->irq ) | ||
1034 | break; | ||
1035 | /* kick the card and try again */ | ||
1036 | smc_reset( ioaddr ); | ||
1037 | } | ||
1038 | } | ||
1039 | if (dev->irq == 0 ) { | ||
1040 | printk(CARDNAME": Couldn't autodetect your IRQ. Use irq=xx.\n"); | ||
1041 | retval = -ENODEV; | ||
1042 | goto err_out; | ||
1043 | } | ||
1044 | |||
1045 | /* now, print out the card info, in a short format.. */ | ||
1046 | |||
1047 | printk("%s: %s(r:%d) at %#3x IRQ:%d INTF:%s MEM:%db ", dev->name, | ||
1048 | version_string, revision_register & 0xF, ioaddr, dev->irq, | ||
1049 | if_string, memory ); | ||
1050 | /* | ||
1051 | . Print the Ethernet address | ||
1052 | */ | ||
1053 | printk("ADDR: "); | ||
1054 | for (i = 0; i < 5; i++) | ||
1055 | printk("%2.2x:", dev->dev_addr[i] ); | ||
1056 | printk("%2.2x \n", dev->dev_addr[5] ); | ||
1057 | |||
1058 | /* set the private data to zero by default */ | ||
1059 | memset(dev->priv, 0, sizeof(struct smc_local)); | ||
1060 | |||
1061 | /* Grab the IRQ */ | ||
1062 | retval = request_irq(dev->irq, &smc_interrupt, 0, DRV_NAME, dev); | ||
1063 | if (retval) { | ||
1064 | printk("%s: unable to get IRQ %d (irqval=%d).\n", DRV_NAME, | ||
1065 | dev->irq, retval); | ||
1066 | goto err_out; | ||
1067 | } | ||
1068 | |||
1069 | dev->open = smc_open; | ||
1070 | dev->stop = smc_close; | ||
1071 | dev->hard_start_xmit = smc_wait_to_send_packet; | ||
1072 | dev->tx_timeout = smc_timeout; | ||
1073 | dev->watchdog_timeo = HZ/20; | ||
1074 | dev->get_stats = smc_query_statistics; | ||
1075 | dev->set_multicast_list = smc_set_multicast_list; | ||
1076 | |||
1077 | return 0; | ||
1078 | |||
1079 | err_out: | ||
1080 | release_region(ioaddr, SMC_IO_EXTENT); | ||
1081 | return retval; | ||
1082 | } | ||
1083 | |||
1084 | #if SMC_DEBUG > 2 | ||
1085 | static void print_packet( byte * buf, int length ) | ||
1086 | { | ||
1087 | #if 0 | ||
1088 | int i; | ||
1089 | int remainder; | ||
1090 | int lines; | ||
1091 | |||
1092 | printk("Packet of length %d \n", length ); | ||
1093 | lines = length / 16; | ||
1094 | remainder = length % 16; | ||
1095 | |||
1096 | for ( i = 0; i < lines ; i ++ ) { | ||
1097 | int cur; | ||
1098 | |||
1099 | for ( cur = 0; cur < 8; cur ++ ) { | ||
1100 | byte a, b; | ||
1101 | |||
1102 | a = *(buf ++ ); | ||
1103 | b = *(buf ++ ); | ||
1104 | printk("%02x%02x ", a, b ); | ||
1105 | } | ||
1106 | printk("\n"); | ||
1107 | } | ||
1108 | for ( i = 0; i < remainder/2 ; i++ ) { | ||
1109 | byte a, b; | ||
1110 | |||
1111 | a = *(buf ++ ); | ||
1112 | b = *(buf ++ ); | ||
1113 | printk("%02x%02x ", a, b ); | ||
1114 | } | ||
1115 | printk("\n"); | ||
1116 | #endif | ||
1117 | } | ||
1118 | #endif | ||
1119 | |||
1120 | |||
1121 | /* | ||
1122 | * Open and Initialize the board | ||
1123 | * | ||
1124 | * Set up everything, reset the card, etc .. | ||
1125 | * | ||
1126 | */ | ||
1127 | static int smc_open(struct net_device *dev) | ||
1128 | { | ||
1129 | int ioaddr = dev->base_addr; | ||
1130 | |||
1131 | int i; /* used to set hw ethernet address */ | ||
1132 | |||
1133 | /* clear out all the junk that was put here before... */ | ||
1134 | memset(dev->priv, 0, sizeof(struct smc_local)); | ||
1135 | |||
1136 | /* reset the hardware */ | ||
1137 | |||
1138 | smc_reset( ioaddr ); | ||
1139 | smc_enable( ioaddr ); | ||
1140 | |||
1141 | /* Select which interface to use */ | ||
1142 | |||
1143 | SMC_SELECT_BANK( 1 ); | ||
1144 | if ( dev->if_port == 1 ) { | ||
1145 | outw( inw( ioaddr + CONFIG ) & ~CFG_AUI_SELECT, | ||
1146 | ioaddr + CONFIG ); | ||
1147 | } | ||
1148 | else if ( dev->if_port == 2 ) { | ||
1149 | outw( inw( ioaddr + CONFIG ) | CFG_AUI_SELECT, | ||
1150 | ioaddr + CONFIG ); | ||
1151 | } | ||
1152 | |||
1153 | /* | ||
1154 | According to Becker, I have to set the hardware address | ||
1155 | at this point, because the (l)user can set it with an | ||
1156 | ioctl. Easily done... | ||
1157 | */ | ||
1158 | SMC_SELECT_BANK( 1 ); | ||
1159 | for ( i = 0; i < 6; i += 2 ) { | ||
1160 | word address; | ||
1161 | |||
1162 | address = dev->dev_addr[ i + 1 ] << 8 ; | ||
1163 | address |= dev->dev_addr[ i ]; | ||
1164 | outw( address, ioaddr + ADDR0 + i ); | ||
1165 | } | ||
1166 | |||
1167 | netif_start_queue(dev); | ||
1168 | return 0; | ||
1169 | } | ||
1170 | |||
1171 | /*-------------------------------------------------------- | ||
1172 | . Called by the kernel to send a packet out into the void | ||
1173 | . of the net. This routine is largely based on | ||
1174 | . skeleton.c, from Becker. | ||
1175 | .-------------------------------------------------------- | ||
1176 | */ | ||
1177 | |||
1178 | static void smc_timeout(struct net_device *dev) | ||
1179 | { | ||
1180 | /* If we get here, some higher level has decided we are broken. | ||
1181 | There should really be a "kick me" function call instead. */ | ||
1182 | printk(KERN_WARNING CARDNAME": transmit timed out, %s?\n", | ||
1183 | tx_done(dev) ? "IRQ conflict" : | ||
1184 | "network cable problem"); | ||
1185 | /* "kick" the adaptor */ | ||
1186 | smc_reset( dev->base_addr ); | ||
1187 | smc_enable( dev->base_addr ); | ||
1188 | dev->trans_start = jiffies; | ||
1189 | /* clear anything saved */ | ||
1190 | ((struct smc_local *)dev->priv)->saved_skb = NULL; | ||
1191 | netif_wake_queue(dev); | ||
1192 | } | ||
1193 | |||
1194 | /*------------------------------------------------------------- | ||
1195 | . | ||
1196 | . smc_rcv - receive a packet from the card | ||
1197 | . | ||
1198 | . There is ( at least ) a packet waiting to be read from | ||
1199 | . chip-memory. | ||
1200 | . | ||
1201 | . o Read the status | ||
1202 | . o If an error, record it | ||
1203 | . o otherwise, read in the packet | ||
1204 | -------------------------------------------------------------- | ||
1205 | */ | ||
1206 | static void smc_rcv(struct net_device *dev) | ||
1207 | { | ||
1208 | struct smc_local *lp = netdev_priv(dev); | ||
1209 | int ioaddr = dev->base_addr; | ||
1210 | int packet_number; | ||
1211 | word status; | ||
1212 | word packet_length; | ||
1213 | |||
1214 | /* assume bank 2 */ | ||
1215 | |||
1216 | packet_number = inw( ioaddr + FIFO_PORTS ); | ||
1217 | |||
1218 | if ( packet_number & FP_RXEMPTY ) { | ||
1219 | /* we got called , but nothing was on the FIFO */ | ||
1220 | PRINTK((CARDNAME ": WARNING: smc_rcv with nothing on FIFO. \n")); | ||
1221 | /* don't need to restore anything */ | ||
1222 | return; | ||
1223 | } | ||
1224 | |||
1225 | /* start reading from the start of the packet */ | ||
1226 | outw( PTR_READ | PTR_RCV | PTR_AUTOINC, ioaddr + POINTER ); | ||
1227 | |||
1228 | /* First two words are status and packet_length */ | ||
1229 | status = inw( ioaddr + DATA_1 ); | ||
1230 | packet_length = inw( ioaddr + DATA_1 ); | ||
1231 | |||
1232 | packet_length &= 0x07ff; /* mask off top bits */ | ||
1233 | |||
1234 | PRINTK2(("RCV: STATUS %4x LENGTH %4x\n", status, packet_length )); | ||
1235 | /* | ||
1236 | . the packet length contains 3 extra words : | ||
1237 | . status, length, and an extra word with an odd byte . | ||
1238 | */ | ||
1239 | packet_length -= 6; | ||
1240 | |||
1241 | if ( !(status & RS_ERRORS ) ){ | ||
1242 | /* do stuff to make a new packet */ | ||
1243 | struct sk_buff * skb; | ||
1244 | byte * data; | ||
1245 | |||
1246 | /* read one extra byte */ | ||
1247 | if ( status & RS_ODDFRAME ) | ||
1248 | packet_length++; | ||
1249 | |||
1250 | /* set multicast stats */ | ||
1251 | if ( status & RS_MULTICAST ) | ||
1252 | lp->stats.multicast++; | ||
1253 | |||
1254 | skb = dev_alloc_skb( packet_length + 5); | ||
1255 | |||
1256 | if ( skb == NULL ) { | ||
1257 | printk(KERN_NOTICE CARDNAME ": Low memory, packet dropped.\n"); | ||
1258 | lp->stats.rx_dropped++; | ||
1259 | goto done; | ||
1260 | } | ||
1261 | |||
1262 | /* | ||
1263 | ! This should work without alignment, but it could be | ||
1264 | ! in the worse case | ||
1265 | */ | ||
1266 | |||
1267 | skb_reserve( skb, 2 ); /* 16 bit alignment */ | ||
1268 | |||
1269 | skb->dev = dev; | ||
1270 | data = skb_put( skb, packet_length); | ||
1271 | |||
1272 | #ifdef USE_32_BIT | ||
1273 | /* QUESTION: Like in the TX routine, do I want | ||
1274 | to send the DWORDs or the bytes first, or some | ||
1275 | mixture. A mixture might improve already slow PIO | ||
1276 | performance */ | ||
1277 | PRINTK3((" Reading %d dwords (and %d bytes) \n", | ||
1278 | packet_length >> 2, packet_length & 3 )); | ||
1279 | insl(ioaddr + DATA_1 , data, packet_length >> 2 ); | ||
1280 | /* read the left over bytes */ | ||
1281 | insb( ioaddr + DATA_1, data + (packet_length & 0xFFFFFC), | ||
1282 | packet_length & 0x3 ); | ||
1283 | #else | ||
1284 | PRINTK3((" Reading %d words and %d byte(s) \n", | ||
1285 | (packet_length >> 1 ), packet_length & 1 )); | ||
1286 | insw(ioaddr + DATA_1 , data, packet_length >> 1); | ||
1287 | if ( packet_length & 1 ) { | ||
1288 | data += packet_length & ~1; | ||
1289 | *(data++) = inb( ioaddr + DATA_1 ); | ||
1290 | } | ||
1291 | #endif | ||
1292 | #if SMC_DEBUG > 2 | ||
1293 | print_packet( data, packet_length ); | ||
1294 | #endif | ||
1295 | |||
1296 | skb->protocol = eth_type_trans(skb, dev ); | ||
1297 | netif_rx(skb); | ||
1298 | dev->last_rx = jiffies; | ||
1299 | lp->stats.rx_packets++; | ||
1300 | lp->stats.rx_bytes += packet_length; | ||
1301 | } else { | ||
1302 | /* error ... */ | ||
1303 | lp->stats.rx_errors++; | ||
1304 | |||
1305 | if ( status & RS_ALGNERR ) lp->stats.rx_frame_errors++; | ||
1306 | if ( status & (RS_TOOSHORT | RS_TOOLONG ) ) | ||
1307 | lp->stats.rx_length_errors++; | ||
1308 | if ( status & RS_BADCRC) lp->stats.rx_crc_errors++; | ||
1309 | } | ||
1310 | |||
1311 | done: | ||
1312 | /* error or good, tell the card to get rid of this packet */ | ||
1313 | outw( MC_RELEASE, ioaddr + MMU_CMD ); | ||
1314 | } | ||
1315 | |||
1316 | |||
1317 | /************************************************************************* | ||
1318 | . smc_tx | ||
1319 | . | ||
1320 | . Purpose: Handle a transmit error message. This will only be called | ||
1321 | . when an error, because of the AUTO_RELEASE mode. | ||
1322 | . | ||
1323 | . Algorithm: | ||
1324 | . Save pointer and packet no | ||
1325 | . Get the packet no from the top of the queue | ||
1326 | . check if it's valid ( if not, is this an error??? ) | ||
1327 | . read the status word | ||
1328 | . record the error | ||
1329 | . ( resend? Not really, since we don't want old packets around ) | ||
1330 | . Restore saved values | ||
1331 | ************************************************************************/ | ||
1332 | static void smc_tx( struct net_device * dev ) | ||
1333 | { | ||
1334 | int ioaddr = dev->base_addr; | ||
1335 | struct smc_local *lp = netdev_priv(dev); | ||
1336 | byte saved_packet; | ||
1337 | byte packet_no; | ||
1338 | word tx_status; | ||
1339 | |||
1340 | |||
1341 | /* assume bank 2 */ | ||
1342 | |||
1343 | saved_packet = inb( ioaddr + PNR_ARR ); | ||
1344 | packet_no = inw( ioaddr + FIFO_PORTS ); | ||
1345 | packet_no &= 0x7F; | ||
1346 | |||
1347 | /* select this as the packet to read from */ | ||
1348 | outb( packet_no, ioaddr + PNR_ARR ); | ||
1349 | |||
1350 | /* read the first word from this packet */ | ||
1351 | outw( PTR_AUTOINC | PTR_READ, ioaddr + POINTER ); | ||
1352 | |||
1353 | tx_status = inw( ioaddr + DATA_1 ); | ||
1354 | PRINTK3((CARDNAME": TX DONE STATUS: %4x \n", tx_status )); | ||
1355 | |||
1356 | lp->stats.tx_errors++; | ||
1357 | if ( tx_status & TS_LOSTCAR ) lp->stats.tx_carrier_errors++; | ||
1358 | if ( tx_status & TS_LATCOL ) { | ||
1359 | printk(KERN_DEBUG CARDNAME | ||
1360 | ": Late collision occurred on last xmit.\n"); | ||
1361 | lp->stats.tx_window_errors++; | ||
1362 | } | ||
1363 | #if 0 | ||
1364 | if ( tx_status & TS_16COL ) { ... } | ||
1365 | #endif | ||
1366 | |||
1367 | if ( tx_status & TS_SUCCESS ) { | ||
1368 | printk(CARDNAME": Successful packet caused interrupt \n"); | ||
1369 | } | ||
1370 | /* re-enable transmit */ | ||
1371 | SMC_SELECT_BANK( 0 ); | ||
1372 | outw( inw( ioaddr + TCR ) | TCR_ENABLE, ioaddr + TCR ); | ||
1373 | |||
1374 | /* kill the packet */ | ||
1375 | SMC_SELECT_BANK( 2 ); | ||
1376 | outw( MC_FREEPKT, ioaddr + MMU_CMD ); | ||
1377 | |||
1378 | /* one less packet waiting for me */ | ||
1379 | lp->packets_waiting--; | ||
1380 | |||
1381 | outb( saved_packet, ioaddr + PNR_ARR ); | ||
1382 | return; | ||
1383 | } | ||
1384 | |||
1385 | /*-------------------------------------------------------------------- | ||
1386 | . | ||
1387 | . This is the main routine of the driver, to handle the device when | ||
1388 | . it needs some attention. | ||
1389 | . | ||
1390 | . So: | ||
1391 | . first, save state of the chipset | ||
1392 | . branch off into routines to handle each case, and acknowledge | ||
1393 | . each to the interrupt register | ||
1394 | . and finally restore state. | ||
1395 | . | ||
1396 | ---------------------------------------------------------------------*/ | ||
1397 | |||
1398 | static irqreturn_t smc_interrupt(int irq, void * dev_id, struct pt_regs * regs) | ||
1399 | { | ||
1400 | struct net_device *dev = dev_id; | ||
1401 | int ioaddr = dev->base_addr; | ||
1402 | struct smc_local *lp = netdev_priv(dev); | ||
1403 | |||
1404 | byte status; | ||
1405 | word card_stats; | ||
1406 | byte mask; | ||
1407 | int timeout; | ||
1408 | /* state registers */ | ||
1409 | word saved_bank; | ||
1410 | word saved_pointer; | ||
1411 | int handled = 0; | ||
1412 | |||
1413 | |||
1414 | PRINTK3((CARDNAME": SMC interrupt started \n")); | ||
1415 | |||
1416 | saved_bank = inw( ioaddr + BANK_SELECT ); | ||
1417 | |||
1418 | SMC_SELECT_BANK(2); | ||
1419 | saved_pointer = inw( ioaddr + POINTER ); | ||
1420 | |||
1421 | mask = inb( ioaddr + INT_MASK ); | ||
1422 | /* clear all interrupts */ | ||
1423 | outb( 0, ioaddr + INT_MASK ); | ||
1424 | |||
1425 | |||
1426 | /* set a timeout value, so I don't stay here forever */ | ||
1427 | timeout = 4; | ||
1428 | |||
1429 | PRINTK2((KERN_WARNING CARDNAME ": MASK IS %x \n", mask )); | ||
1430 | do { | ||
1431 | /* read the status flag, and mask it */ | ||
1432 | status = inb( ioaddr + INTERRUPT ) & mask; | ||
1433 | if (!status ) | ||
1434 | break; | ||
1435 | |||
1436 | handled = 1; | ||
1437 | |||
1438 | PRINTK3((KERN_WARNING CARDNAME | ||
1439 | ": Handling interrupt status %x \n", status )); | ||
1440 | |||
1441 | if (status & IM_RCV_INT) { | ||
1442 | /* Got a packet(s). */ | ||
1443 | PRINTK2((KERN_WARNING CARDNAME | ||
1444 | ": Receive Interrupt\n")); | ||
1445 | smc_rcv(dev); | ||
1446 | } else if (status & IM_TX_INT ) { | ||
1447 | PRINTK2((KERN_WARNING CARDNAME | ||
1448 | ": TX ERROR handled\n")); | ||
1449 | smc_tx(dev); | ||
1450 | outb(IM_TX_INT, ioaddr + INTERRUPT ); | ||
1451 | } else if (status & IM_TX_EMPTY_INT ) { | ||
1452 | /* update stats */ | ||
1453 | SMC_SELECT_BANK( 0 ); | ||
1454 | card_stats = inw( ioaddr + COUNTER ); | ||
1455 | /* single collisions */ | ||
1456 | lp->stats.collisions += card_stats & 0xF; | ||
1457 | card_stats >>= 4; | ||
1458 | /* multiple collisions */ | ||
1459 | lp->stats.collisions += card_stats & 0xF; | ||
1460 | |||
1461 | /* these are for when linux supports these statistics */ | ||
1462 | |||
1463 | SMC_SELECT_BANK( 2 ); | ||
1464 | PRINTK2((KERN_WARNING CARDNAME | ||
1465 | ": TX_BUFFER_EMPTY handled\n")); | ||
1466 | outb( IM_TX_EMPTY_INT, ioaddr + INTERRUPT ); | ||
1467 | mask &= ~IM_TX_EMPTY_INT; | ||
1468 | lp->stats.tx_packets += lp->packets_waiting; | ||
1469 | lp->packets_waiting = 0; | ||
1470 | |||
1471 | } else if (status & IM_ALLOC_INT ) { | ||
1472 | PRINTK2((KERN_DEBUG CARDNAME | ||
1473 | ": Allocation interrupt \n")); | ||
1474 | /* clear this interrupt so it doesn't happen again */ | ||
1475 | mask &= ~IM_ALLOC_INT; | ||
1476 | |||
1477 | smc_hardware_send_packet( dev ); | ||
1478 | |||
1479 | /* enable xmit interrupts based on this */ | ||
1480 | mask |= ( IM_TX_EMPTY_INT | IM_TX_INT ); | ||
1481 | |||
1482 | /* and let the card send more packets to me */ | ||
1483 | netif_wake_queue(dev); | ||
1484 | |||
1485 | PRINTK2((CARDNAME": Handoff done successfully.\n")); | ||
1486 | } else if (status & IM_RX_OVRN_INT ) { | ||
1487 | lp->stats.rx_errors++; | ||
1488 | lp->stats.rx_fifo_errors++; | ||
1489 | outb( IM_RX_OVRN_INT, ioaddr + INTERRUPT ); | ||
1490 | } else if (status & IM_EPH_INT ) { | ||
1491 | PRINTK((CARDNAME ": UNSUPPORTED: EPH INTERRUPT \n")); | ||
1492 | } else if (status & IM_ERCV_INT ) { | ||
1493 | PRINTK((CARDNAME ": UNSUPPORTED: ERCV INTERRUPT \n")); | ||
1494 | outb( IM_ERCV_INT, ioaddr + INTERRUPT ); | ||
1495 | } | ||
1496 | } while ( timeout -- ); | ||
1497 | |||
1498 | |||
1499 | /* restore state register */ | ||
1500 | SMC_SELECT_BANK( 2 ); | ||
1501 | outb( mask, ioaddr + INT_MASK ); | ||
1502 | |||
1503 | PRINTK3(( KERN_WARNING CARDNAME ": MASK is now %x \n", mask )); | ||
1504 | outw( saved_pointer, ioaddr + POINTER ); | ||
1505 | |||
1506 | SMC_SELECT_BANK( saved_bank ); | ||
1507 | |||
1508 | PRINTK3((CARDNAME ": Interrupt done\n")); | ||
1509 | return IRQ_RETVAL(handled); | ||
1510 | } | ||
1511 | |||
1512 | |||
1513 | /*---------------------------------------------------- | ||
1514 | . smc_close | ||
1515 | . | ||
1516 | . this makes the board clean up everything that it can | ||
1517 | . and not talk to the outside world. Caused by | ||
1518 | . an 'ifconfig ethX down' | ||
1519 | . | ||
1520 | -----------------------------------------------------*/ | ||
1521 | static int smc_close(struct net_device *dev) | ||
1522 | { | ||
1523 | netif_stop_queue(dev); | ||
1524 | /* clear everything */ | ||
1525 | smc_shutdown( dev->base_addr ); | ||
1526 | |||
1527 | /* Update the statistics here. */ | ||
1528 | return 0; | ||
1529 | } | ||
1530 | |||
1531 | /*------------------------------------------------------------ | ||
1532 | . Get the current statistics. | ||
1533 | . This may be called with the card open or closed. | ||
1534 | .-------------------------------------------------------------*/ | ||
1535 | static struct net_device_stats* smc_query_statistics(struct net_device *dev) { | ||
1536 | struct smc_local *lp = netdev_priv(dev); | ||
1537 | |||
1538 | return &lp->stats; | ||
1539 | } | ||
1540 | |||
1541 | /*----------------------------------------------------------- | ||
1542 | . smc_set_multicast_list | ||
1543 | . | ||
1544 | . This routine will, depending on the values passed to it, | ||
1545 | . either make it accept multicast packets, go into | ||
1546 | . promiscuous mode ( for TCPDUMP and cousins ) or accept | ||
1547 | . a select set of multicast packets | ||
1548 | */ | ||
1549 | static void smc_set_multicast_list(struct net_device *dev) | ||
1550 | { | ||
1551 | short ioaddr = dev->base_addr; | ||
1552 | |||
1553 | SMC_SELECT_BANK(0); | ||
1554 | if ( dev->flags & IFF_PROMISC ) | ||
1555 | outw( inw(ioaddr + RCR ) | RCR_PROMISC, ioaddr + RCR ); | ||
1556 | |||
1557 | /* BUG? I never disable promiscuous mode if multicasting was turned on. | ||
1558 | Now, I turn off promiscuous mode, but I don't do anything to multicasting | ||
1559 | when promiscuous mode is turned on. | ||
1560 | */ | ||
1561 | |||
1562 | /* Here, I am setting this to accept all multicast packets. | ||
1563 | I don't need to zero the multicast table, because the flag is | ||
1564 | checked before the table is | ||
1565 | */ | ||
1566 | else if (dev->flags & IFF_ALLMULTI) | ||
1567 | outw( inw(ioaddr + RCR ) | RCR_ALMUL, ioaddr + RCR ); | ||
1568 | |||
1569 | /* We just get all multicast packets even if we only want them | ||
1570 | . from one source. This will be changed at some future | ||
1571 | . point. */ | ||
1572 | else if (dev->mc_count ) { | ||
1573 | /* support hardware multicasting */ | ||
1574 | |||
1575 | /* be sure I get rid of flags I might have set */ | ||
1576 | outw( inw( ioaddr + RCR ) & ~(RCR_PROMISC | RCR_ALMUL), | ||
1577 | ioaddr + RCR ); | ||
1578 | /* NOTE: this has to set the bank, so make sure it is the | ||
1579 | last thing called. The bank is set to zero at the top */ | ||
1580 | smc_setmulticast( ioaddr, dev->mc_count, dev->mc_list ); | ||
1581 | } | ||
1582 | else { | ||
1583 | outw( inw( ioaddr + RCR ) & ~(RCR_PROMISC | RCR_ALMUL), | ||
1584 | ioaddr + RCR ); | ||
1585 | |||
1586 | /* | ||
1587 | since I'm disabling all multicast entirely, I need to | ||
1588 | clear the multicast list | ||
1589 | */ | ||
1590 | SMC_SELECT_BANK( 3 ); | ||
1591 | outw( 0, ioaddr + MULTICAST1 ); | ||
1592 | outw( 0, ioaddr + MULTICAST2 ); | ||
1593 | outw( 0, ioaddr + MULTICAST3 ); | ||
1594 | outw( 0, ioaddr + MULTICAST4 ); | ||
1595 | } | ||
1596 | } | ||
1597 | |||
1598 | #ifdef MODULE | ||
1599 | |||
1600 | static struct net_device *devSMC9194; | ||
1601 | MODULE_LICENSE("GPL"); | ||
1602 | |||
1603 | module_param(io, int, 0); | ||
1604 | module_param(irq, int, 0); | ||
1605 | module_param(ifport, int, 0); | ||
1606 | MODULE_PARM_DESC(io, "SMC 99194 I/O base address"); | ||
1607 | MODULE_PARM_DESC(irq, "SMC 99194 IRQ number"); | ||
1608 | MODULE_PARM_DESC(ifport, "SMC 99194 interface port (0-default, 1-TP, 2-AUI)"); | ||
1609 | |||
1610 | int init_module(void) | ||
1611 | { | ||
1612 | if (io == 0) | ||
1613 | printk(KERN_WARNING | ||
1614 | CARDNAME": You shouldn't use auto-probing with insmod!\n" ); | ||
1615 | |||
1616 | /* copy the parameters from insmod into the device structure */ | ||
1617 | devSMC9194 = smc_init(-1); | ||
1618 | if (IS_ERR(devSMC9194)) | ||
1619 | return PTR_ERR(devSMC9194); | ||
1620 | return 0; | ||
1621 | } | ||
1622 | |||
1623 | void cleanup_module(void) | ||
1624 | { | ||
1625 | unregister_netdev(devSMC9194); | ||
1626 | free_irq(devSMC9194->irq, devSMC9194); | ||
1627 | release_region(devSMC9194->base_addr, SMC_IO_EXTENT); | ||
1628 | free_netdev(devSMC9194); | ||
1629 | } | ||
1630 | |||
1631 | #endif /* MODULE */ | ||