xref: /openbsd/sys/dev/isa/if_ie.c (revision 471aeecf)
1 /*	$OpenBSD: if_ie.c,v 1.59 2022/04/06 18:59:28 naddy Exp $	*/
2 /*	$NetBSD: if_ie.c,v 1.51 1996/05/12 23:52:48 mycroft Exp $	*/
3 
4 /*-
5  * Copyright (c) 1993, 1994, 1995 Charles Hannum.
6  * Copyright (c) 1992, 1993, University of Vermont and State
7  *  Agricultural College.
8  * Copyright (c) 1992, 1993, Garrett A. Wollman.
9  *
10  * Portions:
11  * Copyright (c) 1993, 1994, 1995, Rodney W. Grimes
12  * Copyright (c) 1994, 1995, Rafal K. Boni
13  * Copyright (c) 1990, 1991, William F. Jolitz
14  * Copyright (c) 1990, The Regents of the University of California
15  *
16  * All rights reserved.
17  *
18  * Redistribution and use in source and binary forms, with or without
19  * modification, are permitted provided that the following conditions
20  * are met:
21  * 1. Redistributions of source code must retain the above copyright
22  *    notice, this list of conditions and the following disclaimer.
23  * 2. Redistributions in binary form must reproduce the above copyright
24  *    notice, this list of conditions and the following disclaimer in the
25  *    documentation and/or other materials provided with the distribution.
26  * 3. All advertising materials mentioning features or use of this software
27  *    must display the following acknowledgement:
28  *	This product includes software developed by Charles Hannum, by the
29  *	University of Vermont and State Agricultural College and Garrett A.
30  *	Wollman, by William F. Jolitz, and by the University of California,
31  *	Berkeley, Lawrence Berkeley Laboratory, and its contributors.
32  * 4. Neither the names of the Universities nor the names of the authors
33  *    may be used to endorse or promote products derived from this software
34  *    without specific prior written permission.
35  *
36  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
37  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
38  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
39  * ARE DISCLAIMED.  IN NO EVENT SHALL THE UNIVERSITY OR AUTHORS BE LIABLE
40  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
41  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
42  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
43  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
44  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
45  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
46  * SUCH DAMAGE.
47  */
48 
49 /*
50  * Intel 82586 Ethernet chip
51  * Register, bit, and structure definitions.
52  *
53  * Original StarLAN driver written by Garrett Wollman with reference to the
54  * Clarkson Packet Driver code for this chip written by Russ Nelson and others.
55  *
56  * BPF support code taken from hpdev/if_le.c, supplied with tcpdump.
57  *
58  * 3C507 support is loosely based on code donated to NetBSD by Rafal Boni.
59  *
60  * Intel EtherExpress 16 support taken from FreeBSD's if_ix.c, written
61  * by Rodney W. Grimes.
62  *
63  * Majorly cleaned up and 3C507 code merged by Charles Hannum.
64  */
65 
66 /*
67  * The i82586 is a very versatile chip, found in many implementations.
68  * Programming this chip is mostly the same, but certain details differ
69  * from card to card.  This driver is written so that different cards
70  * can be automatically detected at run-time.
71  */
72 
73 /*
74 Mode of operation:
75 
76 We run the 82586 in a standard Ethernet mode.  We keep NFRAMES received frame
77 descriptors around for the receiver to use, and NRXBUF associated receive
78 buffer descriptors, both in a circular list.  Whenever a frame is received, we
79 rotate both lists as necessary.  (The 586 treats both lists as a simple
80 queue.)  We also keep a transmit command around so that packets can be sent
81 off quickly.
82 
83 We configure the adapter in AL-LOC = 1 mode, which means that the
84 Ethernet/802.3 MAC header is placed at the beginning of the receive buffer
85 rather than being split off into various fields in the RFD.  This also means
86 that we must include this header in the transmit buffer as well.
87 
88 By convention, all transmit commands, and only transmit commands, shall have
89 the I (IE_CMD_INTR) bit set in the command.  This way, when an interrupt
90 arrives at ieintr(), it is immediately possible to tell what precisely caused
91 it.  ANY OTHER command-sending routines should run at splnet(), and should
92 post an acknowledgement to every interrupt they generate.
93 
94 The 82586 has a 24-bit address space internally, and the adaptor's memory is
95 located at the top of this region.  However, the value we are given in
96 configuration is the CPU's idea of where the adaptor RAM is.  So, we must go
97 through a few gyrations to come up with a kernel virtual address which
98 represents the actual beginning of the 586 address space.  First, we autosize
99 the RAM by running through several possible sizes and trying to initialize the
100 adapter under the assumption that the selected size is correct.  Then, knowing
101 the correct RAM size, we set up our pointers in the softc.  `sc_maddr'
102 represents the computed base of the 586 address space.  `iomembot' represents
103 the actual configured base of adapter RAM.  Finally, `sc_msize' represents the
104 calculated size of 586 RAM.  Then, when laying out commands, we use the
105 interval [sc_maddr, sc_maddr + sc_msize); to make 24-pointers, we subtract
106 iomem, and to make 16-pointers, we subtract sc_maddr and and with 0xffff.
107 */
108 
109 #include "bpfilter.h"
110 
111 #include <sys/param.h>
112 #include <sys/systm.h>
113 #include <sys/mbuf.h>
114 #include <sys/buf.h>
115 #include <sys/socket.h>
116 #include <sys/ioctl.h>
117 #include <sys/errno.h>
118 #include <sys/syslog.h>
119 #include <sys/device.h>
120 #include <sys/timeout.h>
121 
122 #include <net/if.h>
123 
124 #if NBPFILTER > 0
125 #include <net/bpf.h>
126 #endif
127 
128 #include <netinet/in.h>
129 #include <netinet/if_ether.h>
130 
131 #include <machine/cpu.h>
132 #include <machine/bus.h>
133 #include <machine/intr.h>
134 
135 #include <dev/isa/isareg.h>
136 #include <dev/isa/isavar.h>
137 #include <i386/isa/isa_machdep.h>	/* XXX USES ISA HOLE DIRECTLY */
138 #include <dev/ic/i82586reg.h>
139 #include <dev/isa/if_ieatt.h>
140 #include <dev/isa/if_ie507.h>
141 #include <dev/isa/if_iee16.h>
142 #include <dev/isa/elink.h>
143 
144 #define	IED_RINT	0x01
145 #define	IED_TINT	0x02
146 #define	IED_RNR		0x04
147 #define	IED_CNA		0x08
148 #define	IED_READFRAME	0x10
149 #define	IED_ENQ		0x20
150 #define	IED_XMIT	0x40
151 #define	IED_ALL		0x7f
152 
153 /*
154 sizeof(iscp) == 1+1+2+4 == 8
155 sizeof(scb) == 2+2+2+2+2+2+2+2 == 16
156 NFRAMES * sizeof(rfd) == NFRAMES*(2+2+2+2+6+6+2+2) == NFRAMES*24 == 384
157 sizeof(xmit_cmd) == 2+2+2+2+6+2 == 18
158 sizeof(transmit buffer) == ETHER_MAX_LEN == 1518
159 sizeof(transmit buffer desc) == 8
160 -----
161 1952
162 
163 NRXBUF * sizeof(rbd) == NRXBUF*(2+2+4+2+2) == NRXBUF*12
164 NRXBUF * IE_RBUF_SIZE == NRXBUF*256
165 
166 NRXBUF should be (16384 - 1952) / (256 + 12) == 14432 / 268 == 53
167 
168 With NRXBUF == 48, this leaves us 1568 bytes for another command or
169 more buffers.  Another transmit command would be 18+8+1518 == 1544
170 ---just barely fits!
171 
172 Obviously all these would have to be reduced for smaller memory sizes.
173 With a larger memory, it would be possible to roughly double the number of
174 both transmit and receive buffers.
175 */
176 
177 #define	NFRAMES		16		/* number of receive frames */
178 #define	NRXBUF		48		/* number of buffers to allocate */
179 #define	IE_RBUF_SIZE	256		/* size of each receive buffer;
180 						MUST BE POWER OF TWO */
181 #define	NTXBUF		2		/* number of transmit commands */
182 #define	IE_TBUF_SIZE	ETHER_MAX_LEN	/* length of transmit buffer */
183 
184 
185 enum ie_hardware {
186 	IE_STARLAN10,
187 	IE_EN100,
188 	IE_SLFIBER,
189 	IE_3C507,
190 	IE_EE16,
191 	IE_UNKNOWN
192 };
193 
194 const char *ie_hardware_names[] = {
195 	"StarLAN 10",
196 	"EN100",
197 	"StarLAN Fiber",
198 	"3C507",
199 	"EtherExpress 16",
200 	"Unknown"
201 };
202 
203 /*
204  * Ethernet status, per interface.
205  */
206 struct ie_softc {
207 	struct device sc_dev;
208 	void *sc_ih;
209 
210 	int sc_iobase;
211 	caddr_t sc_maddr;
212 	u_int sc_msize;
213 
214 	struct arpcom sc_arpcom;
215 
216 	void (*reset_586)(struct ie_softc *);
217 	void (*chan_attn)(struct ie_softc *);
218 
219 	enum ie_hardware hard_type;
220 	int hard_vers;
221 
222 	int want_mcsetup;
223 	int promisc;
224 	volatile struct ie_int_sys_conf_ptr *iscp;
225 	volatile struct ie_sys_ctl_block *scb;
226 
227 	int rfhead, rftail, rbhead, rbtail;
228 	volatile struct ie_recv_frame_desc *rframes[NFRAMES];
229 	volatile struct ie_recv_buf_desc *rbuffs[NRXBUF];
230 	volatile char *cbuffs[NRXBUF];
231 
232 	int xmit_busy;
233 	int xchead, xctail;
234 	volatile struct ie_xmit_cmd *xmit_cmds[NTXBUF];
235 	volatile struct ie_xmit_buf *xmit_buffs[NTXBUF];
236 	u_char *xmit_cbuffs[NTXBUF];
237 
238 	struct ie_en_addr mcast_addrs[MAXMCAST + 1];
239 	int mcast_count;
240 
241 	u_short	irq_encoded;		/* encoded interrupt on IEE16 */
242 
243 #ifdef IEDEBUG
244 	int sc_debug;
245 #endif
246 };
247 
248 void iewatchdog(struct ifnet *);
249 int ieintr(void *);
250 void iestop(struct ie_softc *);
251 int ieinit(struct ie_softc *);
252 int ieioctl(struct ifnet *, u_long, caddr_t);
253 void iestart(struct ifnet *);
254 static void el_reset_586(struct ie_softc *);
255 static void sl_reset_586(struct ie_softc *);
256 static void el_chan_attn(struct ie_softc *);
257 static void sl_chan_attn(struct ie_softc *);
258 static void slel_get_address(struct ie_softc *);
259 
260 static void ee16_reset_586(struct ie_softc *);
261 static void ee16_chan_attn(struct ie_softc *);
262 static void ee16_interrupt_enable(struct ie_softc *);
263 void ee16_eeprom_outbits(struct ie_softc *, int, int);
264 void ee16_eeprom_clock(struct ie_softc *, int);
265 u_short ee16_read_eeprom(struct ie_softc *, int);
266 int ee16_eeprom_inbits(struct ie_softc *);
267 
268 void iereset(struct ie_softc *);
269 void ie_readframe(struct ie_softc *, int);
270 void ie_drop_packet_buffer(struct ie_softc *);
271 void ie_find_mem_size(struct ie_softc *);
272 static int command_and_wait(struct ie_softc *, int,
273     void volatile *, int);
274 void ierint(struct ie_softc *);
275 void ietint(struct ie_softc *);
276 void iexmit(struct ie_softc *);
277 struct mbuf *ieget(struct ie_softc *, struct ether_header *);
278 void iememinit(void *, struct ie_softc *);
279 static int mc_setup(struct ie_softc *, void *);
280 static void mc_reset(struct ie_softc *);
281 
282 #ifdef IEDEBUG
283 void print_rbd(volatile struct ie_recv_buf_desc *);
284 
285 int in_ierint = 0;
286 int in_ietint = 0;
287 #endif
288 
289 int	ieprobe(struct device *, void *, void *);
290 void	ieattach(struct device *, struct device *, void *);
291 int	sl_probe(struct ie_softc *, struct isa_attach_args *);
292 int	el_probe(struct ie_softc *, struct isa_attach_args *);
293 int	ee16_probe(struct ie_softc *, struct isa_attach_args *);
294 int	check_ie_present(struct ie_softc *, caddr_t, u_int);
295 
296 static __inline void ie_setup_config(volatile struct ie_config_cmd *,
297     int, int);
298 static __inline void ie_ack(struct ie_softc *, u_int);
299 static __inline int ether_equal(u_char *, u_char *);
300 static __inline int check_eh(struct ie_softc *, struct ether_header *);
301 static __inline int ie_buflen(struct ie_softc *, int);
302 static __inline int ie_packet_len(struct ie_softc *);
303 
304 static void run_tdr(struct ie_softc *, struct ie_tdr_cmd *);
305 
306 const struct cfattach ie_isa_ca = {
307 	sizeof(struct ie_softc), ieprobe, ieattach
308 };
309 
310 struct cfdriver ie_cd = {
311 	NULL, "ie", DV_IFNET
312 };
313 
314 #define MK_24(base, ptr) ((caddr_t)((u_long)ptr - (u_long)base))
315 #define MK_16(base, ptr) ((u_short)(u_long)MK_24(base, ptr))
316 
317 #define PORT	sc->sc_iobase
318 #define MEM 	sc->sc_maddr
319 
320 /*
321  * Here are a few useful functions.  We could have done these as macros, but
322  * since we have the inline facility, it makes sense to use that instead.
323  */
324 static __inline void
ie_setup_config(volatile struct ie_config_cmd * cmd,int promiscuous,int manchester)325 ie_setup_config(volatile struct ie_config_cmd *cmd, int promiscuous,
326     int manchester)
327 {
328 
329 	cmd->ie_config_count = 0x0c;
330 	cmd->ie_fifo = 8;
331 	cmd->ie_save_bad = 0x40;
332 	cmd->ie_addr_len = 0x2e;
333 	cmd->ie_priority = 0;
334 	cmd->ie_ifs = 0x60;
335 	cmd->ie_slot_low = 0;
336 	cmd->ie_slot_high = 0xf2;
337 	cmd->ie_promisc = promiscuous | manchester << 2;
338 	cmd->ie_crs_cdt = 0;
339 	cmd->ie_min_len = 64;
340 	cmd->ie_junk = 0xff;
341 }
342 
343 static __inline void
ie_ack(struct ie_softc * sc,u_int mask)344 ie_ack(struct ie_softc *sc, u_int mask)
345 {
346 	volatile struct ie_sys_ctl_block *scb = sc->scb;
347 
348 	scb->ie_command = scb->ie_status & mask;
349 	(sc->chan_attn)(sc);
350 
351 	while (scb->ie_command)
352 		;		/* Spin Lock */
353 }
354 
355 int
ieprobe(struct device * parent,void * match,void * aux)356 ieprobe(struct device *parent, void *match, void *aux)
357 {
358 	struct ie_softc *sc = match;
359 	struct isa_attach_args *ia = aux;
360 
361 	if (sl_probe(sc, ia))
362 		return 1;
363 	if (el_probe(sc, ia))
364 		return 1;
365 	if (ee16_probe(sc, ia))
366 		return 1;
367 	return 0;
368 }
369 
370 int
sl_probe(struct ie_softc * sc,struct isa_attach_args * ia)371 sl_probe(struct ie_softc *sc, struct isa_attach_args *ia)
372 {
373 	u_char c;
374 
375 	sc->sc_iobase = ia->ia_iobase;
376 
377 	/* Need this for part of the probe. */
378 	sc->reset_586 = sl_reset_586;
379 	sc->chan_attn = sl_chan_attn;
380 
381 	c = inb(PORT + IEATT_REVISION);
382 	switch (SL_BOARD(c)) {
383 	case SL10_BOARD:
384 		sc->hard_type = IE_STARLAN10;
385 		break;
386 	case EN100_BOARD:
387 		sc->hard_type = IE_EN100;
388 		break;
389 	case SLFIBER_BOARD:
390 		sc->hard_type = IE_SLFIBER;
391 		break;
392 
393 	default:
394 		/* Anything else is not recognized or cannot be used. */
395 #if 0
396 		printf("%s: unknown AT&T board type code %d\n",
397 		    sc->sc_dev.dv_xname, SL_BOARD(c));
398 #endif
399 		return 0;
400 	}
401 
402 	sc->hard_vers = SL_REV(c);
403 
404 	if (ia->ia_irq == IRQUNK || ia->ia_maddr == MADDRUNK) {
405 		printf("%s: %s does not have soft configuration\n",
406 		    sc->sc_dev.dv_xname, ie_hardware_names[sc->hard_type]);
407 		return 0;
408 	}
409 
410 	/*
411 	 * Divine memory size on-board the card.  Usually 16k.
412 	 */
413 	sc->sc_maddr = ISA_HOLE_VADDR(ia->ia_maddr);
414 	ie_find_mem_size(sc);
415 
416 	if (!sc->sc_msize) {
417 		printf("%s: can't find shared memory\n", sc->sc_dev.dv_xname);
418 		return 0;
419 	}
420 
421 	if (!ia->ia_msize)
422 		ia->ia_msize = sc->sc_msize;
423 	else if (ia->ia_msize != sc->sc_msize) {
424 		printf("%s: msize mismatch; kernel configured %d != board configured %d\n",
425 		    sc->sc_dev.dv_xname, ia->ia_msize, sc->sc_msize);
426 		return 0;
427 	}
428 
429 	slel_get_address(sc);
430 
431 	ia->ia_iosize = 16;
432 	return 1;
433 }
434 
435 int
el_probe(struct ie_softc * sc,struct isa_attach_args * ia)436 el_probe(struct ie_softc *sc, struct isa_attach_args *ia)
437 {
438 	bus_space_tag_t iot = ia->ia_iot;
439 	bus_space_handle_t ioh;
440 	u_char c;
441 	int i, rval = 0;
442 	u_char signature[] = "*3COM*";
443 
444 	sc->sc_iobase = ia->ia_iobase;
445 
446 	/* Need this for part of the probe. */
447 	sc->reset_586 = el_reset_586;
448 	sc->chan_attn = el_chan_attn;
449 
450 	/*
451 	 * Map the Etherlink ID port for the probe sequence.
452 	 */
453 	if (bus_space_map(iot, ELINK_ID_PORT, 1, 0, &ioh)) {
454 		printf("3c507 probe: can't map Etherlink ID port\n");
455 		return 0;
456 	}
457 
458 	/*
459 	 * Reset and put card in CONFIG state without changing address.
460 	 * XXX Indirect brokenness here!
461 	 */
462 	elink_reset(iot, ioh, sc->sc_dev.dv_parent->dv_unit);
463 	elink_idseq(iot, ioh, ELINK_507_POLY);
464 	elink_idseq(iot, ioh, ELINK_507_POLY);
465 	outb(ELINK_ID_PORT, 0xff);
466 
467 	/* Check for 3COM signature before proceeding. */
468 	outb(PORT + IE507_CTRL, inb(PORT + IE507_CTRL) & 0xfc);	/* XXX */
469 	for (i = 0; i < 6; i++)
470 		if (inb(PORT + i) != signature[i])
471 			goto out;
472 
473 	c = inb(PORT + IE507_MADDR);
474 	if (c & 0x20) {
475 		printf("%s: can't map 3C507 RAM in high memory\n",
476 		    sc->sc_dev.dv_xname);
477 		goto out;
478 	}
479 
480 	/* Go to RUN state. */
481 	outb(ELINK_ID_PORT, 0x00);
482 	elink_idseq(iot, ioh, ELINK_507_POLY);
483 	outb(ELINK_ID_PORT, 0x00);
484 
485 	/* Set bank 2 for version info and read BCD version byte. */
486 	outb(PORT + IE507_CTRL, EL_CTRL_NRST | EL_CTRL_BNK2);
487 	i = inb(PORT + 3);
488 
489 	sc->hard_type = IE_3C507;
490 	sc->hard_vers = 10*(i / 16) + (i % 16) - 1;
491 
492 	i = inb(PORT + IE507_IRQ) & 0x0f;
493 
494 	if (ia->ia_irq != IRQUNK) {
495 		if (ia->ia_irq != i) {
496 			printf("%s: irq mismatch; kernel configured %d != board configured %d\n",
497 			    sc->sc_dev.dv_xname, ia->ia_irq, i);
498 			goto out;
499 		}
500 	} else
501 		ia->ia_irq = i;
502 
503 	i = ((inb(PORT + IE507_MADDR) & 0x1c) << 12) + 0xc0000;
504 
505 	if (ia->ia_maddr != MADDRUNK) {
506 		if (ia->ia_maddr != i) {
507 			printf("%s: maddr mismatch; kernel configured %x != board configured %x\n",
508 			    sc->sc_dev.dv_xname, ia->ia_maddr, i);
509 			goto out;
510 		}
511 	} else
512 		ia->ia_maddr = i;
513 
514 	outb(PORT + IE507_CTRL, EL_CTRL_NORMAL);
515 
516 	/*
517 	 * Divine memory size on-board the card.
518 	 */
519 	sc->sc_maddr = ISA_HOLE_VADDR(ia->ia_maddr);
520 	ie_find_mem_size(sc);
521 
522 	if (!sc->sc_msize) {
523 		printf("%s: can't find shared memory\n", sc->sc_dev.dv_xname);
524 		outb(PORT + IE507_CTRL, EL_CTRL_NRST);
525 		goto out;
526 	}
527 
528 	if (!ia->ia_msize)
529 		ia->ia_msize = sc->sc_msize;
530 	else if (ia->ia_msize != sc->sc_msize) {
531 		printf("%s: msize mismatch; kernel configured %d != board configured %d\n",
532 		    sc->sc_dev.dv_xname, ia->ia_msize, sc->sc_msize);
533 		outb(PORT + IE507_CTRL, EL_CTRL_NRST);
534 		goto out;
535 	}
536 
537 	slel_get_address(sc);
538 
539 	/* Clear the interrupt latch just in case. */
540 	outb(PORT + IE507_ICTRL, 1);
541 
542 	ia->ia_iosize = 16;
543 	rval = 1;
544 
545  out:
546 	bus_space_unmap(iot, ioh, 1);
547 	return rval;
548 }
549 
550 /* Taken almost exactly from Rod's if_ix.c. */
551 
552 int
ee16_probe(struct ie_softc * sc,struct isa_attach_args * ia)553 ee16_probe(struct ie_softc *sc, struct isa_attach_args *ia)
554 {
555 	int i;
556 	u_short board_id, id_var1, id_var2, checksum = 0;
557 	u_short eaddrtemp, irq;
558         u_short pg, adjust, decode, edecode;
559 	u_char	bart_config;
560 
561 	short	irq_translate[] = {0, 0x09, 0x03, 0x04, 0x05, 0x0a, 0x0b, 0};
562 
563 	/* Need this for part of the probe. */
564 	sc->reset_586 = ee16_reset_586;
565 	sc->chan_attn = ee16_chan_attn;
566 
567 	/* reset any ee16 at the current iobase */
568 	outb(ia->ia_iobase + IEE16_ECTRL, IEE16_RESET_ASIC);
569 	outb(ia->ia_iobase + IEE16_ECTRL, 0);
570 	delay(240);
571 
572 	/* now look for ee16. */
573 	board_id = id_var1 = id_var2 = 0;
574 	for (i=0; i<4 ; i++) {
575 		id_var1 = inb(ia->ia_iobase + IEE16_ID_PORT);
576 		id_var2 = ((id_var1 & 0x03) << 2);
577 		board_id |= (( id_var1 >> 4)  << id_var2);
578 		}
579 
580 	if (board_id != IEE16_ID)
581 		return 0;
582 
583 	/* need sc->sc_iobase for ee16_read_eeprom */
584 	sc->sc_iobase = ia->ia_iobase;
585 	sc->hard_type = IE_EE16;
586 
587 	/*
588 	 * If ia->maddr == MADDRUNK, use value in eeprom location 6.
589 	 *
590 	 * The shared RAM location on the EE16 is encoded into bits
591 	 * 3-7 of EEPROM location 6.  We zero the upper byte, and
592 	 * shift the 5 bits right 3.  The resulting number tells us
593 	 * the RAM location.  Because the EE16 supports either 16k or 32k
594 	 * of shared RAM, we only worry about the 32k locations.
595 	 *
596 	 * NOTE: if a 64k EE16 exists, it should be added to this switch.
597 	 *       then the ia->ia_msize would need to be set per case statement.
598 	 *
599 	 *	value	msize	location
600 	 *	=====	=====	========
601 	 *	0x03	0x8000	0xCC000
602 	 *	0x06	0x8000	0xD0000
603 	 *	0x0C	0x8000	0xD4000
604 	 *	0x18	0x8000	0xD8000
605 	 *
606 	 */
607 
608 	if ((ia->ia_maddr == MADDRUNK) || (ia->ia_msize == 0)) {
609 		i = (ee16_read_eeprom(sc, 6) & 0x00ff ) >> 3;
610 		switch(i) {
611 			case 0x03:
612 				ia->ia_maddr = 0xCC000;
613 				break;
614 			case 0x06:
615 				ia->ia_maddr = 0xD0000;
616 				break;
617 			case 0x0c:
618 				ia->ia_maddr = 0xD4000;
619 				break;
620 			case 0x18:
621 				ia->ia_maddr = 0xD8000;
622 				break;
623 			default:
624 				return 0 ;
625 				break; /* NOTREACHED */
626 		}
627 		ia->ia_msize = 0x8000;
628 	}
629 
630 	/* need to set these after checking for MADDRUNK */
631 	sc->sc_maddr = ISA_HOLE_VADDR(ia->ia_maddr);
632 	sc->sc_msize = ia->ia_msize;
633 
634 	/* need to put the 586 in RESET, and leave it */
635 	outb( PORT + IEE16_ECTRL, IEE16_RESET_586);
636 
637 	/* read the eeprom and checksum it, should == IEE16_ID */
638 	for(i=0 ; i< 0x40 ; i++)
639 		checksum += ee16_read_eeprom(sc, i);
640 
641 	if (checksum != IEE16_ID)
642 		return 0;
643 
644 	/*
645 	 * Size and test the memory on the board.  The size of the memory
646 	 * can be one of 16k, 32k, 48k or 64k.  It can be located in the
647 	 * address range 0xC0000 to 0xEFFFF on 16k boundaries.
648 	 *
649 	 * If the size does not match the passed in memory allocation size
650 	 * issue a warning, but continue with the minimum of the two sizes.
651 	 */
652 
653 	switch (ia->ia_msize) {
654 		case 65536:
655 		case 32768: /* XXX Only support 32k and 64k right now */
656 			break;
657 		case 16384:
658 		case 49512:
659 		default:
660 			printf("ieprobe mapped memory size out of range\n");
661 			return 0;
662 			break; /* NOTREACHED */
663 	}
664 
665 	if ((kvtop(sc->sc_maddr) < 0xC0000) ||
666 	    (kvtop(sc->sc_maddr) + sc->sc_msize > 0xF0000)) {
667 		printf("ieprobe mapped memory address out of range\n");
668 		return 0;
669 	}
670 
671 	pg = (kvtop(sc->sc_maddr) & 0x3C000) >> 14;
672 	adjust = IEE16_MCTRL_FMCS16 | (pg & 0x3) << 2;
673 	decode = ((1 << (sc->sc_msize / 16384)) - 1) << pg;
674 	edecode = ((~decode >> 4) & 0xF0) | (decode >> 8);
675 
676 	/* ZZZ This should be checked against eeprom location 6, low byte */
677 	outb(PORT + IEE16_MEMDEC, decode & 0xFF);
678 	/* ZZZ This should be checked against eeprom location 1, low byte */
679 	outb(PORT + IEE16_MCTRL, adjust);
680 	/* ZZZ Now if I could find this one I would have it made */
681 	outb(PORT + IEE16_MPCTRL, (~decode & 0xFF));
682 	/* ZZZ I think this is location 6, high byte */
683 	outb(PORT + IEE16_MECTRL, edecode); /*XXX disable Exxx */
684 
685 	/*
686 	 * first prime the stupid bart DRAM controller so that it
687 	 * works, then zero out all of memory.
688 	 */
689 	bzero(sc->sc_maddr, 32);
690 	bzero(sc->sc_maddr, sc->sc_msize);
691 
692 	/*
693 	 * Get the encoded interrupt number from the EEPROM, check it
694 	 * against the passed in IRQ.  Issue a warning if they do not
695 	 * match, and fail the probe.  If irq is 'IRQUNK' then we
696 	 * use the EEPROM irq, and continue.
697 	 */
698 	irq = ee16_read_eeprom(sc, IEE16_EEPROM_CONFIG1);
699 	irq = (irq & IEE16_EEPROM_IRQ) >> IEE16_EEPROM_IRQ_SHIFT;
700 	sc->irq_encoded = irq;
701 	irq = irq_translate[irq];
702 	if (ia->ia_irq != IRQUNK) {
703 		if (irq != ia->ia_irq) {
704 #ifdef DIAGNOSTIC
705 			printf("\nie%d: fatal: board IRQ %d does not match kernel\n", sc->sc_dev.dv_unit, irq);
706 #endif /* DIAGNOSTIC */
707 			return 0; 	/* _must_ match or probe fails */
708 		}
709 	} else
710 		ia->ia_irq = irq;
711 
712 	/*
713 	 * Get the hardware ethernet address from the EEPROM and
714 	 * save it in the softc for use by the 586 setup code.
715 	 */
716 	eaddrtemp = ee16_read_eeprom(sc, IEE16_EEPROM_ENET_HIGH);
717 	sc->sc_arpcom.ac_enaddr[1] = eaddrtemp & 0xFF;
718 	sc->sc_arpcom.ac_enaddr[0] = eaddrtemp >> 8;
719 	eaddrtemp = ee16_read_eeprom(sc, IEE16_EEPROM_ENET_MID);
720 	sc->sc_arpcom.ac_enaddr[3] = eaddrtemp & 0xFF;
721 	sc->sc_arpcom.ac_enaddr[2] = eaddrtemp >> 8;
722 	eaddrtemp = ee16_read_eeprom(sc, IEE16_EEPROM_ENET_LOW);
723 	sc->sc_arpcom.ac_enaddr[5] = eaddrtemp & 0xFF;
724 	sc->sc_arpcom.ac_enaddr[4] = eaddrtemp >> 8;
725 
726 	/* disable the board interrupts */
727 	outb(PORT + IEE16_IRQ, sc->irq_encoded);
728 
729 	/* enable loopback to keep bad packets off the wire */
730 	if(sc->hard_type == IE_EE16) {
731 		bart_config = inb(PORT + IEE16_CONFIG);
732 		bart_config |= IEE16_BART_LOOPBACK;
733 		bart_config |= IEE16_BART_MCS16_TEST; /* inb doesn't get bit! */
734 		outb(PORT + IEE16_CONFIG, bart_config);
735 		bart_config = inb(PORT + IEE16_CONFIG);
736 	}
737 
738 	outb(PORT + IEE16_ECTRL, 0);
739 	delay(100);
740 	if (!check_ie_present(sc, sc->sc_maddr, sc->sc_msize))
741 		return 0;
742 
743 	ia->ia_iosize = 16;	/* the number of I/O ports */
744 	return 1;		/* found */
745 }
746 
747 /*
748  * Taken almost exactly from Bill's if_is.c, then modified beyond recognition.
749  */
750 void
ieattach(struct device * parent,struct device * self,void * aux)751 ieattach(struct device *parent, struct device *self, void *aux)
752 {
753 	struct ie_softc *sc = (void *)self;
754 	struct isa_attach_args *ia = aux;
755 	struct ifnet *ifp = &sc->sc_arpcom.ac_if;
756 
757 	bcopy(sc->sc_dev.dv_xname, ifp->if_xname, IFNAMSIZ);
758 	ifp->if_softc = sc;
759 	ifp->if_start = iestart;
760 	ifp->if_ioctl = ieioctl;
761 	ifp->if_watchdog = iewatchdog;
762 	ifp->if_flags =
763 	    IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST;
764 
765 	/* Attach the interface. */
766 	if_attach(ifp);
767 	ether_ifattach(ifp);
768 
769 	printf(": address %s, type %s R%d\n",
770 	    ether_sprintf(sc->sc_arpcom.ac_enaddr),
771 	    ie_hardware_names[sc->hard_type], sc->hard_vers + 1);
772 
773 	sc->sc_ih = isa_intr_establish(ia->ia_ic, ia->ia_irq, IST_EDGE,
774 	    IPL_NET, ieintr, sc, sc->sc_dev.dv_xname);
775 }
776 
777 /*
778  * Device timeout/watchdog routine.  Entered if the device neglects to generate
779  * an interrupt after a transmit has been started on it.
780  */
781 void
iewatchdog(struct ifnet * ifp)782 iewatchdog(struct ifnet *ifp)
783 {
784 	struct ie_softc *sc = ifp->if_softc;
785 
786 	log(LOG_ERR, "%s: device timeout\n", sc->sc_dev.dv_xname);
787 	++sc->sc_arpcom.ac_if.if_oerrors;
788 	iereset(sc);
789 }
790 
791 /*
792  * What to do upon receipt of an interrupt.
793  */
794 int
ieintr(void * arg)795 ieintr(void *arg)
796 {
797 	struct ie_softc *sc = arg;
798 	register u_short status;
799 
800 	/* Clear the interrupt latch on the 3C507. */
801 	if (sc->hard_type == IE_3C507)
802 		outb(PORT + IE507_ICTRL, 1);
803 
804 	/* disable interrupts on the EE16. */
805 	if (sc->hard_type == IE_EE16)
806 		outb(PORT + IEE16_IRQ, sc->irq_encoded);
807 
808 	status = sc->scb->ie_status & IE_ST_WHENCE;
809 	if (status == 0)
810 		return 0;
811 
812 loop:
813 	/* Ack interrupts FIRST in case we receive more during the ISR. */
814 	ie_ack(sc, status);
815 
816 	if (status & (IE_ST_FR | IE_ST_RNR)) {
817 #ifdef IEDEBUG
818 		in_ierint++;
819 		if (sc->sc_debug & IED_RINT)
820 			printf("%s: rint\n", sc->sc_dev.dv_xname);
821 #endif
822 		ierint(sc);
823 #ifdef IEDEBUG
824 		in_ierint--;
825 #endif
826 	}
827 
828 	if (status & IE_ST_CX) {
829 #ifdef IEDEBUG
830 		in_ietint++;
831 		if (sc->sc_debug & IED_TINT)
832 			printf("%s: tint\n", sc->sc_dev.dv_xname);
833 #endif
834 		ietint(sc);
835 #ifdef IEDEBUG
836 		in_ietint--;
837 #endif
838 	}
839 
840 	if (status & IE_ST_RNR) {
841 		printf("%s: receiver not ready\n", sc->sc_dev.dv_xname);
842 		sc->sc_arpcom.ac_if.if_ierrors++;
843 		iereset(sc);
844 	}
845 
846 #ifdef IEDEBUG
847 	if ((status & IE_ST_CNA) && (sc->sc_debug & IED_CNA))
848 		printf("%s: cna\n", sc->sc_dev.dv_xname);
849 #endif
850 
851 	/* Clear the interrupt latch on the 3C507. */
852 	if (sc->hard_type == IE_3C507)
853 		outb(PORT + IE507_ICTRL, 1);
854 
855 	status = sc->scb->ie_status & IE_ST_WHENCE;
856 	if (status == 0) {
857 		/* enable interrupts on the EE16. */
858 		if (sc->hard_type == IE_EE16)
859 		    outb(PORT + IEE16_IRQ, sc->irq_encoded | IEE16_IRQ_ENABLE);
860 		return 1;
861 	}
862 
863 	goto loop;
864 }
865 
866 /*
867  * Process a received-frame interrupt.
868  */
869 void
ierint(struct ie_softc * sc)870 ierint(struct ie_softc *sc)
871 {
872 	volatile struct ie_sys_ctl_block *scb = sc->scb;
873 	int i, status;
874 	static int timesthru = 1024;
875 
876 	i = sc->rfhead;
877 	for (;;) {
878 		status = sc->rframes[i]->ie_fd_status;
879 
880 		if ((status & IE_FD_COMPLETE) && (status & IE_FD_OK)) {
881 			if (!--timesthru) {
882 				sc->sc_arpcom.ac_if.if_ierrors +=
883 				    scb->ie_err_crc + scb->ie_err_align +
884 				    scb->ie_err_resource + scb->ie_err_overrun;
885 				scb->ie_err_crc = scb->ie_err_align =
886 				    scb->ie_err_resource = scb->ie_err_overrun =
887 				    0;
888 				timesthru = 1024;
889 			}
890 			ie_readframe(sc, i);
891 		} else {
892 			if ((status & IE_FD_RNR) != 0 &&
893 			    (scb->ie_status & IE_RU_READY) == 0) {
894 				sc->rframes[0]->ie_fd_buf_desc =
895 						MK_16(MEM, sc->rbuffs[0]);
896 				scb->ie_recv_list = MK_16(MEM, sc->rframes[0]);
897 				command_and_wait(sc, IE_RU_START, 0, 0);
898 			}
899 			break;
900 		}
901 		i = (i + 1) % NFRAMES;
902 	}
903 }
904 
905 /*
906  * Process a command-complete interrupt.  These are only generated by the
907  * transmission of frames.  This routine is deceptively simple, since most of
908  * the real work is done by iestart().
909  */
910 void
ietint(struct ie_softc * sc)911 ietint(struct ie_softc *sc)
912 {
913 	struct ifnet *ifp = &sc->sc_arpcom.ac_if;
914 	int status;
915 
916 	ifp->if_timer = 0;
917 	ifq_clr_oactive(&ifp->if_snd);
918 
919 	status = sc->xmit_cmds[sc->xctail]->ie_xmit_status;
920 
921 	if (!(status & IE_STAT_COMPL) || (status & IE_STAT_BUSY))
922 		printf("ietint: command still busy!\n");
923 
924 	if (status & IE_STAT_OK) {
925 		ifp->if_collisions += status & IE_XS_MAXCOLL;
926 	} else {
927 		ifp->if_oerrors++;
928 		/*
929 		 * XXX
930 		 * Check SQE and DEFERRED?
931 		 * What if more than one bit is set?
932 		 */
933 		if (status & IE_STAT_ABORT)
934 			printf("%s: send aborted\n", sc->sc_dev.dv_xname);
935 		else if (status & IE_XS_LATECOLL)
936 			printf("%s: late collision\n", sc->sc_dev.dv_xname);
937 		else if (status & IE_XS_NOCARRIER)
938 			printf("%s: no carrier\n", sc->sc_dev.dv_xname);
939 		else if (status & IE_XS_LOSTCTS)
940 			printf("%s: lost CTS\n", sc->sc_dev.dv_xname);
941 		else if (status & IE_XS_UNDERRUN)
942 			printf("%s: DMA underrun\n", sc->sc_dev.dv_xname);
943 		else if (status & IE_XS_EXCMAX) {
944 			printf("%s: too many collisions\n", sc->sc_dev.dv_xname);
945 			ifp->if_collisions += 16;
946 		}
947 	}
948 
949 	/*
950 	 * If multicast addresses were added or deleted while transmitting,
951 	 * mc_reset() set the want_mcsetup flag indicating that we should do
952 	 * it.
953 	 */
954 	if (sc->want_mcsetup) {
955 		mc_setup(sc, (caddr_t)sc->xmit_cbuffs[sc->xctail]);
956 		sc->want_mcsetup = 0;
957 	}
958 
959 	/* Done with the buffer. */
960 	sc->xmit_busy--;
961 	sc->xctail = (sc->xctail + 1) % NTXBUF;
962 
963 	/* Start the next packet, if any, transmitting. */
964 	if (sc->xmit_busy > 0)
965 		iexmit(sc);
966 
967 	iestart(ifp);
968 }
969 
970 /*
971  * Compare two Ether/802 addresses for equality, inlined and unrolled for
972  * speed.  I'd love to have an inline assembler version of this...
973  */
974 static __inline int
ether_equal(u_char * one,u_char * two)975 ether_equal(u_char *one, u_char *two)
976 {
977 
978 	if (one[0] != two[0] || one[1] != two[1] || one[2] != two[2] ||
979 	    one[3] != two[3] || one[4] != two[4] || one[5] != two[5])
980 		return 0;
981 	return 1;
982 }
983 
984 /*
985  * Check for a valid address.
986  * Return value is true if the packet is for us, and false otherwise.
987  */
988 static __inline int
check_eh(struct ie_softc * sc,struct ether_header * eh)989 check_eh(struct ie_softc *sc, struct ether_header *eh)
990 {
991 	int i;
992 
993 	switch (sc->promisc) {
994 	case IFF_ALLMULTI:
995 		/*
996 		 * Receiving all multicasts, but no unicasts except those
997 		 * destined for us.
998 		 */
999 		if (eh->ether_dhost[0] & 1)
1000 			return 1;
1001 		if (ether_equal(eh->ether_dhost, sc->sc_arpcom.ac_enaddr))
1002 			return 1;
1003 		return 0;
1004 
1005 	case IFF_PROMISC:
1006 		/* If for us, accept and hand up to BPF */
1007 		if (ether_equal(eh->ether_dhost, sc->sc_arpcom.ac_enaddr))
1008 			return 1;
1009 
1010 		/*
1011 		 * Not a multicast, so BPF wants to see it but we don't.
1012 		 */
1013 		if (!(eh->ether_dhost[0] & 1))
1014 			return 1;
1015 
1016 		/*
1017 		 * If it's one of our multicast groups, accept it and pass it
1018 		 * up.
1019 		 */
1020 		for (i = 0; i < sc->mcast_count; i++) {
1021 			if (ether_equal(eh->ether_dhost, (u_char *)&sc->mcast_addrs[i])) {
1022 				return 1;
1023 			}
1024 		}
1025 		return 1;
1026 
1027 	case IFF_ALLMULTI | IFF_PROMISC:
1028 		/* We want to see multicasts. */
1029 		if (eh->ether_dhost[0] & 1)
1030 			return 1;
1031 
1032 		/* We want to see our own packets */
1033 		if (ether_equal(eh->ether_dhost, sc->sc_arpcom.ac_enaddr))
1034 			return 1;
1035 
1036 		return 1;
1037 
1038 	case 0:
1039 		return 1;
1040 	}
1041 
1042 #ifdef DIAGNOSTIC
1043 	panic("check_eh: impossible");
1044 #endif
1045 	return 0;
1046 }
1047 
1048 /*
1049  * We want to isolate the bits that have meaning...  This assumes that
1050  * IE_RBUF_SIZE is an even power of two.  If somehow the act_len exceeds
1051  * the size of the buffer, then we are screwed anyway.
1052  */
1053 static __inline int
ie_buflen(struct ie_softc * sc,int head)1054 ie_buflen(struct ie_softc *sc, int head)
1055 {
1056 
1057 	return (sc->rbuffs[head]->ie_rbd_actual
1058 	    & (IE_RBUF_SIZE | (IE_RBUF_SIZE - 1)));
1059 }
1060 
1061 static __inline int
ie_packet_len(struct ie_softc * sc)1062 ie_packet_len(struct ie_softc *sc)
1063 {
1064 	int i;
1065 	int head = sc->rbhead;
1066 	int acc = 0;
1067 
1068 	do {
1069 		if (!(sc->rbuffs[sc->rbhead]->ie_rbd_actual & IE_RBD_USED))
1070 			return -1;
1071 
1072 		i = sc->rbuffs[head]->ie_rbd_actual & IE_RBD_LAST;
1073 
1074 		acc += ie_buflen(sc, head);
1075 		head = (head + 1) % NRXBUF;
1076 	} while (!i);
1077 
1078 	return acc;
1079 }
1080 
1081 /*
1082  * Setup all necessary artifacts for an XMIT command, and then pass the XMIT
1083  * command to the chip to be executed.  On the way, if we have a BPF listener
1084  * also give him a copy.
1085  */
1086 void
iexmit(struct ie_softc * sc)1087 iexmit(struct ie_softc *sc)
1088 {
1089 
1090 #ifdef IEDEBUG
1091 	if (sc->sc_debug & IED_XMIT)
1092 		printf("%s: xmit buffer %d\n", sc->sc_dev.dv_xname,
1093 		    sc->xctail);
1094 #endif
1095 
1096 	sc->xmit_buffs[sc->xctail]->ie_xmit_flags |= IE_XMIT_LAST;
1097 	sc->xmit_buffs[sc->xctail]->ie_xmit_next = 0xffff;
1098 	sc->xmit_buffs[sc->xctail]->ie_xmit_buf =
1099 	    MK_24(MEM, sc->xmit_cbuffs[sc->xctail]);
1100 
1101 	sc->xmit_cmds[sc->xctail]->com.ie_cmd_link = 0xffff;
1102 	sc->xmit_cmds[sc->xctail]->com.ie_cmd_cmd =
1103 	    IE_CMD_XMIT | IE_CMD_INTR | IE_CMD_LAST;
1104 
1105 	sc->xmit_cmds[sc->xctail]->ie_xmit_status = 0;
1106 	sc->xmit_cmds[sc->xctail]->ie_xmit_desc =
1107 	    MK_16(MEM, sc->xmit_buffs[sc->xctail]);
1108 
1109 	sc->scb->ie_command_list = MK_16(MEM, sc->xmit_cmds[sc->xctail]);
1110 	command_and_wait(sc, IE_CU_START, 0, 0);
1111 
1112 	sc->sc_arpcom.ac_if.if_timer = 5;
1113 }
1114 
1115 /*
1116  * Read data off the interface, and turn it into an mbuf chain.
1117  *
1118  * This code is DRAMATICALLY different from the previous version; this version
1119  * tries to allocate the entire mbuf chain up front, given the length of the
1120  * data available.  This enables us to allocate mbuf clusters in many
1121  * situations where before we would have had a long chain of partially-full
1122  * mbufs.  This should help to speed up the operation considerably.  (Provided
1123  * that it works, of course.)
1124  */
1125 struct mbuf *
ieget(struct ie_softc * sc,struct ether_header * ehp)1126 ieget(struct ie_softc *sc, struct ether_header *ehp)
1127 {
1128 	struct mbuf *top, **mp, *m;
1129 	int len, totlen, resid;
1130 	int thisrboff, thismboff;
1131 	int head;
1132 
1133 	resid = totlen = ie_packet_len(sc);
1134 	if (totlen <= 0) {
1135 		sc->sc_arpcom.ac_if.if_ierrors++;
1136 		return 0;
1137 	}
1138 
1139 	head = sc->rbhead;
1140 
1141 	/*
1142 	 * Snarf the Ethernet header.
1143 	 */
1144 	bcopy((caddr_t)sc->cbuffs[head], (caddr_t)ehp, sizeof *ehp);
1145 
1146 	/*
1147 	 * As quickly as possible, check if this packet is for us.
1148 	 * If not, don't waste a single cycle copying the rest of the
1149 	 * packet in.
1150 	 * This is only a consideration when FILTER is defined; i.e., when
1151 	 * we are either running BPF or doing multicasting.
1152 	 */
1153 	if (!check_eh(sc, ehp))
1154 		/* not an error */
1155 		return 0;
1156 
1157 	MGETHDR(m, M_DONTWAIT, MT_DATA);
1158 	if (m == NULL) {
1159 		sc->sc_arpcom.ac_if.if_ierrors++;
1160 		return 0;
1161 	}
1162 	m->m_pkthdr.len = totlen;
1163 	len = MHLEN;
1164 	top = 0;
1165 	mp = &top;
1166 
1167 	/*
1168 	 * This loop goes through and allocates mbufs for all the data we will
1169 	 * be copying in.  It does not actually do the copying yet.
1170 	 */
1171 	while (totlen > 0) {
1172 		if (top) {
1173 			MGET(m, M_DONTWAIT, MT_DATA);
1174 			if (m == NULL) {
1175 				m_freem(top);
1176 				sc->sc_arpcom.ac_if.if_ierrors++;
1177 				return 0;
1178 			}
1179 			len = MLEN;
1180 		}
1181 		if (totlen >= MINCLSIZE) {
1182 			MCLGET(m, M_DONTWAIT);
1183 			if (m->m_flags & M_EXT)
1184 				len = MCLBYTES;
1185 		}
1186 		m->m_len = len = min(totlen, len);
1187 		totlen -= len;
1188 		*mp = m;
1189 		mp = &m->m_next;
1190 	}
1191 
1192 	m = top;
1193 	thisrboff = 0;
1194 	thismboff = 0;
1195 
1196 	/*
1197 	 * Now we take the mbuf chain (hopefully only one mbuf most of the
1198 	 * time) and stuff the data into it.  There are no possible failures at
1199 	 * or after this point.
1200 	 */
1201 	while (resid > 0) {
1202 		int thisrblen = ie_buflen(sc, head) - thisrboff,
1203 		    thismblen = m->m_len - thismboff;
1204 		len = min(thisrblen, thismblen);
1205 
1206 		bcopy((caddr_t)(sc->cbuffs[head] + thisrboff),
1207 		    mtod(m, caddr_t) + thismboff, (u_int)len);
1208 		resid -= len;
1209 
1210 		if (len == thismblen) {
1211 			m = m->m_next;
1212 			thismboff = 0;
1213 		} else
1214 			thismboff += len;
1215 
1216 		if (len == thisrblen) {
1217 			head = (head + 1) % NRXBUF;
1218 			thisrboff = 0;
1219 		} else
1220 			thisrboff += len;
1221 	}
1222 
1223 	/*
1224 	 * Unless something changed strangely while we were doing the copy, we
1225 	 * have now copied everything in from the shared memory.
1226 	 * This means that we are done.
1227 	 */
1228 
1229 	if (top == NULL)
1230 		sc->sc_arpcom.ac_if.if_ierrors++;
1231 	return top;
1232 }
1233 
1234 /*
1235  * Read frame NUM from unit UNIT (pre-cached as IE).
1236  *
1237  * This routine reads the RFD at NUM, and copies in the buffers from the list
1238  * of RBD, then rotates the RBD and RFD lists so that the receiver doesn't
1239  * start complaining.  Trailers are DROPPED---there's no point in wasting time
1240  * on confusing code to deal with them.  Hopefully, this machine will never ARP
1241  * for trailers anyway.
1242  */
1243 void
ie_readframe(struct ie_softc * sc,int num)1244 ie_readframe(struct ie_softc *sc, int num)	/* frame number to read */
1245 {
1246 	int status;
1247 	struct mbuf *m = NULL;
1248 	struct mbuf_list ml = MBUF_LIST_INITIALIZER();
1249 	struct ether_header eh;
1250 
1251 	status = sc->rframes[num]->ie_fd_status;
1252 
1253 	/* Advance the RFD list, since we're done with this descriptor. */
1254 	sc->rframes[num]->ie_fd_status = 0;
1255 	sc->rframes[num]->ie_fd_last |= IE_FD_LAST;
1256 	sc->rframes[sc->rftail]->ie_fd_last &= ~IE_FD_LAST;
1257 	sc->rftail = (sc->rftail + 1) % NFRAMES;
1258 	sc->rfhead = (sc->rfhead + 1) % NFRAMES;
1259 
1260 	if (status & IE_FD_OK) {
1261 		m = ieget(sc, &eh);
1262 		ie_drop_packet_buffer(sc);
1263 	} else
1264 		sc->sc_arpcom.ac_if.if_ierrors++;
1265 	if (m == NULL)
1266 		return;
1267 
1268 #ifdef IEDEBUG
1269 	if (sc->sc_debug & IED_READFRAME)
1270 		printf("%s: frame from ether %s type %x\n", sc->sc_dev.dv_xname,
1271 		    ether_sprintf(eh.ether_shost), (u_int)eh.ether_type);
1272 #endif
1273 
1274 	ml_enqueue(&ml, m);
1275 	if_input(&sc->sc_arpcom.ac_if, &ml);
1276 }
1277 
1278 void
ie_drop_packet_buffer(struct ie_softc * sc)1279 ie_drop_packet_buffer(struct ie_softc *sc)
1280 {
1281 	int i;
1282 
1283 	do {
1284 		/*
1285 		 * This means we are somehow out of sync.  So, we reset the
1286 		 * adapter.
1287 		 */
1288 		if (!(sc->rbuffs[sc->rbhead]->ie_rbd_actual & IE_RBD_USED)) {
1289 #ifdef IEDEBUG
1290 			print_rbd(sc->rbuffs[sc->rbhead]);
1291 #endif
1292 			log(LOG_ERR, "%s: receive descriptors out of sync at %d\n",
1293 			    sc->sc_dev.dv_xname, sc->rbhead);
1294 			iereset(sc);
1295 			return;
1296 		}
1297 
1298 		i = sc->rbuffs[sc->rbhead]->ie_rbd_actual & IE_RBD_LAST;
1299 
1300 		sc->rbuffs[sc->rbhead]->ie_rbd_length |= IE_RBD_LAST;
1301 		sc->rbuffs[sc->rbhead]->ie_rbd_actual = 0;
1302 		sc->rbhead = (sc->rbhead + 1) % NRXBUF;
1303 		sc->rbuffs[sc->rbtail]->ie_rbd_length &= ~IE_RBD_LAST;
1304 		sc->rbtail = (sc->rbtail + 1) % NRXBUF;
1305 	} while (!i);
1306 }
1307 
1308 /*
1309  * Start transmission on an interface.
1310  */
1311 void
iestart(struct ifnet * ifp)1312 iestart(struct ifnet *ifp)
1313 {
1314 	struct ie_softc *sc = ifp->if_softc;
1315 	struct mbuf *m0, *m;
1316 	u_char *buffer;
1317 	u_short len;
1318 
1319 	if (!(ifp->if_flags & IFF_RUNNING) || ifq_is_oactive(&ifp->if_snd))
1320 		return;
1321 
1322 	for (;;) {
1323 		if (sc->xmit_busy == NTXBUF) {
1324 			ifq_set_oactive(&ifp->if_snd);
1325 			break;
1326 		}
1327 
1328 		m0 = ifq_dequeue(&ifp->if_snd);
1329 		if (m0 == NULL)
1330 			break;
1331 
1332 		/* We need to use m->m_pkthdr.len, so require the header */
1333 		if ((m0->m_flags & M_PKTHDR) == 0)
1334 			panic("iestart: no header mbuf");
1335 
1336 #if NBPFILTER > 0
1337 		/* Tap off here if there is a BPF listener. */
1338 		if (ifp->if_bpf)
1339 			bpf_mtap(ifp->if_bpf, m0, BPF_DIRECTION_OUT);
1340 #endif
1341 
1342 #ifdef IEDEBUG
1343 		if (sc->sc_debug & IED_ENQ)
1344 			printf("%s: fill buffer %d\n", sc->sc_dev.dv_xname,
1345 			    sc->xchead);
1346 #endif
1347 
1348 		len = 0;
1349 		buffer = sc->xmit_cbuffs[sc->xchead];
1350 
1351 		for (m = m0; m != NULL && (len + m->m_len) < IE_TBUF_SIZE;
1352 		    m = m->m_next) {
1353 			bcopy(mtod(m, caddr_t), buffer, m->m_len);
1354 			buffer += m->m_len;
1355 			len += m->m_len;
1356 		}
1357 		if (m != NULL)
1358 			printf("%s: tbuf overflow\n", sc->sc_dev.dv_xname);
1359 
1360 		m_freem(m0);
1361 
1362 		if (len < ETHER_MIN_LEN - ETHER_CRC_LEN) {
1363 			bzero(buffer, ETHER_MIN_LEN - ETHER_CRC_LEN - len);
1364 			len = ETHER_MIN_LEN - ETHER_CRC_LEN;
1365 			buffer += ETHER_MIN_LEN - ETHER_CRC_LEN;
1366 		}
1367 
1368 		sc->xmit_buffs[sc->xchead]->ie_xmit_flags = len;
1369 
1370 		/* Start the first packet transmitting. */
1371 		if (sc->xmit_busy == 0)
1372 			iexmit(sc);
1373 
1374 		sc->xchead = (sc->xchead + 1) % NTXBUF;
1375 		sc->xmit_busy++;
1376 	}
1377 }
1378 
1379 /*
1380  * Check to see if there's an 82586 out there.
1381  */
1382 int
check_ie_present(struct ie_softc * sc,caddr_t where,u_int size)1383 check_ie_present(struct ie_softc *sc, caddr_t where, u_int size)
1384 {
1385 	volatile struct ie_sys_conf_ptr *scp;
1386 	volatile struct ie_int_sys_conf_ptr *iscp;
1387 	volatile struct ie_sys_ctl_block *scb;
1388 	u_long realbase;
1389 	int s;
1390 
1391 	s = splnet();
1392 
1393 	realbase = (u_long)where + size - (1 << 24);
1394 
1395 	scp = (volatile struct ie_sys_conf_ptr *)(realbase + IE_SCP_ADDR);
1396 	bzero((char *)scp, sizeof *scp);
1397 
1398 	/*
1399 	 * First we put the ISCP at the bottom of memory; this tests to make
1400 	 * sure that our idea of the size of memory is the same as the
1401 	 * controller's.  This is NOT where the ISCP will be in normal
1402 	 * operation.
1403 	 */
1404 	iscp = (volatile struct ie_int_sys_conf_ptr *)where;
1405 	bzero((char *)iscp, sizeof *iscp);
1406 
1407 	scb = (volatile struct ie_sys_ctl_block *)where;
1408 	bzero((char *)scb, sizeof *scb);
1409 
1410 	scp->ie_bus_use = 0;		/* 16-bit */
1411 	scp->ie_iscp_ptr = (caddr_t)((volatile caddr_t)iscp -
1412 	    (volatile caddr_t)realbase);
1413 
1414 	iscp->ie_busy = 1;
1415 	iscp->ie_scb_offset = MK_16(realbase, scb) + 256;
1416 
1417 	(sc->reset_586)(sc);
1418 	(sc->chan_attn)(sc);
1419 
1420 	delay(100);			/* wait a while... */
1421 
1422 	if (iscp->ie_busy) {
1423 		splx(s);
1424 		return 0;
1425 	}
1426 
1427 	/*
1428 	 * Now relocate the ISCP to its real home, and reset the controller
1429 	 * again.
1430 	 */
1431 	iscp = (void *)ALIGN(realbase + IE_SCP_ADDR - sizeof(*iscp));
1432 	bzero((char *)iscp, sizeof *iscp);
1433 
1434 	scp->ie_iscp_ptr = (caddr_t)((caddr_t)iscp - (caddr_t)realbase);
1435 
1436 	iscp->ie_busy = 1;
1437 	iscp->ie_scb_offset = MK_16(realbase, scb);
1438 
1439 	(sc->reset_586)(sc);
1440 	(sc->chan_attn)(sc);
1441 
1442 	delay(100);
1443 
1444 	if (iscp->ie_busy) {
1445 		splx(s);
1446 		return 0;
1447 	}
1448 
1449 	sc->sc_msize = size;
1450 	sc->sc_maddr = (caddr_t)realbase;
1451 
1452 	sc->iscp = iscp;
1453 	sc->scb = scb;
1454 
1455 	/*
1456 	 * Acknowledge any interrupts we may have caused...
1457 	 */
1458 	ie_ack(sc, IE_ST_WHENCE);
1459 	splx(s);
1460 
1461 	return 1;
1462 }
1463 
1464 /*
1465  * Divine the memory size of ie board UNIT.
1466  * Better hope there's nothing important hiding just below the ie card...
1467  */
1468 void
ie_find_mem_size(struct ie_softc * sc)1469 ie_find_mem_size(struct ie_softc *sc)
1470 {
1471 	u_int size;
1472 
1473 	sc->sc_msize = 0;
1474 
1475 	for (size = 65536; size >= 16384; size -= 16384)
1476 		if (check_ie_present(sc, sc->sc_maddr, size))
1477 			return;
1478 
1479 	return;
1480 }
1481 
1482 void
el_reset_586(struct ie_softc * sc)1483 el_reset_586(struct ie_softc *sc)
1484 {
1485 
1486 	outb(PORT + IE507_CTRL, EL_CTRL_RESET);
1487 	delay(100);
1488 	outb(PORT + IE507_CTRL, EL_CTRL_NORMAL);
1489 	delay(100);
1490 }
1491 
1492 void
sl_reset_586(struct ie_softc * sc)1493 sl_reset_586(struct ie_softc *sc)
1494 {
1495 
1496 	outb(PORT + IEATT_RESET, 0);
1497 }
1498 
1499 void
ee16_reset_586(struct ie_softc * sc)1500 ee16_reset_586(struct ie_softc *sc)
1501 {
1502 
1503 	outb(PORT + IEE16_ECTRL, IEE16_RESET_586);
1504 	delay(100);
1505 	outb(PORT + IEE16_ECTRL, 0);
1506 	delay(100);
1507 }
1508 
1509 void
el_chan_attn(struct ie_softc * sc)1510 el_chan_attn(struct ie_softc *sc)
1511 {
1512 
1513 	outb(PORT + IE507_ATTN, 1);
1514 }
1515 
1516 void
sl_chan_attn(struct ie_softc * sc)1517 sl_chan_attn(struct ie_softc *sc)
1518 {
1519 
1520 	outb(PORT + IEATT_ATTN, 0);
1521 }
1522 
1523 void
ee16_chan_attn(struct ie_softc * sc)1524 ee16_chan_attn(struct ie_softc *sc)
1525 {
1526 	outb(PORT + IEE16_ATTN, 0);
1527 }
1528 
1529 u_short
ee16_read_eeprom(struct ie_softc * sc,int location)1530 ee16_read_eeprom(struct ie_softc *sc, int location)
1531 {
1532 	int ectrl, edata;
1533 
1534 	ectrl = inb(PORT + IEE16_ECTRL);
1535 	ectrl &= IEE16_ECTRL_MASK;
1536 	ectrl |= IEE16_ECTRL_EECS;
1537 	outb(PORT + IEE16_ECTRL, ectrl);
1538 
1539 	ee16_eeprom_outbits(sc, IEE16_EEPROM_READ, IEE16_EEPROM_OPSIZE1);
1540 	ee16_eeprom_outbits(sc, location, IEE16_EEPROM_ADDR_SIZE);
1541 	edata = ee16_eeprom_inbits(sc);
1542 	ectrl = inb(PORT + IEE16_ECTRL);
1543 	ectrl &= ~(IEE16_RESET_ASIC | IEE16_ECTRL_EEDI | IEE16_ECTRL_EECS);
1544 	outb(PORT + IEE16_ECTRL, ectrl);
1545 	ee16_eeprom_clock(sc, 1);
1546 	ee16_eeprom_clock(sc, 0);
1547 	return edata;
1548 }
1549 
1550 void
ee16_eeprom_outbits(struct ie_softc * sc,int edata,int count)1551 ee16_eeprom_outbits(struct ie_softc *sc, int edata, int count)
1552 {
1553 	int ectrl, i;
1554 
1555 	ectrl = inb(PORT + IEE16_ECTRL);
1556 	ectrl &= ~IEE16_RESET_ASIC;
1557 	for (i = count - 1; i >= 0; i--) {
1558 		ectrl &= ~IEE16_ECTRL_EEDI;
1559 		if (edata & (1 << i)) {
1560 			ectrl |= IEE16_ECTRL_EEDI;
1561 		}
1562 		outb(PORT + IEE16_ECTRL, ectrl);
1563 		delay(1);	/* eeprom data must be setup for 0.4 uSec */
1564 		ee16_eeprom_clock(sc, 1);
1565 		ee16_eeprom_clock(sc, 0);
1566 	}
1567 	ectrl &= ~IEE16_ECTRL_EEDI;
1568 	outb(PORT + IEE16_ECTRL, ectrl);
1569 	delay(1);		/* eeprom data must be held for 0.4 uSec */
1570 }
1571 
1572 int
ee16_eeprom_inbits(struct ie_softc * sc)1573 ee16_eeprom_inbits(struct ie_softc *sc)
1574 {
1575 	int ectrl, edata, i;
1576 
1577 	ectrl = inb(PORT + IEE16_ECTRL);
1578 	ectrl &= ~IEE16_RESET_ASIC;
1579 	for (edata = 0, i = 0; i < 16; i++) {
1580 		edata = edata << 1;
1581 		ee16_eeprom_clock(sc, 1);
1582 		ectrl = inb(PORT + IEE16_ECTRL);
1583 		if (ectrl & IEE16_ECTRL_EEDO) {
1584 			edata |= 1;
1585 		}
1586 		ee16_eeprom_clock(sc, 0);
1587 	}
1588 	return (edata);
1589 }
1590 
1591 void
ee16_eeprom_clock(struct ie_softc * sc,int state)1592 ee16_eeprom_clock(struct ie_softc *sc, int state)
1593 {
1594 	int ectrl;
1595 
1596 	ectrl = inb(PORT + IEE16_ECTRL);
1597 	ectrl &= ~(IEE16_RESET_ASIC | IEE16_ECTRL_EESK);
1598 	if (state) {
1599 		ectrl |= IEE16_ECTRL_EESK;
1600 	}
1601 	outb(PORT + IEE16_ECTRL, ectrl);
1602 	delay(9);		/* EESK must be stable for 8.38 uSec */
1603 }
1604 
1605 static inline void
ee16_interrupt_enable(struct ie_softc * sc)1606 ee16_interrupt_enable(struct ie_softc *sc)
1607 {
1608 	delay(100);
1609 	outb(PORT + IEE16_IRQ, sc->irq_encoded | IEE16_IRQ_ENABLE);
1610 	delay(100);
1611 }
1612 
1613 void
slel_get_address(struct ie_softc * sc)1614 slel_get_address(struct ie_softc *sc)
1615 {
1616 	u_char *addr = sc->sc_arpcom.ac_enaddr;
1617 	int i;
1618 
1619 	for (i = 0; i < ETHER_ADDR_LEN; i++)
1620 		addr[i] = inb(PORT + i);
1621 }
1622 
1623 void
iereset(struct ie_softc * sc)1624 iereset(struct ie_softc *sc)
1625 {
1626 	int s = splnet();
1627 
1628 	iestop(sc);
1629 
1630 	/*
1631 	 * Stop i82586 dead in its tracks.
1632 	 */
1633 	if (command_and_wait(sc, IE_RU_ABORT | IE_CU_ABORT, 0, 0))
1634 		printf("%s: abort commands timed out\n", sc->sc_dev.dv_xname);
1635 
1636 	if (command_and_wait(sc, IE_RU_DISABLE | IE_CU_STOP, 0, 0))
1637 		printf("%s: disable commands timed out\n", sc->sc_dev.dv_xname);
1638 
1639 	ieinit(sc);
1640 
1641 	splx(s);
1642 }
1643 
1644 /*
1645  * Send a command to the controller and wait for it to either complete or be
1646  * accepted, depending on the command.  If the command pointer is null, then
1647  * pretend that the command is not an action command.  If the command pointer
1648  * is not null, and the command is an action command, wait for
1649  * ((volatile struct ie_cmd_common *)pcmd)->ie_cmd_status & MASK
1650  * to become true.
1651  */
1652 static int
command_and_wait(struct ie_softc * sc,int cmd,volatile void * pcmd,int mask)1653 command_and_wait(struct ie_softc *sc, int cmd, volatile void *pcmd, int mask)
1654 {
1655 	volatile struct ie_cmd_common *cc = pcmd;
1656 	volatile struct ie_sys_ctl_block *scb = sc->scb;
1657 	int i;
1658 
1659 	scb->ie_command = (u_short)cmd;
1660 
1661 	if (IE_ACTION_COMMAND(cmd) && pcmd) {
1662 		(sc->chan_attn)(sc);
1663 
1664 		/*
1665 		 * According to the packet driver, the minimum timeout should
1666 		 * be .369 seconds, which we round up to .4.
1667 		 *
1668 		 * Now spin-lock waiting for status.  This is not a very nice
1669 		 * thing to do, but I haven't figured out how, or indeed if, we
1670 		 * can put the process waiting for action to sleep.  (We may
1671 		 * be getting called through some other timeout running in the
1672 		 * kernel.)
1673 		 */
1674 		for (i = 36900; i--; DELAY(10))
1675 			if ((cc->ie_cmd_status & mask))
1676 				break;
1677 
1678 		return i < 0;
1679 	} else {
1680 		/*
1681 		 * Otherwise, just wait for the command to be accepted.
1682 		 */
1683 		(sc->chan_attn)(sc);
1684 
1685 		while (scb->ie_command)
1686 			;				/* spin lock */
1687 
1688 		return 0;
1689 	}
1690 }
1691 
1692 /*
1693  * Run the time-domain reflectometer.
1694  */
1695 static void
run_tdr(struct ie_softc * sc,struct ie_tdr_cmd * cmd)1696 run_tdr(struct ie_softc *sc, struct ie_tdr_cmd *cmd)
1697 {
1698 	int result;
1699 
1700 	cmd->com.ie_cmd_status = 0;
1701 	cmd->com.ie_cmd_cmd = IE_CMD_TDR | IE_CMD_LAST;
1702 	cmd->com.ie_cmd_link = 0xffff;
1703 
1704 	sc->scb->ie_command_list = MK_16(MEM, cmd);
1705 	cmd->ie_tdr_time = 0;
1706 
1707 	if (command_and_wait(sc, IE_CU_START, cmd, IE_STAT_COMPL) ||
1708 	    !(cmd->com.ie_cmd_status & IE_STAT_OK))
1709 		result = 0x10000;
1710 	else
1711 		result = cmd->ie_tdr_time;
1712 
1713 	ie_ack(sc, IE_ST_WHENCE);
1714 
1715 	if (result & IE_TDR_SUCCESS)
1716 		return;
1717 
1718 	if (result & 0x10000)
1719 		printf("%s: TDR command failed\n", sc->sc_dev.dv_xname);
1720 	else if (result & IE_TDR_XCVR)
1721 		printf("%s: transceiver problem\n", sc->sc_dev.dv_xname);
1722 	else if (result & IE_TDR_OPEN)
1723 		printf("%s: TDR detected an open %d clocks away\n",
1724 		    sc->sc_dev.dv_xname, result & IE_TDR_TIME);
1725 	else if (result & IE_TDR_SHORT)
1726 		printf("%s: TDR detected a short %d clocks away\n",
1727 		    sc->sc_dev.dv_xname, result & IE_TDR_TIME);
1728 	else
1729 		printf("%s: TDR returned unknown status %x\n",
1730 		    sc->sc_dev.dv_xname, result);
1731 }
1732 
1733 #define	_ALLOC(p, n)	(bzero(p, n), p += n, p - n)
1734 #define	ALLOC(p, n)	_ALLOC(p, ALIGN(n))
1735 
1736 /*
1737  * Here is a helper routine for ieinit().  This sets up the buffers.
1738  */
1739 void
iememinit(void * ptr,struct ie_softc * sc)1740 iememinit(void *ptr, struct ie_softc *sc)
1741 {
1742 	int i;
1743 
1744 	/* First lay them out. */
1745 	for (i = 0; i < NFRAMES; i++)
1746 		sc->rframes[i] = ALLOC(ptr, sizeof(*sc->rframes[i]));
1747 
1748 	/* Now link them together. */
1749 	for (i = 0; i < NFRAMES; i++)
1750 		sc->rframes[i]->ie_fd_next =
1751 		    MK_16(MEM, sc->rframes[(i + 1) % NFRAMES]);
1752 
1753 	/* Finally, set the EOL bit on the last one. */
1754 	sc->rframes[NFRAMES - 1]->ie_fd_last |= IE_FD_LAST;
1755 
1756 	/*
1757 	 * Now lay out some buffers for the incoming frames.  Note that we set
1758 	 * aside a bit of slop in each buffer, to make sure that we have enough
1759 	 * space to hold a single frame in every buffer.
1760 	 */
1761 	for (i = 0; i < NRXBUF; i++) {
1762 		sc->rbuffs[i] = ALLOC(ptr, sizeof(*sc->rbuffs[i]));
1763 		sc->rbuffs[i]->ie_rbd_length = IE_RBUF_SIZE;
1764 		sc->rbuffs[i]->ie_rbd_buffer = MK_24(MEM, ptr);
1765 		sc->cbuffs[i] = ALLOC(ptr, IE_RBUF_SIZE);
1766 	}
1767 
1768 	/* Now link them together. */
1769 	for (i = 0; i < NRXBUF; i++)
1770 		sc->rbuffs[i]->ie_rbd_next =
1771 		    MK_16(MEM, sc->rbuffs[(i + 1) % NRXBUF]);
1772 
1773 	/* Tag EOF on the last one. */
1774 	sc->rbuffs[NRXBUF - 1]->ie_rbd_length |= IE_RBD_LAST;
1775 
1776 	/*
1777 	 * We use the head and tail pointers on receive to keep track of the
1778 	 * order in which RFDs and RBDs are used.
1779 	 */
1780 	sc->rfhead = 0;
1781 	sc->rftail = NFRAMES - 1;
1782 	sc->rbhead = 0;
1783 	sc->rbtail = NRXBUF - 1;
1784 
1785 	sc->scb->ie_recv_list = MK_16(MEM, sc->rframes[0]);
1786 	sc->rframes[0]->ie_fd_buf_desc = MK_16(MEM, sc->rbuffs[0]);
1787 
1788 	/*
1789 	 * Finally, the transmit command and buffer are the last little bit of
1790 	 * work.
1791 	 */
1792 	for (i = 0; i < NTXBUF; i++) {
1793 		sc->xmit_cmds[i] = ALLOC(ptr, sizeof(*sc->xmit_cmds[i]));
1794 		sc->xmit_buffs[i] = ALLOC(ptr, sizeof(*sc->xmit_buffs[i]));
1795 	}
1796 
1797 	for (i = 0; i < NTXBUF; i++)
1798 		sc->xmit_cbuffs[i] = ALLOC(ptr, IE_TBUF_SIZE);
1799 
1800 	/* Pointers to last packet sent and next available transmit buffer. */
1801 	sc->xchead = sc->xctail = 0;
1802 
1803 	/* Clear transmit-busy flag and set number of free transmit buffers. */
1804 	sc->xmit_busy = 0;
1805 }
1806 
1807 /*
1808  * Run the multicast setup command.
1809  * Called at splnet().
1810  */
1811 static int
mc_setup(struct ie_softc * sc,void * ptr)1812 mc_setup(struct ie_softc *sc, void *ptr)
1813 {
1814 	volatile struct ie_mcast_cmd *cmd = ptr;
1815 
1816 	cmd->com.ie_cmd_status = 0;
1817 	cmd->com.ie_cmd_cmd = IE_CMD_MCAST | IE_CMD_LAST;
1818 	cmd->com.ie_cmd_link = 0xffff;
1819 
1820 	bcopy((caddr_t)sc->mcast_addrs, (caddr_t)cmd->ie_mcast_addrs,
1821 	    sc->mcast_count * sizeof *sc->mcast_addrs);
1822 
1823 	cmd->ie_mcast_bytes = sc->mcast_count * ETHER_ADDR_LEN; /* grrr... */
1824 
1825 	sc->scb->ie_command_list = MK_16(MEM, cmd);
1826 	if (command_and_wait(sc, IE_CU_START, cmd, IE_STAT_COMPL) ||
1827 	    !(cmd->com.ie_cmd_status & IE_STAT_OK)) {
1828 		printf("%s: multicast address setup command failed\n",
1829 		    sc->sc_dev.dv_xname);
1830 		return 0;
1831 	}
1832 	return 1;
1833 }
1834 
1835 /*
1836  * This routine takes the environment generated by check_ie_present() and adds
1837  * to it all the other structures we need to operate the adapter.  This
1838  * includes executing the CONFIGURE, IA-SETUP, and MC-SETUP commands, starting
1839  * the receiver unit, and clearing interrupts.
1840  *
1841  * THIS ROUTINE MUST BE CALLED AT splnet() OR HIGHER.
1842  */
1843 int
ieinit(struct ie_softc * sc)1844 ieinit(struct ie_softc *sc)
1845 {
1846 	volatile struct ie_sys_ctl_block *scb = sc->scb;
1847 	void *ptr;
1848 
1849 	ptr = (void *)ALIGN(scb + 1);
1850 
1851 	/*
1852 	 * Send the configure command first.
1853 	 */
1854 	{
1855 		volatile struct ie_config_cmd *cmd = ptr;
1856 
1857 		scb->ie_command_list = MK_16(MEM, cmd);
1858 		cmd->com.ie_cmd_status = 0;
1859 		cmd->com.ie_cmd_cmd = IE_CMD_CONFIG | IE_CMD_LAST;
1860 		cmd->com.ie_cmd_link = 0xffff;
1861 
1862 		ie_setup_config(cmd, sc->promisc != 0,
1863 		    sc->hard_type == IE_STARLAN10);
1864 
1865 		if (command_and_wait(sc, IE_CU_START, cmd, IE_STAT_COMPL) ||
1866 		    !(cmd->com.ie_cmd_status & IE_STAT_OK)) {
1867 			printf("%s: configure command failed\n",
1868 			    sc->sc_dev.dv_xname);
1869 			return 0;
1870 		}
1871 	}
1872 
1873 	/*
1874 	 * Now send the Individual Address Setup command.
1875 	 */
1876 	{
1877 		volatile struct ie_iasetup_cmd *cmd = ptr;
1878 
1879 		scb->ie_command_list = MK_16(MEM, cmd);
1880 		cmd->com.ie_cmd_status = 0;
1881 		cmd->com.ie_cmd_cmd = IE_CMD_IASETUP | IE_CMD_LAST;
1882 		cmd->com.ie_cmd_link = 0xffff;
1883 
1884 		bcopy(sc->sc_arpcom.ac_enaddr, (caddr_t)&cmd->ie_address,
1885 		    sizeof cmd->ie_address);
1886 
1887 		if (command_and_wait(sc, IE_CU_START, cmd, IE_STAT_COMPL) ||
1888 		    !(cmd->com.ie_cmd_status & IE_STAT_OK)) {
1889 			printf("%s: individual address setup command failed\n",
1890 			    sc->sc_dev.dv_xname);
1891 			return 0;
1892 		}
1893 	}
1894 
1895 	/*
1896 	 * Now run the time-domain reflectometer.
1897 	 */
1898 	run_tdr(sc, ptr);
1899 
1900 	/*
1901 	 * Acknowledge any interrupts we have generated thus far.
1902 	 */
1903 	ie_ack(sc, IE_ST_WHENCE);
1904 
1905 	/*
1906 	 * Set up the RFA.
1907 	 */
1908 	iememinit(ptr, sc);
1909 
1910 	sc->sc_arpcom.ac_if.if_flags |= IFF_RUNNING;
1911 	ifq_clr_oactive(&sc->sc_arpcom.ac_if.if_snd);
1912 
1913 	sc->scb->ie_recv_list = MK_16(MEM, sc->rframes[0]);
1914 	command_and_wait(sc, IE_RU_START, 0, 0);
1915 
1916 	ie_ack(sc, IE_ST_WHENCE);
1917 
1918 	/* take the ee16 out of loopback */
1919 	{
1920 	u_char	bart_config;
1921 
1922 	if(sc->hard_type == IE_EE16) {
1923 		bart_config = inb(PORT + IEE16_CONFIG);
1924 		bart_config &= ~IEE16_BART_LOOPBACK;
1925 		bart_config |= IEE16_BART_MCS16_TEST; /* inb doesn't get bit! */
1926 		outb(PORT + IEE16_CONFIG, bart_config);
1927 		ee16_interrupt_enable(sc);
1928 		ee16_chan_attn(sc);
1929 		}
1930 	}
1931 	return 0;
1932 }
1933 
1934 void
iestop(struct ie_softc * sc)1935 iestop(struct ie_softc *sc)
1936 {
1937 
1938 	command_and_wait(sc, IE_RU_DISABLE, 0, 0);
1939 }
1940 
1941 int
ieioctl(struct ifnet * ifp,u_long cmd,caddr_t data)1942 ieioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
1943 {
1944 	struct ie_softc *sc = ifp->if_softc;
1945 	int s, error = 0;
1946 
1947 	s = splnet();
1948 
1949 	switch (cmd) {
1950 	case SIOCSIFADDR:
1951 		ifp->if_flags |= IFF_UP;
1952 		ieinit(sc);
1953 		break;
1954 
1955 	case SIOCSIFFLAGS:
1956 		sc->promisc = ifp->if_flags & (IFF_PROMISC | IFF_ALLMULTI);
1957 		if ((ifp->if_flags & IFF_UP) == 0 &&
1958 		    (ifp->if_flags & IFF_RUNNING) != 0) {
1959 			/*
1960 			 * If interface is marked down and it is running, then
1961 			 * stop it.
1962 			 */
1963 			iestop(sc);
1964 			ifp->if_flags &= ~IFF_RUNNING;
1965 		} else if ((ifp->if_flags & IFF_UP) != 0 &&
1966 			   (ifp->if_flags & IFF_RUNNING) == 0) {
1967 			/*
1968 			 * If interface is marked up and it is stopped, then
1969 			 * start it.
1970 			 */
1971 			ieinit(sc);
1972 		} else {
1973 			/*
1974 			 * Reset the interface to pick up changes in any other
1975 			 * flags that affect hardware registers.
1976 			 */
1977 			iestop(sc);
1978 			ieinit(sc);
1979 		}
1980 #ifdef IEDEBUG
1981 		if (ifp->if_flags & IFF_DEBUG)
1982 			sc->sc_debug = IED_ALL;
1983 		else
1984 			sc->sc_debug = 0;
1985 #endif
1986 		break;
1987 
1988 	default:
1989 		error = ether_ioctl(ifp, &sc->sc_arpcom, cmd, data);
1990 	}
1991 
1992 	if (error == ENETRESET) {
1993 		if (ifp->if_flags & IFF_RUNNING)
1994 			mc_reset(sc);
1995 		error = 0;
1996 	}
1997 
1998 	splx(s);
1999 	return error;
2000 }
2001 
2002 static void
mc_reset(struct ie_softc * sc)2003 mc_reset(struct ie_softc *sc)
2004 {
2005 	struct arpcom *ac = &sc->sc_arpcom;
2006 	struct ether_multi *enm;
2007 	struct ether_multistep step;
2008 
2009 	if (ac->ac_multirangecnt > 0) {
2010 		ac->ac_if.if_flags |= IFF_ALLMULTI;
2011 		ieioctl(&ac->ac_if, SIOCSIFFLAGS, NULL);
2012 		goto setflag;
2013 	}
2014 	/*
2015 	 * Step through the list of addresses.
2016 	 */
2017 	sc->mcast_count = 0;
2018 	ETHER_FIRST_MULTI(step, ac, enm);
2019 	while (enm) {
2020 		if (sc->mcast_count >= MAXMCAST) {
2021 			ac->ac_if.if_flags |= IFF_ALLMULTI;
2022 			ieioctl(&ac->ac_if, SIOCSIFFLAGS, NULL);
2023 			goto setflag;
2024 		}
2025 
2026 		bcopy(enm->enm_addrlo, &sc->mcast_addrs[sc->mcast_count], 6);
2027 		sc->mcast_count++;
2028 		ETHER_NEXT_MULTI(step, enm);
2029 	}
2030 setflag:
2031 	sc->want_mcsetup = 1;
2032 }
2033 
2034 #ifdef IEDEBUG
2035 void
print_rbd(volatile struct ie_recv_buf_desc * rbd)2036 print_rbd(volatile struct ie_recv_buf_desc *rbd)
2037 {
2038 
2039 	printf("RBD at %08lx:\nactual %04x, next %04x, buffer %08x\n"
2040 	    "length %04x, mbz %04x\n", (u_long)rbd, rbd->ie_rbd_actual,
2041 	    rbd->ie_rbd_next, rbd->ie_rbd_buffer, rbd->ie_rbd_length,
2042 	    rbd->mbz);
2043 }
2044 #endif
2045