|
|
1.1 root 1: /*
2: * EAGLE Technology Model NE3210
3: * 32-Bit EISA BUS Ethernet LAN Adapter.
4: * Programmer's Reference Guide kindly supplied
5: * by Artisoft Inc/Eagle Technology.
6: *
7: * BUGS:
8: * no setting of values from config file;
9: * should we worry about doubleword memmove restrictions?
10: * no way to use mem addresses > 0xD8000 at present.
11: */
12: #include "u.h"
13: #include "lib.h"
14: #include "mem.h"
15: #include "dat.h"
16: #include "fns.h"
17: #include "io.h"
18:
19: #include "ether.h"
20:
21: enum { /* EISA slot space */
22: NVLreset = 0xC84, /* 0 == reset, 1 == enable */
23: NVLconfig = 0xC90,
24:
25: DP83902off = 0x000, /* offset of DP83902 registers */
26: Eaddroff = 0x016, /* offset of Ethernet address */
27: };
28:
29: static struct {
30: ulong port;
31: ulong config;
32: } slotinfo[MaxEISA];
33:
34: static ulong mem[8] = {
35: 0x00FF0000, 0x00FE0000, 0x000D8000, 0x0FFF0000,
36: 0x0FFE0000, 0x0FFC0000, 0x000D0000, 0x00000000,
37: };
38:
39: static ulong irq[8] = {
40: 15, 12, 11, 10, 9, 7, 5, 3,
41: };
42:
43: static struct {
44: char *type;
45: uchar val;
46: } media[] = {
47: { "10BaseT", 0x00, },
48: { "RJ-45", 0x00, },
49: { "10Base5", 0x80, },
50: { "AUI", 0x80, },
51: { "10Base2", 0xC0, },
52: { "BNC", 0xC0, },
53: { 0, },
54: };
55:
56: static void*
57: read(Ctlr *ctlr, void *to, ulong from, ulong len)
58: {
59: /*
60: * In this case, 'from' is an index into the shared memory.
61: */
62: memmove(to, (void*)(ctlr->card.mem+from), len);
63: return to;
64: }
65:
66: static void*
67: write(Ctlr *ctlr, ulong to, void *from, ulong len)
68: {
69: /*
70: * In this case, 'to' is an index into the shared memory.
71: */
72: memmove((void*)(ctlr->card.mem+to), from, len);
73: return (void*)to;
74: }
75:
76: int
77: ne3210reset(Ctlr *ctlr)
78: {
79: static int already;
80: int i;
81: ulong p;
82:
83: /*
84: * First time through, check if this is an EISA machine.
85: * If not, nothing to do. If it is, run through the slots
86: * looking for appropriate cards and saving the
87: * configuration info.
88: */
89: if(already == 0){
90: already = 1;
91: if(strncmp((char*)(KZERO|0xFFFD9), "EISA", 4))
92: return 0;
93:
94: for(i = 1; i < MaxEISA; i++){
95: p = i*0x1000;
96: if(inl(p+EISAconfig) != 0x0118CC3A)
97: continue;
98:
99: slotinfo[i].port = p;
100: slotinfo[i].config = inb(p+NVLconfig);
101: }
102: }
103:
104: /*
105: * Look through the found adapters for one that matches
106: * the given port address (if any). The possibilties are:
107: * 1) 0;
108: * 2) a slot address.
109: */
110: i = 0;
111: if(ctlr->card.port == 0){
112: for(i = 1; i < MaxEISA; i++){
113: if(slotinfo[i].port)
114: break;
115: }
116: }
117: else if(ctlr->card.port >= 0x1000){
118: if((i = (ctlr->card.port>>16)) < MaxEISA){
119: if((ctlr->card.port & 0xFFF) || slotinfo[i].port == 0)
120: i = 0;
121: }
122: }
123: if(i >= MaxEISA || slotinfo[i].port == 0)
124: return 0;
125:
126: /*
127: * Set the software configuration using the values obtained.
128: * For now, ignore any values from the config file.
129: */
130: ctlr->card.port = slotinfo[i].port;
131: ctlr->card.mem = KZERO|mem[slotinfo[i].config & 0x07];
132: ctlr->card.irq = irq[(slotinfo[i].config>>3) & 0x07];
133: ctlr->card.size = 32*1024;
134:
135: /*
136: * Set up the stupid DP83902 configuration.
137: */
138: ctlr->card.reset = ne3210reset;
139: ctlr->card.attach = dp8390attach;
140: ctlr->card.read = read;
141: ctlr->card.write = write;
142: ctlr->card.receive = dp8390receive;
143: ctlr->card.transmit = dp8390transmit;
144: ctlr->card.intr = dp8390intr;
145: ctlr->card.bit16 = 1;
146: ctlr->card.ram = 1;
147:
148: ctlr->card.dp8390 = ctlr->card.port+DP83902off;
149: ctlr->card.tstart = 0;
150: ctlr->card.pstart = HOWMANY(sizeof(Etherpkt), Dp8390BufSz);
151: ctlr->card.pstop = HOWMANY(ctlr->card.size, Dp8390BufSz);
152:
153: /*
154: * Reset the board, then
155: * initialise the DP83902,
156: * set the ether address.
157: */
158: outb(ctlr->card.port+NVLreset, 0x00);
159: delay(2);
160: outb(ctlr->card.port+NVLreset, 0x01);
161:
162: dp8390reset(ctlr);
163: if((ctlr->card.ea[0]|ctlr->card.ea[1]|ctlr->card.ea[2]|ctlr->card.ea[3]|ctlr->card.ea[4]|ctlr->card.ea[5]) == 0){
164: for(i = 0; i < sizeof(ctlr->card.ea); i++)
165: ctlr->card.ea[i] = inb(ctlr->card.port+Eaddroff+i);
166: }
167: dp8390setea(ctlr);
168:
169: return 0;
170: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.