iPXE
smc9000.c
Go to the documentation of this file.
1#ifdef ALLMULTI
2#error multicast support is not yet implemented
3#endif
4 /*------------------------------------------------------------------------
5 * smc9000.c
6 * This is a Etherboot driver for SMC's 9000 series of Ethernet cards.
7 *
8 * Copyright (C) 1998 Daniel Engström
9 * Based on the Linux SMC9000 driver, smc9194.c by Eric Stahlman
10 * Copyright (C) 1996 by Erik Stahlman <eric@vt.edu>
11 *
12 * This software may be used and distributed according to the terms
13 * of the GNU Public License, incorporated herein by reference.
14 *
15 * "Features" of the SMC chip:
16 * 4608 byte packet memory. ( for the 91C92/4. Others have more )
17 * EEPROM for configuration
18 * AUI/TP selection
19 *
20 * Authors
21 * Erik Stahlman <erik@vt.edu>
22 * Daniel Engström <daniel.engstrom@riksnett.no>
23 *
24 * History
25 * 98-09-25 Daniel Engström Etherboot driver crated from Eric's
26 * Linux driver.
27 *
28 *---------------------------------------------------------------------------*/
29
30FILE_LICENCE ( GPL_ANY );
31
32#define LINUX_OUT_MACROS 1
33#define SMC9000_DEBUG 0
34
35#if SMC9000_DEBUG > 1
36#define PRINTK2 printf
37#else
38#define PRINTK2(args...)
39#endif
40
41#include <ipxe/ethernet.h>
42#include <errno.h>
43#include "etherboot.h"
44#include "nic.h"
45#include <ipxe/isa.h>
46#include "smc9000.h"
47
48# define _outb outb
49# define _outw outw
50
51static const char smc9000_version[] = "Version 0.99 98-09-30";
52static const char *interfaces[ 2 ] = { "TP", "AUI" };
53static const char *chip_ids[ 15 ] = {
54 NULL, NULL, NULL,
55 /* 3 */ "SMC91C90/91C92",
56 /* 4 */ "SMC91C94",
57 /* 5 */ "SMC91C95",
58 NULL,
59 /* 7 */ "SMC91C100",
60 /* 8 */ "SMC91C100FD",
61 /* 9 */ "SMC91C11xFD",
62 NULL, NULL,
63 NULL, NULL, NULL
64};
65static const char smc91c96_id[] = "SMC91C96";
66
67/*------------------------------------------------------------
68 . Reads a register from the MII Management serial interface
69 .-------------------------------------------------------------*/
70static word smc_read_phy_register(int ioaddr, byte phyaddr, byte phyreg)
71{
72 int oldBank;
73 unsigned int i;
74 byte mask;
75 word mii_reg;
76 byte bits[64];
77 int clk_idx = 0;
78 int input_idx;
79 word phydata;
80
81 // 32 consecutive ones on MDO to establish sync
82 for (i = 0; i < 32; ++i)
83 bits[clk_idx++] = MII_MDOE | MII_MDO;
84
85 // Start code <01>
86 bits[clk_idx++] = MII_MDOE;
87 bits[clk_idx++] = MII_MDOE | MII_MDO;
88
89 // Read command <10>
90 bits[clk_idx++] = MII_MDOE | MII_MDO;
91 bits[clk_idx++] = MII_MDOE;
92
93 // Output the PHY address, msb first
94 mask = (byte)0x10;
95 for (i = 0; i < 5; ++i)
96 {
97 if (phyaddr & mask)
98 bits[clk_idx++] = MII_MDOE | MII_MDO;
99 else
100 bits[clk_idx++] = MII_MDOE;
101
102 // Shift to next lowest bit
103 mask >>= 1;
104 }
105
106 // Output the phy register number, msb first
107 mask = (byte)0x10;
108 for (i = 0; i < 5; ++i)
109 {
110 if (phyreg & mask)
111 bits[clk_idx++] = MII_MDOE | MII_MDO;
112 else
113 bits[clk_idx++] = MII_MDOE;
114
115 // Shift to next lowest bit
116 mask >>= 1;
117 }
118
119 // Tristate and turnaround (2 bit times)
120 bits[clk_idx++] = 0;
121 //bits[clk_idx++] = 0;
122
123 // Input starts at this bit time
124 input_idx = clk_idx;
125
126 // Will input 16 bits
127 for (i = 0; i < 16; ++i)
128 bits[clk_idx++] = 0;
129
130 // Final clock bit
131 bits[clk_idx++] = 0;
132
133 // Save the current bank
134 oldBank = inw( ioaddr+BANK_SELECT );
135
136 // Select bank 3
138
139 // Get the current MII register value
140 mii_reg = inw( ioaddr+MII_REG );
141
142 // Turn off all MII Interface bits
143 mii_reg &= ~(MII_MDOE|MII_MCLK|MII_MDI|MII_MDO);
144
145 // Clock all 64 cycles
146 for (i = 0; i < sizeof(bits); ++i)
147 {
148 // Clock Low - output data
149 outw( mii_reg | bits[i], ioaddr+MII_REG );
150 udelay(50);
151
152
153 // Clock Hi - input data
154 outw( mii_reg | bits[i] | MII_MCLK, ioaddr+MII_REG );
155 udelay(50);
156 bits[i] |= inw( ioaddr+MII_REG ) & MII_MDI;
157 }
158
159 // Return to idle state
160 // Set clock to low, data to low, and output tristated
161 outw( mii_reg, ioaddr+MII_REG );
162 udelay(50);
163
164 // Restore original bank select
165 SMC_SELECT_BANK(ioaddr, oldBank);
166
167 // Recover input data
168 phydata = 0;
169 for (i = 0; i < 16; ++i)
170 {
171 phydata <<= 1;
172
173 if (bits[input_idx++] & MII_MDI)
174 phydata |= 0x0001;
175 }
176
177#if (SMC_DEBUG > 2 )
178 printf("smc_read_phy_register(): phyaddr=%x,phyreg=%x,phydata=%x\n",
179 phyaddr, phyreg, phydata);
180#endif
181
182 return(phydata);
183}
184
185
186/*------------------------------------------------------------
187 . Writes a register to the MII Management serial interface
188 .-------------------------------------------------------------*/
190 byte phyaddr, byte phyreg, word phydata)
191{
192 int oldBank;
193 unsigned int i;
194 word mask;
195 word mii_reg;
196 byte bits[65];
197 int clk_idx = 0;
198
199 // 32 consecutive ones on MDO to establish sync
200 for (i = 0; i < 32; ++i)
201 bits[clk_idx++] = MII_MDOE | MII_MDO;
202
203 // Start code <01>
204 bits[clk_idx++] = MII_MDOE;
205 bits[clk_idx++] = MII_MDOE | MII_MDO;
206
207 // Write command <01>
208 bits[clk_idx++] = MII_MDOE;
209 bits[clk_idx++] = MII_MDOE | MII_MDO;
210
211 // Output the PHY address, msb first
212 mask = (byte)0x10;
213 for (i = 0; i < 5; ++i)
214 {
215 if (phyaddr & mask)
216 bits[clk_idx++] = MII_MDOE | MII_MDO;
217 else
218 bits[clk_idx++] = MII_MDOE;
219
220 // Shift to next lowest bit
221 mask >>= 1;
222 }
223
224 // Output the phy register number, msb first
225 mask = (byte)0x10;
226 for (i = 0; i < 5; ++i)
227 {
228 if (phyreg & mask)
229 bits[clk_idx++] = MII_MDOE | MII_MDO;
230 else
231 bits[clk_idx++] = MII_MDOE;
232
233 // Shift to next lowest bit
234 mask >>= 1;
235 }
236
237 // Tristate and turnaround (2 bit times)
238 bits[clk_idx++] = 0;
239 bits[clk_idx++] = 0;
240
241 // Write out 16 bits of data, msb first
242 mask = 0x8000;
243 for (i = 0; i < 16; ++i)
244 {
245 if (phydata & mask)
246 bits[clk_idx++] = MII_MDOE | MII_MDO;
247 else
248 bits[clk_idx++] = MII_MDOE;
249
250 // Shift to next lowest bit
251 mask >>= 1;
252 }
253
254 // Final clock bit (tristate)
255 bits[clk_idx++] = 0;
256
257 // Save the current bank
258 oldBank = inw( ioaddr+BANK_SELECT );
259
260 // Select bank 3
262
263 // Get the current MII register value
264 mii_reg = inw( ioaddr+MII_REG );
265
266 // Turn off all MII Interface bits
267 mii_reg &= ~(MII_MDOE|MII_MCLK|MII_MDI|MII_MDO);
268
269 // Clock all cycles
270 for (i = 0; i < sizeof(bits); ++i)
271 {
272 // Clock Low - output data
273 outw( mii_reg | bits[i], ioaddr+MII_REG );
274 udelay(50);
275
276
277 // Clock Hi - input data
278 outw( mii_reg | bits[i] | MII_MCLK, ioaddr+MII_REG );
279 udelay(50);
280 bits[i] |= inw( ioaddr+MII_REG ) & MII_MDI;
281 }
282
283 // Return to idle state
284 // Set clock to low, data to low, and output tristated
285 outw( mii_reg, ioaddr+MII_REG );
286 udelay(50);
287
288 // Restore original bank select
289 SMC_SELECT_BANK(ioaddr, oldBank);
290
291#if (SMC_DEBUG > 2 )
292 printf("smc_write_phy_register(): phyaddr=%x,phyreg=%x,phydata=%x\n",
293 phyaddr, phyreg, phydata);
294#endif
295}
296
297
298/*------------------------------------------------------------
299 . Finds and reports the PHY address
300 .-------------------------------------------------------------*/
301static int smc_detect_phy(int ioaddr, byte *pphyaddr)
302{
303 word phy_id1;
304 word phy_id2;
305 int phyaddr;
306 int found = 0;
307
308 // Scan all 32 PHY addresses if necessary
309 for (phyaddr = 0; phyaddr < 32; ++phyaddr)
310 {
311 // Read the PHY identifiers
312 phy_id1 = smc_read_phy_register(ioaddr, phyaddr, PHY_ID1_REG);
313 phy_id2 = smc_read_phy_register(ioaddr, phyaddr, PHY_ID2_REG);
314
315 // Make sure it is a valid identifier
316 if ((phy_id2 > 0x0000) && (phy_id2 < 0xffff) &&
317 (phy_id1 > 0x0000) && (phy_id1 < 0xffff))
318 {
319 if ((phy_id1 != 0x8000) && (phy_id2 != 0x8000))
320 {
321 // Save the PHY's address
322 *pphyaddr = phyaddr;
323 found = 1;
324 break;
325 }
326 }
327 }
328
329 if (!found)
330 {
331 printf("No PHY found\n");
332 return(0);
333 }
334
335 // Set the PHY type
336 if ( (phy_id1 == 0x0016) && ((phy_id2 & 0xFFF0) == 0xF840 ) )
337 {
338 printf("PHY=LAN83C183 (LAN91C111 Internal)\n");
339 }
340
341 if ( (phy_id1 == 0x0282) && ((phy_id2 & 0xFFF0) == 0x1C50) )
342 {
343 printf("PHY=LAN83C180\n");
344 }
345
346 return(1);
347}
348
349/*------------------------------------------------------------
350 . Configures the specified PHY using Autonegotiation. Calls
351 . smc_phy_fixed() if the user has requested a certain config.
352 .-------------------------------------------------------------*/
353static void smc_phy_configure(int ioaddr)
354{
355 int timeout;
356 byte phyaddr;
357 word my_phy_caps; // My PHY capabilities
358 word my_ad_caps; // My Advertised capabilities
359 word status;
360 int rpc_cur_mode = RPC_DEFAULT;
361 int lastPhy18;
362
363 // Find the address and type of our phy
364 if (!smc_detect_phy(ioaddr, &phyaddr))
365 {
366 return;
367 }
368
369 // Reset the PHY, setting all other bits to zero
371
372 // Wait for the reset to complete, or time out
373 timeout = 6; // Wait up to 3 seconds
374 while (timeout--)
375 {
377 & PHY_CNTL_RST))
378 {
379 // reset complete
380 break;
381 }
382
383 mdelay(500); // wait 500 millisecs
384 }
385
386 if (timeout < 1)
387 {
388 PRINTK2("PHY reset timed out\n");
389 return;
390 }
391
392 // Read PHY Register 18, Status Output
393 lastPhy18 = smc_read_phy_register(ioaddr, phyaddr, PHY_INT_REG);
394
395 // Enable PHY Interrupts (for register 18)
396 // Interrupts listed here are disabled
401
402 /* Configure the Receive/Phy Control register */
404 outw( rpc_cur_mode, ioaddr + RPC_REG );
405
406 // Copy our capabilities from PHY_STAT_REG to PHY_AD_REG
407 my_phy_caps = smc_read_phy_register(ioaddr, phyaddr, PHY_STAT_REG);
408 my_ad_caps = PHY_AD_CSMA; // I am CSMA capable
409
410 if (my_phy_caps & PHY_STAT_CAP_T4)
411 my_ad_caps |= PHY_AD_T4;
412
413 if (my_phy_caps & PHY_STAT_CAP_TXF)
414 my_ad_caps |= PHY_AD_TX_FDX;
415
416 if (my_phy_caps & PHY_STAT_CAP_TXH)
417 my_ad_caps |= PHY_AD_TX_HDX;
418
419 if (my_phy_caps & PHY_STAT_CAP_TF)
420 my_ad_caps |= PHY_AD_10_FDX;
421
422 if (my_phy_caps & PHY_STAT_CAP_TH)
423 my_ad_caps |= PHY_AD_10_HDX;
424
425 // Update our Auto-Neg Advertisement Register
426 smc_write_phy_register(ioaddr, phyaddr, PHY_AD_REG, my_ad_caps);
427
428 PRINTK2("phy caps=%x\n", my_phy_caps);
429 PRINTK2("phy advertised caps=%x\n", my_ad_caps);
430
431 // Restart auto-negotiation process in order to advertise my caps
434
435 // Wait for the auto-negotiation to complete. This may take from
436 // 2 to 3 seconds.
437 // Wait for the reset to complete, or time out
438 timeout = 20; // Wait up to 10 seconds
439 while (timeout--)
440 {
443 {
444 // auto-negotiate complete
445 break;
446 }
447
448 mdelay(500); // wait 500 millisecs
449
450 // Restart auto-negotiation if remote fault
452 {
453 PRINTK2("PHY remote fault detected\n");
454
455 // Restart auto-negotiation
456 PRINTK2("PHY restarting auto-negotiation\n");
460 }
461 }
462
463 if (timeout < 1)
464 {
465 PRINTK2("PHY auto-negotiate timed out\n");
466 }
467
468 // Fail if we detected an auto-negotiate remote fault
470 {
471 PRINTK2("PHY remote fault detected\n");
472 }
473
474 // Set our sysctl parameters to match auto-negotiation results
475 if ( lastPhy18 & PHY_INT_SPDDET )
476 {
477 PRINTK2("PHY 100BaseT\n");
478 rpc_cur_mode |= RPC_SPEED;
479 }
480 else
481 {
482 PRINTK2("PHY 10BaseT\n");
483 rpc_cur_mode &= ~RPC_SPEED;
484 }
485
486 if ( lastPhy18 & PHY_INT_DPLXDET )
487 {
488 PRINTK2("PHY Full Duplex\n");
489 rpc_cur_mode |= RPC_DPLX;
490 }
491 else
492 {
493 PRINTK2("PHY Half Duplex\n");
494 rpc_cur_mode &= ~RPC_DPLX;
495 }
496
497 // Re-Configure the Receive/Phy Control register
498 outw( rpc_cur_mode, ioaddr + RPC_REG );
499}
500
501/*
502 * Function: smc_reset( int ioaddr )
503 * Purpose:
504 * This sets the SMC91xx chip to its normal state, hopefully from whatever
505 * mess that any other DOS driver has put it in.
506 *
507 * Maybe I should reset more registers to defaults in here? SOFTRESET should
508 * do that for me.
509 *
510 * Method:
511 * 1. send a SOFT RESET
512 * 2. wait for it to finish
513 * 3. reset the memory management unit
514 * 4. clear all interrupts
515 *
516*/
517static void smc_reset(int ioaddr)
518{
519 /* This resets the registers mostly to defaults, but doesn't
520 * affect EEPROM. That seems unnecessary */
523
524 /* this should pause enough for the chip to be happy */
526
527 /* Set the transmit and receive configuration registers to
528 * default values */
531
532 /* Reset the MMU */
535
536 /* Note: It doesn't seem that waiting for the MMU busy is needed here,
537 * but this is a place where future chipsets _COULD_ break. Be wary
538 * of issuing another MMU command right after this */
539 _outb(0, ioaddr + INT_MASK);
540}
541
542
543/*----------------------------------------------------------------------
544 * Function: smc9000_probe_addr( int ioaddr )
545 *
546 * Purpose:
547 * Tests to see if a given ioaddr points to an SMC9xxx chip.
548 * Returns a 1 on success
549 *
550 * Algorithm:
551 * (1) see if the high byte of BANK_SELECT is 0x33
552 * (2) compare the ioaddr with the base register's address
553 * (3) see if I recognize the chip ID in the appropriate register
554 *
555 * ---------------------------------------------------------------------
556 */
558{
559 word bank;
560 word revision_register;
561 word base_address_register;
562
563 /* First, see if the high byte is 0x33 */
564 bank = inw(ioaddr + BANK_SELECT);
565 if ((bank & 0xFF00) != 0x3300) {
566 return 0;
567 }
568 /* The above MIGHT indicate a device, but I need to write to further
569 * test this. */
570 _outw(0x0, ioaddr + BANK_SELECT);
571 bank = inw(ioaddr + BANK_SELECT);
572 if ((bank & 0xFF00) != 0x3300) {
573 return 0;
574 }
575
576 /* well, we've already written once, so hopefully another time won't
577 * hurt. This time, I need to switch the bank register to bank 1,
578 * so I can access the base address register */
580 base_address_register = inw(ioaddr + BASE);
581
582 if (ioaddr != (base_address_register >> 3 & 0x3E0)) {
583 DBG("SMC9000: IOADDR %hX doesn't match configuration (%hX)."
584 "Probably not a SMC chip\n",
585 ioaddr, base_address_register >> 3 & 0x3E0);
586 /* well, the base address register didn't match. Must not have
587 * been a SMC chip after all. */
588 return 0;
589 }
590
591
592 /* check if the revision register is something that I recognize.
593 * These might need to be added to later, as future revisions
594 * could be added. */
596 revision_register = inw(ioaddr + REVISION);
597 if (!chip_ids[(revision_register >> 4) & 0xF]) {
598 /* I don't recognize this chip, so... */
599 DBG( "SMC9000: IO %hX: Unrecognized revision register:"
600 " %hX, Contact author.\n", ioaddr, revision_register );
601 return 0;
602 }
603
604 /* at this point I'll assume that the chip is an SMC9xxx.
605 * It might be prudent to check a listing of MAC addresses
606 * against the hardware address, or do some other tests. */
607 return 1;
608}
609
610
611/**************************************************************************
612 * ETH_TRANSMIT - Transmit a frame
613 ***************************************************************************/
615 struct nic *nic,
616 const char *d, /* Destination */
617 unsigned int t, /* Type */
618 unsigned int s, /* size */
619 const char *p) /* Packet */
620{
621 word length; /* real, length incl. header */
622 word numPages;
623 unsigned long time_out;
624 byte packet_no;
625 word status;
626 int i;
627
628 /* We dont pad here since we can have the hardware doing it for us */
629 length = (s + ETH_HLEN + 1)&~1;
630
631 /* convert to MMU pages */
632 numPages = length / 256;
633
634 if (numPages > 7 ) {
635 DBG("SMC9000: Far too big packet error. \n");
636 return;
637 }
638
639 /* dont try more than, say 30 times */
640 for (i=0;i<30;i++) {
641 /* now, try to allocate the memory */
643 _outw(MC_ALLOC | numPages, nic->ioaddr + MMU_CMD);
644
645 status = 0;
646 /* wait for the memory allocation to finnish */
647 for (time_out = currticks() + 5*TICKS_PER_SEC; currticks() < time_out; ) {
649 if ( status & IM_ALLOC_INT ) {
650 /* acknowledge the interrupt */
652 break;
653 }
654 }
655
656 if ((status & IM_ALLOC_INT) != 0 ) {
657 /* We've got the memory */
658 break;
659 } else {
660 printf("SMC9000: Memory allocation timed out, resetting MMU.\n");
662 }
663 }
664
665 /* If I get here, I _know_ there is a packet slot waiting for me */
666 packet_no = inb(nic->ioaddr + PNR_ARR + 1);
667 if (packet_no & 0x80) {
668 /* or isn't there? BAD CHIP! */
669 printf("SMC9000: Memory allocation failed. \n");
670 return;
671 }
672
673 /* we have a packet address, so tell the card to use it */
674 _outb(packet_no, nic->ioaddr + PNR_ARR);
675
676 /* point to the beginning of the packet */
678
679#if SMC9000_DEBUG > 2
680 printf("Trying to xmit packet of length %hX\n", length );
681#endif
682
683 /* send the packet length ( +6 for status, length and ctl byte )
684 * and the status word ( set to zeros ) */
685 _outw(0, nic->ioaddr + DATA_1 );
686
687 /* send the packet length ( +6 for status words, length, and ctl) */
688 _outb((length+6) & 0xFF, nic->ioaddr + DATA_1);
689 _outb((length+6) >> 8 , nic->ioaddr + DATA_1);
690
691 /* Write the contents of the packet */
692
693 /* The ethernet header first... */
694 outsw(nic->ioaddr + DATA_1, d, ETH_ALEN >> 1);
696 _outw(htons(t), nic->ioaddr + DATA_1);
697
698 /* ... the data ... */
699 outsw(nic->ioaddr + DATA_1 , p, s >> 1);
700
701 /* ... and the last byte, if there is one. */
702 if ((s & 1) == 0) {
703 _outw(0, nic->ioaddr + DATA_1);
704 } else {
705 _outb(p[s-1], nic->ioaddr + DATA_1);
706 _outb(0x20, nic->ioaddr + DATA_1);
707 }
708
709 /* and let the chipset deal with it */
711
712 status = 0; time_out = currticks() + 5*TICKS_PER_SEC;
713 do {
715
716 if ((status & IM_TX_INT ) != 0) {
717 word tx_status;
718
719 /* ack interrupt */
721
722 packet_no = inw(nic->ioaddr + FIFO_PORTS);
723 packet_no &= 0x7F;
724
725 /* select this as the packet to read from */
726 _outb( packet_no, nic->ioaddr + PNR_ARR );
727
728 /* read the first word from this packet */
730
731 tx_status = inw( nic->ioaddr + DATA_1 );
732
733 if (0 == (tx_status & TS_SUCCESS)) {
734 DBG("SMC9000: TX FAIL STATUS: %hX \n", tx_status);
735 /* re-enable transmit */
738 }
739
740 /* kill the packet */
743
744 return;
745 }
746 }while(currticks() < time_out);
747
748 printf("SMC9000: TX timed out, resetting board\n");
750 return;
751}
752
753/**************************************************************************
754 * ETH_POLL - Wait for a frame
755 ***************************************************************************/
756static int smc9000_poll(struct nic *nic, int retrieve)
757{
760 return 0;
761
762 if ( ! retrieve ) return 1;
763
764 /* start reading from the start of the packet */
766
767 /* First read the status and check that we're ok */
768 if (!(inw(nic->ioaddr + DATA_1) & RS_ERRORS)) {
769 /* Next: read the packet length and mask off the top bits */
770 nic->packetlen = (inw(nic->ioaddr + DATA_1) & 0x07ff);
771
772 /* the packet length includes the 3 extra words */
773 nic->packetlen -= 6;
774#if SMC9000_DEBUG > 2
775 printf(" Reading %d words (and %d byte(s))\n",
776 (nic->packetlen >> 1), nic->packetlen & 1);
777#endif
778 /* read the packet (and the last "extra" word) */
779 insw(nic->ioaddr + DATA_1, nic->packet, (nic->packetlen+2) >> 1);
780 /* is there an odd last byte ? */
781 if (nic->packet[nic->packetlen+1] & 0x20)
782 nic->packetlen++;
783
784 /* error or good, tell the card to get rid of this packet */
786 return 1;
787 }
788
789 printf("SMC9000: RX error\n");
790 /* error or good, tell the card to get rid of this packet */
792 return 0;
793}
794
795static void smc9000_disable ( struct nic *nic, struct isa_device *isa __unused ) {
796
798
799 /* no more interrupts for me */
801 _outb( 0, nic->ioaddr + INT_MASK);
802
803 /* and tell the card to stay away from that nasty outside world */
807}
808
809static void smc9000_irq(struct nic *nic __unused, irq_action_t action __unused)
810{
811 switch ( action ) {
812 case DISABLE :
813 break;
814 case ENABLE :
815 break;
816 case FORCE :
817 break;
818 }
819}
820
822 .connect = dummy_connect,
823 .poll = smc9000_poll,
824 .transmit = smc9000_transmit,
825 .irq = smc9000_irq,
826
827};
828
829/**************************************************************************
830 * ETH_PROBE - Look for an adapter
831 ***************************************************************************/
832
833static int smc9000_probe ( struct nic *nic, struct isa_device *isa ) {
834
835 unsigned short revision;
836 int memory;
837 int media;
838 const char * version_string;
839 const char * if_string;
840 int i;
841
842 nic->irqno = 0;
843 nic->ioaddr = isa->ioaddr;
844
845 /*
846 * Get the MAC address ( bank 1, regs 4 - 9 )
847 */
849 for ( i = 0; i < 6; i += 2 ) {
851
852 address = inw(nic->ioaddr + ADDR0 + i);
853 nic->node_addr[i+1] = address >> 8;
854 nic->node_addr[i] = address & 0xFF;
855 }
856
857 /* get the memory information */
859 memory = ( inw(nic->ioaddr + MCR) >> 9 ) & 0x7; /* multiplier */
860 memory *= 256 * (inw(nic->ioaddr + MIR) & 0xFF);
861
862 /*
863 * Now, I want to find out more about the chip. This is sort of
864 * redundant, but it's cleaner to have it in both, rather than having
865 * one VERY long probe procedure.
866 */
869 version_string = chip_ids[(revision >> 4) & 0xF];
870
871 if (((revision & 0xF0) >> 4 == CHIP_9196) &&
872 ((revision & 0x0F) >= REV_9196)) {
873 /* This is a 91c96. 'c96 has the same chip id as 'c94 (4) but
874 * a revision starting at 6 */
875 version_string = smc91c96_id;
876 }
877
878 if ( !version_string ) {
879 /* I shouldn't get here because this call was done before.... */
880 return 0;
881 }
882
883 /* is it using AUI or 10BaseT ? */
885 if (inw(nic->ioaddr + CFG) & CFG_AUI_SELECT)
886 media = 2;
887 else
888 media = 1;
889
890 if_string = interfaces[media - 1];
891
892 /* now, reset the chip, and put it into a known state */
894
895 printf("SMC9000 %s\n", smc9000_version);
896 DBG("Copyright (C) 1998 Daniel Engstr\x94m\n");
897 DBG("Copyright (C) 1996 Eric Stahlman\n");
898
899 printf("%s rev:%d I/O port:%hX Interface:%s RAM:%d bytes \n",
900 version_string, revision & 0xF,
901 nic->ioaddr, if_string, memory );
902
903 DBG ( "Ethernet MAC address: %s\n", eth_ntoa ( nic->node_addr ) );
904
906
907 /* see the header file for options in TCR/RCR NORMAL*/
910
911 /* Select which interface to use */
913 if ( media == 1 ) {
915 nic->ioaddr + CFG );
916 }
917 else if ( media == 2 ) {
919 nic->ioaddr + CFG );
920 }
921
923
925 return 1;
926}
927
928/*
929 * The SMC9000 can be at any of the following port addresses. To
930 * change for a slightly different card, you can add it to the array.
931 *
932 */
934 0x200, 0x220, 0x240, 0x260, 0x280, 0x2A0, 0x2C0, 0x2E0,
935 0x300, 0x320, 0x340, 0x360, 0x380, 0x3A0, 0x3C0, 0x3E0,
936};
937
939 GENERIC_ISAPNP_VENDOR, 0x8228 );
940
941DRIVER ( "SMC9000", nic_driver, isa_driver, smc9000_driver,
943
944ISA_ROM ( "smc9000", "SMC9000" );
945
946/*
947 * Local variables:
948 * c-basic-offset: 8
949 * c-indent-level: 8
950 * tab-width: 8
951 * End:
952 */
#define BASE
Definition 3c595.h:69
#define NULL
NULL pointer (VOID *)
Definition Base.h:322
static volatile void * bits
Definition bitops.h:28
void timeout(int)
static unsigned long ioaddr
Definition davicom.c:129
uint8_t status
Status.
Definition ena.h:5
uint64_t address
Base address.
Definition ena.h:13
Error codes.
const char * eth_ntoa(const void *ll_addr)
Transcribe Ethernet address.
Definition ethernet.c:176
Ethernet protocol.
#define __unused
Declare a variable or data structure as unused.
Definition compiler.h:573
#define DBG(...)
Print a debugging message.
Definition compiler.h:498
#define FILE_LICENCE(_licence)
Declare a particular licence as applying to a file.
Definition compiler.h:896
uint32_t revision
Entry point revision.
Definition ib_mad.h:9
#define ETH_ALEN
Definition if_ether.h:9
#define ETH_HLEN
Definition if_ether.h:10
#define htons(value)
Definition byteswap.h:136
#define inw(io_addr)
Definition io.h:292
#define outw(data, io_addr)
Definition io.h:320
#define insw(io_addr, data, count)
Definition io.h:412
#define inb(io_addr)
Definition io.h:283
#define outsw(io_addr, data, count)
Definition io.h:447
uint16_t isa_probe_addr_t
Definition isa.h:31
#define ISA_ROM(IMAGE, DESCRIPTION)
Definition isa.h:92
#define TICKS_PER_SEC
Number of ticks per second.
Definition timer.h:16
#define GENERIC_ISAPNP_VENDOR
Definition isa_ids.h:38
int dummy_connect(struct nic *nic __unused)
Definition legacy.c:175
#define DRIVER(_name_text, _unused2, _unused3, _name, _probe, _disable, _fake_bss)
Definition nic.h:220
irq_action_t
Definition nic.h:34
@ FORCE
Definition nic.h:37
@ ENABLE
Definition nic.h:36
@ DISABLE
Definition nic.h:35
#define ISA_DRIVER(_name, _probe_addrs, _probe_addr, _vendor_id, _prod_id)
Definition nic.h:188
struct @002057171240057303273132130141036221271355330106 no_fake_bss
u16 length
Definition sky2.h:1
static void smc9000_disable(struct nic *nic, struct isa_device *isa __unused)
Definition smc9000.c:795
#define _outw
Definition smc9000.c:49
static int smc9000_probe(struct nic *nic, struct isa_device *isa)
Definition smc9000.c:833
static void smc_phy_configure(int ioaddr)
Definition smc9000.c:353
static isa_probe_addr_t smc9000_probe_addrs[]
Definition smc9000.c:933
static const char * interfaces[2]
Definition smc9000.c:52
static int smc9000_probe_addr(isa_probe_addr_t ioaddr)
Definition smc9000.c:557
static void smc_write_phy_register(int ioaddr, byte phyaddr, byte phyreg, word phydata)
Definition smc9000.c:189
static int smc_detect_phy(int ioaddr, byte *pphyaddr)
Definition smc9000.c:301
static const char smc9000_version[]
Definition smc9000.c:51
#define _outb
Definition smc9000.c:48
static const char smc91c96_id[]
Definition smc9000.c:65
static int smc9000_poll(struct nic *nic, int retrieve)
Definition smc9000.c:756
static void smc9000_irq(struct nic *nic __unused, irq_action_t action __unused)
Definition smc9000.c:809
#define PRINTK2(args...)
Definition smc9000.c:38
static const char * chip_ids[15]
Definition smc9000.c:53
static struct nic_operations smc9000_operations
Definition smc9000.c:821
static void smc_reset(int ioaddr)
Definition smc9000.c:517
static word smc_read_phy_register(int ioaddr, byte phyaddr, byte phyreg)
Definition smc9000.c:70
static void smc9000_transmit(struct nic *nic, const char *d, unsigned int t, unsigned int s, const char *p)
Definition smc9000.c:614
#define PHY_STAT_ANEG_ACK
Definition smc9000.h:256
#define PHY_INT_DPLXDET
Definition smc9000.h:316
unsigned char byte
Definition smc9000.h:38
#define RPC_SPEED
Definition smc9000.h:100
#define SMC_DELAY(x)
Definition smc9000.h:422
#define PHY_STAT_REG
Definition smc9000.h:249
#define RPC_REG
Definition smc9000.h:99
#define PHY_AD_TX_FDX
Definition smc9000.h:273
unsigned short word
Definition smc9000.h:39
#define MII_MDOE
Definition smc9000.h:196
#define PTR_AUTOINC
Definition smc9000.h:169
#define PHY_CNTL_SPEED
Definition smc9000.h:240
#define SMC_SELECT_BANK(x, y)
Definition smc9000.h:419
#define RCR
Definition smc9000.h:81
#define TCR
Definition smc9000.h:66
#define PHY_CNTL_ANEG_EN
Definition smc9000.h:241
#define PHY_AD_10_FDX
Definition smc9000.h:275
#define REV_9196
Definition smc9000.h:213
#define MII_REG
Definition smc9000.h:194
#define PHY_INT_JAB
Definition smc9000.h:314
#define PHY_STAT_REM_FLT
Definition smc9000.h:257
#define PHY_AD_10_HDX
Definition smc9000.h:276
#define RPC_DEFAULT
Definition smc9000.h:113
#define PHY_INT_SSD
Definition smc9000.h:311
#define DATA_1
Definition smc9000.h:172
#define MC_ALLOC
Definition smc9000.h:153
#define FIFO_PORTS
Definition smc9000.h:161
#define PHY_INT_ESD
Definition smc9000.h:312
#define MCR
Definition smc9000.h:94
#define MIR
Definition smc9000.h:93
#define PTR_READ
Definition smc9000.h:167
#define CFG_AUI_SELECT
Definition smc9000.h:135
#define PHY_CNTL_DPLX
Definition smc9000.h:245
#define PHY_STAT_CAP_T4
Definition smc9000.h:250
#define MC_RELEASE
Definition smc9000.h:156
#define MC_RESET
Definition smc9000.h:154
#define PHY_ID2_REG
Definition smc9000.h:265
#define PHY_INT_SPDDET
Definition smc9000.h:315
#define IM_TX_INT
Definition smc9000.h:178
#define PHY_AD_TX_HDX
Definition smc9000.h:274
#define RCR_NORMAL
Definition smc9000.h:89
#define POINTER
Definition smc9000.h:166
#define RCR_SOFTRESET
Definition smc9000.h:82
#define PHY_STAT_CAP_TXF
Definition smc9000.h:251
#define PHY_STAT_CAP_TXH
Definition smc9000.h:252
#define PHY_INT_LOSSSYNC
Definition smc9000.h:309
#define BANK_SELECT
Definition smc9000.h:62
#define FP_RXEMPTY
Definition smc9000.h:163
#define IM_ALLOC_INT
Definition smc9000.h:180
#define MII_MDO
Definition smc9000.h:199
#define RPC_DPLX
Definition smc9000.h:101
#define MC_ENQUEUE
Definition smc9000.h:158
#define PHY_CNTL_ANEG_RST
Definition smc9000.h:244
#define PHY_AD_CSMA
Definition smc9000.h:277
#define PHY_AD_T4
Definition smc9000.h:272
#define INT_MASK
Definition smc9000.h:176
#define PHY_INT_REG
Definition smc9000.h:306
#define PTR_RCV
Definition smc9000.h:168
#define PHY_ID1_REG
Definition smc9000.h:264
#define MII_MDI
Definition smc9000.h:198
#define TS_SUCCESS
Definition smc9000.h:218
#define TCR_CLEAR
Definition smc9000.h:73
#define RS_ERRORS
Definition smc9000.h:232
#define PHY_AD_REG
Definition smc9000.h:268
#define ADDR0
Definition smc9000.h:137
#define CHIP_9196
Definition smc9000.h:209
#define CFG
Definition smc9000.h:134
#define INTERRUPT
Definition smc9000.h:174
#define PHY_MASK_REG
Definition smc9000.h:319
#define PHY_CNTL_RST
Definition smc9000.h:238
#define PNR_ARR
Definition smc9000.h:160
#define MC_FREEPKT
Definition smc9000.h:157
#define PHY_STAT_CAP_TF
Definition smc9000.h:253
#define PHY_INT_CWRD
Definition smc9000.h:310
#define REVISION
Definition smc9000.h:191
#define PHY_STAT_CAP_TH
Definition smc9000.h:254
#define RCR_CLEAR
Definition smc9000.h:90
#define MMU_CMD
Definition smc9000.h:150
#define TCR_ENABLE
Definition smc9000.h:67
#define TCR_NORMAL
Definition smc9000.h:75
#define PHY_INT_RPOL
Definition smc9000.h:313
#define PHY_CNTL_REG
Definition smc9000.h:237
#define MII_MCLK
Definition smc9000.h:197
An ISA device.
Definition isa.h:12
uint16_t ioaddr
I/O address.
Definition isa.h:16
An ISA driver.
Definition isa.h:34
Definition nic.h:49
unsigned char * packet
Definition nic.h:53
unsigned char * node_addr
Definition nic.h:52
unsigned int packetlen
Definition nic.h:54
unsigned char irqno
Definition nic.h:56
unsigned int ioaddr
Definition nic.h:55
struct nic_operations * nic_op
Definition nic.h:50
static char media[]
Definition sundance.c:85
unsigned long currticks(void)
Get current system time in ticks.
Definition timer.c:43
void mdelay(unsigned long msecs)
Delay for a fixed number of milliseconds.
Definition timer.c:79
void udelay(unsigned long usecs)
Delay for a fixed number of microseconds.
Definition timer.c:61
int printf(const char *fmt,...)
Write a formatted string to the console.
Definition vsprintf.c:465