i82586.c revision 1.61 1 /* $NetBSD: i82586.c,v 1.61 2008/04/08 12:07:26 cegger Exp $ */
2
3 /*-
4 * Copyright (c) 1998 The NetBSD Foundation, Inc.
5 * All rights reserved.
6 *
7 * This code is derived from software contributed to The NetBSD Foundation
8 * by Paul Kranenburg and Charles M. Hannum.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
18 * 3. All advertising materials mentioning features or use of this software
19 * must display the following acknowledgement:
20 * This product includes software developed by the NetBSD
21 * Foundation, Inc. and its contributors.
22 * 4. Neither the name of The NetBSD Foundation nor the names of its
23 * contributors may be used to endorse or promote products derived
24 * from this software without specific prior written permission.
25 *
26 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
27 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
28 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
29 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
30 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
31 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
32 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
33 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
34 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
35 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
36 * POSSIBILITY OF SUCH DAMAGE.
37 */
38
39 /*-
40 * Copyright (c) 1997 Paul Kranenburg.
41 * Copyright (c) 1992, 1993, University of Vermont and State
42 * Agricultural College.
43 * Copyright (c) 1992, 1993, Garrett A. Wollman.
44 *
45 * Portions:
46 * Copyright (c) 1994, 1995, Rafal K. Boni
47 * Copyright (c) 1990, 1991, William F. Jolitz
48 * Copyright (c) 1990, The Regents of the University of California
49 *
50 * All rights reserved.
51 *
52 * Redistribution and use in source and binary forms, with or without
53 * modification, are permitted provided that the following conditions
54 * are met:
55 * 1. Redistributions of source code must retain the above copyright
56 * notice, this list of conditions and the following disclaimer.
57 * 2. Redistributions in binary form must reproduce the above copyright
58 * notice, this list of conditions and the following disclaimer in the
59 * documentation and/or other materials provided with the distribution.
60 * 3. All advertising materials mentioning features or use of this software
61 * must display the following acknowledgement:
62 * This product includes software developed by the University of Vermont
63 * and State Agricultural College and Garrett A. Wollman, by William F.
64 * Jolitz, and by the University of California, Berkeley, Lawrence
65 * Berkeley Laboratory, and its contributors.
66 * 4. Neither the names of the Universities nor the names of the authors
67 * may be used to endorse or promote products derived from this software
68 * without specific prior written permission.
69 *
70 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
71 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
72 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
73 * ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR AUTHORS BE LIABLE
74 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
75 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
76 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
77 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
78 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
79 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
80 * SUCH DAMAGE.
81 */
82
83 /*
84 * Intel 82586 Ethernet chip
85 * Register, bit, and structure definitions.
86 *
87 * Original StarLAN driver written by Garrett Wollman with reference to the
88 * Clarkson Packet Driver code for this chip written by Russ Nelson and others.
89 *
90 * BPF support code taken from hpdev/if_le.c, supplied with tcpdump.
91 *
92 * 3C507 support is loosely based on code donated to NetBSD by Rafal Boni.
93 *
94 * Majorly cleaned up and 3C507 code merged by Charles Hannum.
95 *
96 * Converted to SUN ie driver by Charles D. Cranor,
97 * October 1994, January 1995.
98 * This sun version based on i386 version 1.30.
99 */
100
101 /*
102 * The i82586 is a very painful chip, found in sun3's, sun-4/100's
103 * sun-4/200's, and VME based suns. The byte order is all wrong for a
104 * SUN, making life difficult. Programming this chip is mostly the same,
105 * but certain details differ from system to system. This driver is
106 * written so that different "ie" interfaces can be controled by the same
107 * driver.
108 */
109
110 /*
111 Mode of operation:
112
113 We run the 82586 in a standard Ethernet mode. We keep NFRAMES
114 received frame descriptors around for the receiver to use, and
115 NRXBUF associated receive buffer descriptors, both in a circular
116 list. Whenever a frame is received, we rotate both lists as
117 necessary. (The 586 treats both lists as a simple queue.) We also
118 keep a transmit command around so that packets can be sent off
119 quickly.
120
121 We configure the adapter in AL-LOC = 1 mode, which means that the
122 Ethernet/802.3 MAC header is placed at the beginning of the receive
123 buffer rather than being split off into various fields in the RFD.
124 This also means that we must include this header in the transmit
125 buffer as well.
126
127 By convention, all transmit commands, and only transmit commands,
128 shall have the I (IE_CMD_INTR) bit set in the command. This way,
129 when an interrupt arrives at i82586_intr(), it is immediately possible
130 to tell what precisely caused it. ANY OTHER command-sending
131 routines should run at splnet(), and should post an acknowledgement
132 to every interrupt they generate.
133
134 To save the expense of shipping a command to 82586 every time we
135 want to send a frame, we use a linked list of commands consisting
136 of alternate XMIT and NOP commands. The links of these elements
137 are manipulated (in iexmit()) such that the NOP command loops back
138 to itself whenever the following XMIT command is not yet ready to
139 go. Whenever an XMIT is ready, the preceding NOP link is pointed
140 at it, while its own link field points to the following NOP command.
141 Thus, a single transmit command sets off an interlocked traversal
142 of the xmit command chain, with the host processor in control of
143 the synchronization.
144 */
145
146 #include <sys/cdefs.h>
147 __KERNEL_RCSID(0, "$NetBSD: i82586.c,v 1.61 2008/04/08 12:07:26 cegger Exp $");
148
149 #include "bpfilter.h"
150
151 #include <sys/param.h>
152 #include <sys/systm.h>
153 #include <sys/mbuf.h>
154 #include <sys/socket.h>
155 #include <sys/ioctl.h>
156 #include <sys/errno.h>
157 #include <sys/syslog.h>
158 #include <sys/device.h>
159
160 #include <net/if.h>
161 #include <net/if_dl.h>
162 #include <net/if_types.h>
163 #include <net/if_media.h>
164 #include <net/if_ether.h>
165
166 #if NBPFILTER > 0
167 #include <net/bpf.h>
168 #include <net/bpfdesc.h>
169 #endif
170
171 #include <sys/bus.h>
172
173 #include <dev/ic/i82586reg.h>
174 #include <dev/ic/i82586var.h>
175
176 void i82586_reset(struct ie_softc *, int);
177 void i82586_watchdog(struct ifnet *);
178 int i82586_init(struct ifnet *);
179 int i82586_ioctl(struct ifnet *, u_long, void *);
180 void i82586_start(struct ifnet *);
181 void i82586_stop(struct ifnet *, int);
182
183
184 int i82586_rint(struct ie_softc *, int);
185 int i82586_tint(struct ie_softc *, int);
186
187 int i82586_mediachange(struct ifnet *);
188 void i82586_mediastatus(struct ifnet *, struct ifmediareq *);
189
190 static int ie_readframe(struct ie_softc *, int);
191 static struct mbuf *ieget(struct ie_softc *, int, int);
192 static int i82586_get_rbd_list(struct ie_softc *,
193 u_int16_t *, u_int16_t *, int *);
194 static void i82586_release_rbd_list(struct ie_softc *,
195 u_int16_t, u_int16_t);
196 static int i82586_drop_frames(struct ie_softc *);
197 static int i82586_chk_rx_ring(struct ie_softc *);
198
199 static inline void ie_ack(struct ie_softc *, u_int);
200 static inline void iexmit(struct ie_softc *);
201 static void i82586_start_transceiver(struct ie_softc *);
202
203 static void i82586_count_errors(struct ie_softc *);
204 static void i82586_rx_errors(struct ie_softc *, int, int);
205 static void i82586_setup_bufs(struct ie_softc *);
206 static void setup_simple_command(struct ie_softc *, int, int);
207 static int ie_cfg_setup(struct ie_softc *, int, int, int);
208 static int ie_ia_setup(struct ie_softc *, int);
209 static void ie_run_tdr(struct ie_softc *, int);
210 static int ie_mc_setup(struct ie_softc *, int);
211 static void ie_mc_reset(struct ie_softc *);
212 static int i82586_start_cmd(struct ie_softc *, int, int, int, int);
213 static int i82586_cmd_wait(struct ie_softc *);
214
215 #if I82586_DEBUG
216 void print_rbd(struct ie_softc *, int);
217 #endif
218
219 static char* padbuf = NULL;
220
221 /*
222 * Front-ends call this function to attach to the MI driver.
223 *
224 * The front-end has responsibility for managing the ICP and ISCP
225 * structures. Both of these are opaque to us. Also, the front-end
226 * chooses a location for the SCB which is expected to be addressable
227 * (through `sc->scb') as an offset against the shared-memory bus handle.
228 *
229 * The following MD interface function must be setup by the front-end
230 * before calling here:
231 *
232 * hwreset - board dependent reset
233 * hwinit - board dependent initialization
234 * chan_attn - channel attention
235 * intrhook - board dependent interrupt processing
236 * memcopyin - shared memory copy: board to KVA
237 * memcopyout - shared memory copy: KVA to board
238 * ie_bus_read16 - read a sixteen-bit i82586 pointer
239 * ie_bus_write16 - write a sixteen-bit i82586 pointer
240 * ie_bus_write24 - write a twenty-four-bit i82586 pointer
241 *
242 */
243 void
244 i82586_attach(sc, name, etheraddr, media, nmedia, defmedia)
245 struct ie_softc *sc;
246 const char *name;
247 u_int8_t *etheraddr;
248 int *media, nmedia, defmedia;
249 {
250 int i;
251 struct ifnet *ifp = &sc->sc_ethercom.ec_if;
252
253 strlcpy(ifp->if_xname, device_xname(&sc->sc_dev), IFNAMSIZ);
254 ifp->if_softc = sc;
255 ifp->if_start = i82586_start;
256 ifp->if_ioctl = i82586_ioctl;
257 ifp->if_init = i82586_init;
258 ifp->if_stop = i82586_stop;
259 ifp->if_watchdog = i82586_watchdog;
260 ifp->if_flags =
261 IFF_BROADCAST | IFF_SIMPLEX | IFF_NOTRAILERS | IFF_MULTICAST;
262 IFQ_SET_READY(&ifp->if_snd);
263
264 /* Initialize media goo. */
265 ifmedia_init(&sc->sc_media, 0, i82586_mediachange, i82586_mediastatus);
266 if (media != NULL) {
267 for (i = 0; i < nmedia; i++)
268 ifmedia_add(&sc->sc_media, media[i], 0, NULL);
269 ifmedia_set(&sc->sc_media, defmedia);
270 } else {
271 ifmedia_add(&sc->sc_media, IFM_ETHER|IFM_MANUAL, 0, NULL);
272 ifmedia_set(&sc->sc_media, IFM_ETHER|IFM_MANUAL);
273 }
274
275 if (padbuf == NULL) {
276 padbuf = malloc(ETHER_MIN_LEN - ETHER_CRC_LEN, M_DEVBUF,
277 M_ZERO | M_NOWAIT);
278 if (padbuf == NULL) {
279 aprint_error_dev(&sc->sc_dev, "can't allocate pad buffer\n");
280 return;
281 }
282 }
283
284 /* Attach the interface. */
285 if_attach(ifp);
286 ether_ifattach(ifp, etheraddr);
287
288 printf(" address %s, type %s\n", ether_sprintf(etheraddr), name);
289 }
290
291
292 /*
293 * Device timeout/watchdog routine.
294 * Entered if the device neglects to generate an interrupt after a
295 * transmit has been started on it.
296 */
297 void
298 i82586_watchdog(ifp)
299 struct ifnet *ifp;
300 {
301 struct ie_softc *sc = ifp->if_softc;
302
303 log(LOG_ERR, "%s: device timeout\n", device_xname(&sc->sc_dev));
304 ++ifp->if_oerrors;
305
306 i82586_reset(sc, 1);
307 }
308
309 static int
310 i82586_cmd_wait(sc)
311 struct ie_softc *sc;
312 {
313 /* spin on i82586 command acknowledge; wait at most 0.9 (!) seconds */
314 int i, off;
315 u_int16_t cmd;
316
317 for (i = 0; i < 900000; i++) {
318 /* Read the command word */
319 off = IE_SCB_CMD(sc->scb);
320
321 IE_BUS_BARRIER(sc, off, 2, BUS_SPACE_BARRIER_READ);
322 if ((cmd = sc->ie_bus_read16(sc, off)) == 0)
323 return (0);
324 delay(1);
325 }
326
327 off = IE_SCB_STATUS(sc->scb);
328 printf("i82586_cmd_wait: timo(%ssync): scb status: 0x%x, cmd: 0x%x\n",
329 sc->async_cmd_inprogress?"a":"",
330 sc->ie_bus_read16(sc, off), cmd);
331
332 return (1); /* Timeout */
333 }
334
335 /*
336 * Send a command to the controller and wait for it to either complete
337 * or be accepted, depending on the command. If the command pointer
338 * is null, then pretend that the command is not an action command.
339 * If the command pointer is not null, and the command is an action
340 * command, wait for one of the MASK bits to turn on in the command's
341 * status field.
342 * If ASYNC is set, we just call the chip's attention and return.
343 * We may have to wait for the command's acceptance later though.
344 */
345 static int
346 i82586_start_cmd(sc, cmd, iecmdbuf, mask, async)
347 struct ie_softc *sc;
348 int cmd;
349 int iecmdbuf;
350 int mask;
351 int async;
352 {
353 int i;
354 int off;
355
356 if (sc->async_cmd_inprogress != 0) {
357 /*
358 * If previous command was issued asynchronously, wait
359 * for it now.
360 */
361 if (i82586_cmd_wait(sc) != 0)
362 return (1);
363 sc->async_cmd_inprogress = 0;
364 }
365
366 off = IE_SCB_CMD(sc->scb);
367 sc->ie_bus_write16(sc, off, cmd);
368 IE_BUS_BARRIER(sc, off, 2, BUS_SPACE_BARRIER_WRITE);
369 (sc->chan_attn)(sc, CARD_RESET);
370
371 if (async != 0) {
372 sc->async_cmd_inprogress = 1;
373 return (0);
374 }
375
376 if (IE_ACTION_COMMAND(cmd) && iecmdbuf) {
377 int status;
378 /*
379 * Now spin-lock waiting for status. This is not a very nice
380 * thing to do, and can kill performance pretty well...
381 * According to the packet driver, the minimum timeout
382 * should be .369 seconds.
383 */
384 for (i = 0; i < 369000; i++) {
385 /* Read the command status */
386 off = IE_CMD_COMMON_STATUS(iecmdbuf);
387 IE_BUS_BARRIER(sc, off, 2, BUS_SPACE_BARRIER_READ);
388 status = sc->ie_bus_read16(sc, off);
389 if (status & mask)
390 return (0);
391 delay(1);
392 }
393
394 } else {
395 /*
396 * Otherwise, just wait for the command to be accepted.
397 */
398 return (i82586_cmd_wait(sc));
399 }
400
401 /* Timeout */
402 return (1);
403 }
404
405 /*
406 * Interrupt Acknowledge.
407 */
408 static inline void
409 ie_ack(sc, mask)
410 struct ie_softc *sc;
411 u_int mask; /* in native byte-order */
412 {
413 u_int status;
414
415 IE_BUS_BARRIER(sc, 0, 0, BUS_SPACE_BARRIER_READ);
416 status = sc->ie_bus_read16(sc, IE_SCB_STATUS(sc->scb));
417 i82586_start_cmd(sc, status & mask, 0, 0, 0);
418 if (sc->intrhook)
419 sc->intrhook(sc, INTR_ACK);
420 }
421
422 /*
423 * Transfer accumulated chip error counters to IF.
424 */
425 static inline void
426 i82586_count_errors(sc)
427 struct ie_softc *sc;
428 {
429 int scb = sc->scb;
430
431 sc->sc_ethercom.ec_if.if_ierrors +=
432 sc->ie_bus_read16(sc, IE_SCB_ERRCRC(scb)) +
433 sc->ie_bus_read16(sc, IE_SCB_ERRALN(scb)) +
434 sc->ie_bus_read16(sc, IE_SCB_ERRRES(scb)) +
435 sc->ie_bus_read16(sc, IE_SCB_ERROVR(scb));
436
437 /* Clear error counters */
438 sc->ie_bus_write16(sc, IE_SCB_ERRCRC(scb), 0);
439 sc->ie_bus_write16(sc, IE_SCB_ERRALN(scb), 0);
440 sc->ie_bus_write16(sc, IE_SCB_ERRRES(scb), 0);
441 sc->ie_bus_write16(sc, IE_SCB_ERROVR(scb), 0);
442 }
443
444 static void
445 i82586_rx_errors(sc, fn, status)
446 struct ie_softc *sc;
447 int fn;
448 int status;
449 {
450 char bits[128];
451
452 log(LOG_ERR, "%s: rx error (frame# %d): %s\n", device_xname(&sc->sc_dev), fn,
453 bitmask_snprintf(status, IE_FD_STATUSBITS, bits, sizeof(bits)));
454 }
455
456 /*
457 * i82586 interrupt entry point.
458 */
459 int
460 i82586_intr(v)
461 void *v;
462 {
463 struct ie_softc *sc = v;
464 u_int status;
465 int off;
466
467 /*
468 * Implementation dependent interrupt handling.
469 */
470 if (sc->intrhook)
471 (sc->intrhook)(sc, INTR_ENTER);
472
473 off = IE_SCB_STATUS(sc->scb);
474 IE_BUS_BARRIER(sc, off, 2, BUS_SPACE_BARRIER_READ);
475 status = sc->ie_bus_read16(sc, off) & IE_ST_WHENCE;
476
477 if ((status & IE_ST_WHENCE) == 0) {
478 if (sc->intrhook)
479 (sc->intrhook)(sc, INTR_EXIT);
480
481 return (0);
482 }
483
484 loop:
485 /* Ack interrupts FIRST in case we receive more during the ISR. */
486 #if 0
487 ie_ack(sc, status & IE_ST_WHENCE);
488 #endif
489 i82586_start_cmd(sc, status & IE_ST_WHENCE, 0, 0, 1);
490
491 if (status & (IE_ST_FR | IE_ST_RNR))
492 if (i82586_rint(sc, status) != 0)
493 goto reset;
494
495 if (status & IE_ST_CX)
496 if (i82586_tint(sc, status) != 0)
497 goto reset;
498
499 #if I82586_DEBUG
500 if ((status & IE_ST_CNA) && (sc->sc_debug & IED_CNA))
501 printf("%s: cna; status=0x%x\n", device_xname(&sc->sc_dev), status);
502 #endif
503 if (sc->intrhook)
504 (sc->intrhook)(sc, INTR_LOOP);
505
506 /*
507 * Interrupt ACK was posted asynchronously; wait for
508 * completion here before reading SCB status again.
509 *
510 * If ACK fails, try to reset the chip, in hopes that
511 * it helps.
512 */
513 if (i82586_cmd_wait(sc) != 0)
514 goto reset;
515
516 IE_BUS_BARRIER(sc, off, 2, BUS_SPACE_BARRIER_READ);
517 status = sc->ie_bus_read16(sc, off);
518 if ((status & IE_ST_WHENCE) != 0)
519 goto loop;
520
521 out:
522 if (sc->intrhook)
523 (sc->intrhook)(sc, INTR_EXIT);
524 return (1);
525
526 reset:
527 i82586_cmd_wait(sc);
528 i82586_reset(sc, 1);
529 goto out;
530
531 }
532
533 /*
534 * Process a received-frame interrupt.
535 */
536 int
537 i82586_rint(sc, scbstatus)
538 struct ie_softc *sc;
539 int scbstatus;
540 {
541 static int timesthru = 1024;
542 int i, status, off;
543
544 #if I82586_DEBUG
545 if (sc->sc_debug & IED_RINT)
546 printf("%s: rint: status 0x%x\n",
547 device_xname(&sc->sc_dev), scbstatus);
548 #endif
549
550 for (;;) {
551 int drop = 0;
552
553 i = sc->rfhead;
554 off = IE_RFRAME_STATUS(sc->rframes, i);
555 IE_BUS_BARRIER(sc, off, 2, BUS_SPACE_BARRIER_READ);
556 status = sc->ie_bus_read16(sc, off);
557
558 #if I82586_DEBUG
559 if (sc->sc_debug & IED_RINT)
560 printf("%s: rint: frame(%d) status 0x%x\n",
561 device_xname(&sc->sc_dev), i, status);
562 #endif
563 if ((status & IE_FD_COMPLETE) == 0) {
564 if ((status & IE_FD_OK) != 0) {
565 printf("%s: rint: weird: ",
566 device_xname(&sc->sc_dev));
567 i82586_rx_errors(sc, i, status);
568 break;
569 }
570 if (--timesthru == 0) {
571 /* Account the accumulated errors */
572 i82586_count_errors(sc);
573 timesthru = 1024;
574 }
575 break;
576 } else if ((status & IE_FD_OK) == 0) {
577 /*
578 * If the chip is configured to automatically
579 * discard bad frames, the only reason we can
580 * get here is an "out-of-resource" condition.
581 */
582 i82586_rx_errors(sc, i, status);
583 drop = 1;
584 }
585
586 #if I82586_DEBUG
587 if ((status & IE_FD_BUSY) != 0)
588 printf("%s: rint: frame(%d) busy; status=0x%x\n",
589 device_xname(&sc->sc_dev), i, status);
590 #endif
591
592
593 /*
594 * Advance the RFD list, since we're done with
595 * this descriptor.
596 */
597
598 /* Clear frame status */
599 sc->ie_bus_write16(sc, off, 0);
600
601 /* Put fence at this frame (the head) */
602 off = IE_RFRAME_LAST(sc->rframes, i);
603 sc->ie_bus_write16(sc, off, IE_FD_EOL|IE_FD_SUSP);
604
605 /* and clear RBD field */
606 off = IE_RFRAME_BUFDESC(sc->rframes, i);
607 sc->ie_bus_write16(sc, off, 0xffff);
608
609 /* Remove fence from current tail */
610 off = IE_RFRAME_LAST(sc->rframes, sc->rftail);
611 sc->ie_bus_write16(sc, off, 0);
612
613 if (++sc->rftail == sc->nframes)
614 sc->rftail = 0;
615 if (++sc->rfhead == sc->nframes)
616 sc->rfhead = 0;
617
618 /* Pull the frame off the board */
619 if (drop) {
620 i82586_drop_frames(sc);
621 if ((status & IE_FD_RNR) != 0)
622 sc->rnr_expect = 1;
623 sc->sc_ethercom.ec_if.if_ierrors++;
624 } else if (ie_readframe(sc, i) != 0)
625 return (1);
626 }
627
628 if ((scbstatus & IE_ST_RNR) != 0) {
629
630 /*
631 * Receiver went "Not Ready". We try to figure out
632 * whether this was an expected event based on past
633 * frame status values.
634 */
635
636 if ((scbstatus & IE_RUS_SUSPEND) != 0) {
637 /*
638 * We use the "suspend on last frame" flag.
639 * Send a RU RESUME command in response, since
640 * we should have dealt with all completed frames
641 * by now.
642 */
643 printf("RINT: SUSPENDED; scbstatus=0x%x\n",
644 scbstatus);
645 if (i82586_start_cmd(sc, IE_RUC_RESUME, 0, 0, 0) == 0)
646 return (0);
647 aprint_error_dev(&sc->sc_dev, "RU RESUME command timed out\n");
648 return (1); /* Ask for a reset */
649 }
650
651 if (sc->rnr_expect != 0) {
652 /*
653 * The RNR condition was announced in the previously
654 * completed frame. Assume the receive ring is Ok,
655 * so restart the receiver without further delay.
656 */
657 i82586_start_transceiver(sc);
658 sc->rnr_expect = 0;
659 return (0);
660
661 } else if ((scbstatus & IE_RUS_NOSPACE) != 0) {
662 /*
663 * We saw no previous IF_FD_RNR flag.
664 * We check our ring invariants and, if ok,
665 * just restart the receiver at the current
666 * point in the ring.
667 */
668 if (i82586_chk_rx_ring(sc) != 0)
669 return (1);
670
671 i82586_start_transceiver(sc);
672 sc->sc_ethercom.ec_if.if_ierrors++;
673 return (0);
674 } else
675 printf("%s: receiver not ready; scbstatus=0x%x\n",
676 device_xname(&sc->sc_dev), scbstatus);
677
678 sc->sc_ethercom.ec_if.if_ierrors++;
679 return (1); /* Ask for a reset */
680 }
681
682 return (0);
683 }
684
685 /*
686 * Process a command-complete interrupt. These are only generated by the
687 * transmission of frames. This routine is deceptively simple, since most
688 * of the real work is done by i82586_start().
689 */
690 int
691 i82586_tint(sc, scbstatus)
692 struct ie_softc *sc;
693 int scbstatus;
694 {
695 struct ifnet *ifp = &sc->sc_ethercom.ec_if;
696 int status;
697
698 ifp->if_timer = 0;
699 ifp->if_flags &= ~IFF_OACTIVE;
700
701 #if I82586_DEBUG
702 if (sc->xmit_busy <= 0) {
703 printf("i82586_tint: WEIRD: xmit_busy=%d, xctail=%d, xchead=%d\n",
704 sc->xmit_busy, sc->xctail, sc->xchead);
705 return (0);
706 }
707 #endif
708
709 status = sc->ie_bus_read16(sc, IE_CMD_XMIT_STATUS(sc->xmit_cmds,
710 sc->xctail));
711
712 #if I82586_DEBUG
713 if (sc->sc_debug & IED_TINT)
714 printf("%s: tint: SCB status 0x%x; xmit status 0x%x\n",
715 device_xname(&sc->sc_dev), scbstatus, status);
716 #endif
717
718 if ((status & IE_STAT_COMPL) == 0 || (status & IE_STAT_BUSY)) {
719 printf("i82586_tint: command still busy; status=0x%x; tail=%d\n",
720 status, sc->xctail);
721 printf("iestatus = 0x%x\n", scbstatus);
722 }
723
724 if (status & IE_STAT_OK) {
725 ifp->if_opackets++;
726 ifp->if_collisions += (status & IE_XS_MAXCOLL);
727 } else {
728 ifp->if_oerrors++;
729 /*
730 * Check SQE and DEFERRED?
731 * What if more than one bit is set?
732 */
733 if (status & IE_STAT_ABORT)
734 aprint_error_dev(&sc->sc_dev, "send aborted\n");
735 else if (status & IE_XS_NOCARRIER)
736 aprint_error_dev(&sc->sc_dev, "no carrier\n");
737 else if (status & IE_XS_LOSTCTS)
738 aprint_error_dev(&sc->sc_dev, "lost CTS\n");
739 else if (status & IE_XS_UNDERRUN)
740 aprint_error_dev(&sc->sc_dev, "DMA underrun\n");
741 else if (status & IE_XS_EXCMAX) {
742 aprint_error_dev(&sc->sc_dev, "too many collisions\n");
743 sc->sc_ethercom.ec_if.if_collisions += 16;
744 }
745 }
746
747 /*
748 * If multicast addresses were added or deleted while transmitting,
749 * ie_mc_reset() set the want_mcsetup flag indicating that we
750 * should do it.
751 */
752 if (sc->want_mcsetup) {
753 ie_mc_setup(sc, IE_XBUF_ADDR(sc, sc->xctail));
754 sc->want_mcsetup = 0;
755 }
756
757 /* Done with the buffer. */
758 sc->xmit_busy--;
759 sc->xctail = (sc->xctail + 1) % NTXBUF;
760
761 /* Start the next packet, if any, transmitting. */
762 if (sc->xmit_busy > 0)
763 iexmit(sc);
764
765 i82586_start(ifp);
766 return (0);
767 }
768
769 /*
770 * Get a range of receive buffer descriptors that represent one packet.
771 */
772 static int
773 i82586_get_rbd_list(sc, start, end, pktlen)
774 struct ie_softc *sc;
775 u_int16_t *start;
776 u_int16_t *end;
777 int *pktlen;
778 {
779 int off, rbbase = sc->rbds;
780 int rbindex, count = 0;
781 int plen = 0;
782 int rbdstatus;
783
784 *start = rbindex = sc->rbhead;
785
786 do {
787 off = IE_RBD_STATUS(rbbase, rbindex);
788 IE_BUS_BARRIER(sc, off, 2, BUS_SPACE_BARRIER_READ);
789 rbdstatus = sc->ie_bus_read16(sc, off);
790 if ((rbdstatus & IE_RBD_USED) == 0) {
791 /*
792 * This means we are somehow out of sync. So, we
793 * reset the adapter.
794 */
795 #if I82586_DEBUG
796 print_rbd(sc, rbindex);
797 #endif
798 log(LOG_ERR,
799 "%s: receive descriptors out of sync at %d\n",
800 device_xname(&sc->sc_dev), rbindex);
801 return (0);
802 }
803 plen += (rbdstatus & IE_RBD_CNTMASK);
804
805 if (++rbindex == sc->nrxbuf)
806 rbindex = 0;
807
808 ++count;
809 } while ((rbdstatus & IE_RBD_LAST) == 0);
810 *end = rbindex;
811 *pktlen = plen;
812 return (count);
813 }
814
815
816 /*
817 * Release a range of receive buffer descriptors after we've copied the packet.
818 */
819 static void
820 i82586_release_rbd_list(sc, start, end)
821 struct ie_softc *sc;
822 u_int16_t start;
823 u_int16_t end;
824 {
825 int off, rbbase = sc->rbds;
826 int rbindex = start;
827
828 do {
829 /* Clear buffer status */
830 off = IE_RBD_STATUS(rbbase, rbindex);
831 sc->ie_bus_write16(sc, off, 0);
832 if (++rbindex == sc->nrxbuf)
833 rbindex = 0;
834 } while (rbindex != end);
835
836 /* Mark EOL at new tail */
837 rbindex = ((rbindex == 0) ? sc->nrxbuf : rbindex) - 1;
838 off = IE_RBD_BUFLEN(rbbase, rbindex);
839 sc->ie_bus_write16(sc, off, IE_RBUF_SIZE|IE_RBD_EOL);
840
841 /* Remove EOL from current tail */
842 off = IE_RBD_BUFLEN(rbbase, sc->rbtail);
843 sc->ie_bus_write16(sc, off, IE_RBUF_SIZE);
844
845 /* New head & tail pointer */
846 /* hmm, why have both? head is always (tail + 1) % NRXBUF */
847 sc->rbhead = end;
848 sc->rbtail = rbindex;
849 }
850
851 /*
852 * Drop the packet at the head of the RX buffer ring.
853 * Called if the frame descriptor reports an error on this packet.
854 * Returns 1 if the buffer descriptor ring appears to be corrupt;
855 * and 0 otherwise.
856 */
857 static int
858 i82586_drop_frames(sc)
859 struct ie_softc *sc;
860 {
861 u_int16_t bstart, bend;
862 int pktlen;
863
864 if (i82586_get_rbd_list(sc, &bstart, &bend, &pktlen) == 0)
865 return (1);
866 i82586_release_rbd_list(sc, bstart, bend);
867 return (0);
868 }
869
870 /*
871 * Check the RX frame & buffer descriptor lists for our invariants,
872 * i.e.: EOL bit set iff. it is pointed at by the r*tail pointer.
873 *
874 * Called when the receive unit has stopped unexpectedly.
875 * Returns 1 if an inconsistency is detected; 0 otherwise.
876 *
877 * The Receive Unit is expected to be NOT RUNNING.
878 */
879 static int
880 i82586_chk_rx_ring(sc)
881 struct ie_softc *sc;
882 {
883 int n, off, val;
884
885 for (n = 0; n < sc->nrxbuf; n++) {
886 off = IE_RBD_BUFLEN(sc->rbds, n);
887 val = sc->ie_bus_read16(sc, off);
888 if ((n == sc->rbtail) ^ ((val & IE_RBD_EOL) != 0)) {
889 /* `rbtail' and EOL flag out of sync */
890 log(LOG_ERR,
891 "%s: rx buffer descriptors out of sync at %d\n",
892 device_xname(&sc->sc_dev), n);
893 return (1);
894 }
895
896 /* Take the opportunity to clear the status fields here ? */
897 }
898
899 for (n = 0; n < sc->nframes; n++) {
900 off = IE_RFRAME_LAST(sc->rframes, n);
901 val = sc->ie_bus_read16(sc, off);
902 if ((n == sc->rftail) ^ ((val & (IE_FD_EOL|IE_FD_SUSP)) != 0)) {
903 /* `rftail' and EOL flag out of sync */
904 log(LOG_ERR,
905 "%s: rx frame list out of sync at %d\n",
906 device_xname(&sc->sc_dev), n);
907 return (1);
908 }
909 }
910
911 return (0);
912 }
913
914 /*
915 * Read data off the interface, and turn it into an mbuf chain.
916 *
917 * This code is DRAMATICALLY different from the previous version; this
918 * version tries to allocate the entire mbuf chain up front, given the
919 * length of the data available. This enables us to allocate mbuf
920 * clusters in many situations where before we would have had a long
921 * chain of partially-full mbufs. This should help to speed up the
922 * operation considerably. (Provided that it works, of course.)
923 */
924 static inline struct mbuf *
925 ieget(sc, head, totlen)
926 struct ie_softc *sc;
927 int head;
928 int totlen;
929 {
930 struct mbuf *m, *m0, *newm;
931 int len, resid;
932 int thisrboff, thismboff;
933 struct ether_header eh;
934
935 /*
936 * Snarf the Ethernet header.
937 */
938 (sc->memcopyin)(sc, &eh, IE_RBUF_ADDR(sc, head),
939 sizeof(struct ether_header));
940
941 resid = totlen;
942
943 MGETHDR(m0, M_DONTWAIT, MT_DATA);
944 if (m0 == 0)
945 return (0);
946 m0->m_pkthdr.rcvif = &sc->sc_ethercom.ec_if;
947 m0->m_pkthdr.len = totlen;
948 len = MHLEN;
949 m = m0;
950
951 /*
952 * This loop goes through and allocates mbufs for all the data we will
953 * be copying in. It does not actually do the copying yet.
954 */
955 while (totlen > 0) {
956 if (totlen >= MINCLSIZE) {
957 MCLGET(m, M_DONTWAIT);
958 if ((m->m_flags & M_EXT) == 0)
959 goto bad;
960 len = MCLBYTES;
961 }
962
963 if (m == m0) {
964 char *newdata = (char *)
965 ALIGN(m->m_data + sizeof(struct ether_header)) -
966 sizeof(struct ether_header);
967 len -= newdata - m->m_data;
968 m->m_data = newdata;
969 }
970
971 m->m_len = len = min(totlen, len);
972
973 totlen -= len;
974 if (totlen > 0) {
975 MGET(newm, M_DONTWAIT, MT_DATA);
976 if (newm == 0)
977 goto bad;
978 len = MLEN;
979 m = m->m_next = newm;
980 }
981 }
982
983 m = m0;
984 thismboff = 0;
985
986 /*
987 * Copy the Ethernet header into the mbuf chain.
988 */
989 memcpy(mtod(m, void *), &eh, sizeof(struct ether_header));
990 thismboff = sizeof(struct ether_header);
991 thisrboff = sizeof(struct ether_header);
992 resid -= sizeof(struct ether_header);
993
994 /*
995 * Now we take the mbuf chain (hopefully only one mbuf most of the
996 * time) and stuff the data into it. There are no possible failures
997 * at or after this point.
998 */
999 while (resid > 0) {
1000 int thisrblen = IE_RBUF_SIZE - thisrboff,
1001 thismblen = m->m_len - thismboff;
1002 len = min(thisrblen, thismblen);
1003
1004 (sc->memcopyin)(sc, mtod(m, char *) + thismboff,
1005 IE_RBUF_ADDR(sc,head) + thisrboff,
1006 (u_int)len);
1007 resid -= len;
1008
1009 if (len == thismblen) {
1010 m = m->m_next;
1011 thismboff = 0;
1012 } else
1013 thismboff += len;
1014
1015 if (len == thisrblen) {
1016 if (++head == sc->nrxbuf)
1017 head = 0;
1018 thisrboff = 0;
1019 } else
1020 thisrboff += len;
1021 }
1022
1023 /*
1024 * Unless something changed strangely while we were doing the copy,
1025 * we have now copied everything in from the shared memory.
1026 * This means that we are done.
1027 */
1028 return (m0);
1029
1030 bad:
1031 m_freem(m0);
1032 return (0);
1033 }
1034
1035 /*
1036 * Read frame NUM from unit UNIT (pre-cached as IE).
1037 *
1038 * This routine reads the RFD at NUM, and copies in the buffers from the list
1039 * of RBD, then rotates the RBD list so that the receiver doesn't start
1040 * complaining. Trailers are DROPPED---there's no point in wasting time
1041 * on confusing code to deal with them. Hopefully, this machine will
1042 * never ARP for trailers anyway.
1043 */
1044 static int
1045 ie_readframe(
1046 struct ie_softc *sc,
1047 int num) /* frame number to read */
1048 {
1049 struct mbuf *m;
1050 u_int16_t bstart, bend;
1051 int pktlen;
1052
1053 if (i82586_get_rbd_list(sc, &bstart, &bend, &pktlen) == 0) {
1054 sc->sc_ethercom.ec_if.if_ierrors++;
1055 return (1);
1056 }
1057
1058 m = ieget(sc, bstart, pktlen);
1059 i82586_release_rbd_list(sc, bstart, bend);
1060
1061 if (m == 0) {
1062 sc->sc_ethercom.ec_if.if_ierrors++;
1063 return (0);
1064 }
1065
1066 #if I82586_DEBUG
1067 if (sc->sc_debug & IED_READFRAME) {
1068 struct ether_header *eh = mtod(m, struct ether_header *);
1069
1070 printf("%s: frame from ether %s type 0x%x len %d\n",
1071 device_xname(&sc->sc_dev),
1072 ether_sprintf(eh->ether_shost),
1073 (u_int)ntohs(eh->ether_type),
1074 pktlen);
1075 }
1076 #endif
1077
1078 #if NBPFILTER > 0
1079 /* Check for a BPF filter; if so, hand it up. */
1080 if (sc->sc_ethercom.ec_if.if_bpf != 0)
1081 /* Pass it up. */
1082 bpf_mtap(sc->sc_ethercom.ec_if.if_bpf, m);
1083 #endif /* NBPFILTER > 0 */
1084
1085 /*
1086 * Finally pass this packet up to higher layers.
1087 */
1088 (*sc->sc_ethercom.ec_if.if_input)(&sc->sc_ethercom.ec_if, m);
1089 sc->sc_ethercom.ec_if.if_ipackets++;
1090 return (0);
1091 }
1092
1093
1094 /*
1095 * Setup all necessary artifacts for an XMIT command, and then pass the XMIT
1096 * command to the chip to be executed.
1097 */
1098 static inline void
1099 iexmit(sc)
1100 struct ie_softc *sc;
1101 {
1102 int off;
1103 int cur, prev;
1104
1105 cur = sc->xctail;
1106
1107 #if I82586_DEBUG
1108 if (sc->sc_debug & IED_XMIT)
1109 printf("%s: xmit buffer %d\n", device_xname(&sc->sc_dev), cur);
1110 #endif
1111
1112 /*
1113 * Setup the transmit command.
1114 */
1115 sc->ie_bus_write16(sc, IE_CMD_XMIT_DESC(sc->xmit_cmds, cur),
1116 IE_XBD_ADDR(sc->xbds, cur));
1117
1118 sc->ie_bus_write16(sc, IE_CMD_XMIT_STATUS(sc->xmit_cmds, cur), 0);
1119
1120 if (sc->do_xmitnopchain) {
1121 /*
1122 * Gate this XMIT command to the following NOP
1123 */
1124 sc->ie_bus_write16(sc, IE_CMD_XMIT_LINK(sc->xmit_cmds, cur),
1125 IE_CMD_NOP_ADDR(sc->nop_cmds, cur));
1126 sc->ie_bus_write16(sc, IE_CMD_XMIT_CMD(sc->xmit_cmds, cur),
1127 IE_CMD_XMIT | IE_CMD_INTR);
1128
1129 /*
1130 * Loopback at following NOP
1131 */
1132 sc->ie_bus_write16(sc, IE_CMD_NOP_STATUS(sc->nop_cmds, cur), 0);
1133 sc->ie_bus_write16(sc, IE_CMD_NOP_LINK(sc->nop_cmds, cur),
1134 IE_CMD_NOP_ADDR(sc->nop_cmds, cur));
1135
1136 /*
1137 * Gate preceding NOP to this XMIT command
1138 */
1139 prev = (cur + NTXBUF - 1) % NTXBUF;
1140 sc->ie_bus_write16(sc, IE_CMD_NOP_STATUS(sc->nop_cmds, prev), 0);
1141 sc->ie_bus_write16(sc, IE_CMD_NOP_LINK(sc->nop_cmds, prev),
1142 IE_CMD_XMIT_ADDR(sc->xmit_cmds, cur));
1143
1144 off = IE_SCB_STATUS(sc->scb);
1145 IE_BUS_BARRIER(sc, off, 2, BUS_SPACE_BARRIER_READ);
1146 if ((sc->ie_bus_read16(sc, off) & IE_CUS_ACTIVE) == 0) {
1147 printf("iexmit: CU not active\n");
1148 i82586_start_transceiver(sc);
1149 }
1150 } else {
1151 sc->ie_bus_write16(sc, IE_CMD_XMIT_LINK(sc->xmit_cmds,cur),
1152 0xffff);
1153
1154 sc->ie_bus_write16(sc, IE_CMD_XMIT_CMD(sc->xmit_cmds, cur),
1155 IE_CMD_XMIT | IE_CMD_INTR | IE_CMD_LAST);
1156
1157 off = IE_SCB_CMDLST(sc->scb);
1158 sc->ie_bus_write16(sc, off, IE_CMD_XMIT_ADDR(sc->xmit_cmds, cur));
1159 IE_BUS_BARRIER(sc, off, 2, BUS_SPACE_BARRIER_READ);
1160
1161 if (i82586_start_cmd(sc, IE_CUC_START, 0, 0, 1))
1162 aprint_error_dev(&sc->sc_dev, "iexmit: start xmit command timed out\n");
1163 }
1164
1165 sc->sc_ethercom.ec_if.if_timer = 5;
1166 }
1167
1168
1169 /*
1170 * Start transmission on an interface.
1171 */
1172 void
1173 i82586_start(ifp)
1174 struct ifnet *ifp;
1175 {
1176 struct ie_softc *sc = ifp->if_softc;
1177 struct mbuf *m0, *m;
1178 int buffer, head, xbase;
1179 u_short len;
1180 int s;
1181
1182 if ((ifp->if_flags & (IFF_RUNNING | IFF_OACTIVE)) != IFF_RUNNING)
1183 return;
1184
1185 for (;;) {
1186 if (sc->xmit_busy == NTXBUF) {
1187 ifp->if_flags |= IFF_OACTIVE;
1188 break;
1189 }
1190
1191 head = sc->xchead;
1192 xbase = sc->xbds;
1193
1194 IFQ_DEQUEUE(&ifp->if_snd, m0);
1195 if (m0 == 0)
1196 break;
1197
1198 /* We need to use m->m_pkthdr.len, so require the header */
1199 if ((m0->m_flags & M_PKTHDR) == 0)
1200 panic("i82586_start: no header mbuf");
1201
1202 #if NBPFILTER > 0
1203 /* Tap off here if there is a BPF listener. */
1204 if (ifp->if_bpf)
1205 bpf_mtap(ifp->if_bpf, m0);
1206 #endif
1207
1208 #if I82586_DEBUG
1209 if (sc->sc_debug & IED_ENQ)
1210 printf("%s: fill buffer %d\n", device_xname(&sc->sc_dev),
1211 sc->xchead);
1212 #endif
1213
1214 if (m0->m_pkthdr.len > IE_TBUF_SIZE)
1215 printf("%s: tbuf overflow\n", device_xname(&sc->sc_dev));
1216
1217 buffer = IE_XBUF_ADDR(sc, head);
1218 for (m = m0; m != 0; m = m->m_next) {
1219 (sc->memcopyout)(sc, mtod(m,void *), buffer, m->m_len);
1220 buffer += m->m_len;
1221 }
1222 len = m0->m_pkthdr.len;
1223 if (len < ETHER_MIN_LEN - ETHER_CRC_LEN) {
1224 (sc->memcopyout)(sc, padbuf, buffer,
1225 ETHER_MIN_LEN - ETHER_CRC_LEN - len);
1226 buffer += ETHER_MIN_LEN -ETHER_CRC_LEN - len;
1227 len = ETHER_MIN_LEN - ETHER_CRC_LEN;
1228 }
1229 m_freem(m0);
1230
1231 /*
1232 * Setup the transmit buffer descriptor here, while we
1233 * know the packet's length.
1234 */
1235 sc->ie_bus_write16(sc, IE_XBD_FLAGS(xbase, head),
1236 len | IE_TBD_EOL);
1237 sc->ie_bus_write16(sc, IE_XBD_NEXT(xbase, head), 0xffff);
1238 sc->ie_bus_write24(sc, IE_XBD_BUF(xbase, head),
1239 IE_XBUF_ADDR(sc, head));
1240
1241 if (++head == NTXBUF)
1242 head = 0;
1243 sc->xchead = head;
1244
1245 s = splnet();
1246 /* Start the first packet transmitting. */
1247 if (sc->xmit_busy == 0)
1248 iexmit(sc);
1249
1250 sc->xmit_busy++;
1251 splx(s);
1252 }
1253 }
1254
1255 /*
1256 * Probe IE's ram setup [ Move all this into MD front-end!? ]
1257 * Use only if SCP and ISCP represent offsets into shared ram space.
1258 */
1259 int
1260 i82586_proberam(sc)
1261 struct ie_softc *sc;
1262 {
1263 int result, off;
1264
1265 /* Put in 16-bit mode */
1266 off = IE_SCP_BUS_USE(sc->scp);
1267 sc->ie_bus_write16(sc, off, IE_SYSBUS_16BIT);
1268 IE_BUS_BARRIER(sc, off, 2, BUS_SPACE_BARRIER_WRITE);
1269
1270 /* Set the ISCP `busy' bit */
1271 off = IE_ISCP_BUSY(sc->iscp);
1272 sc->ie_bus_write16(sc, off, 1);
1273 IE_BUS_BARRIER(sc, off, 2, BUS_SPACE_BARRIER_WRITE);
1274
1275 if (sc->hwreset)
1276 (sc->hwreset)(sc, CHIP_PROBE);
1277
1278 (sc->chan_attn) (sc, CHIP_PROBE);
1279
1280 delay(100); /* wait a while... */
1281
1282 /* Read back the ISCP `busy' bit; it should be clear by now */
1283 off = IE_ISCP_BUSY(sc->iscp);
1284 IE_BUS_BARRIER(sc, off, 2, BUS_SPACE_BARRIER_READ);
1285 result = sc->ie_bus_read16(sc, off) == 0;
1286
1287 /* Acknowledge any interrupts we may have caused. */
1288 ie_ack(sc, IE_ST_WHENCE);
1289
1290 return (result);
1291 }
1292
1293 void
1294 i82586_reset(sc, hard)
1295 struct ie_softc *sc;
1296 int hard;
1297 {
1298 int s = splnet();
1299
1300 if (hard)
1301 printf("%s: reset\n", device_xname(&sc->sc_dev));
1302
1303 /* Clear OACTIVE in case we're called from watchdog (frozen xmit). */
1304 sc->sc_ethercom.ec_if.if_timer = 0;
1305 sc->sc_ethercom.ec_if.if_flags &= ~IFF_OACTIVE;
1306
1307 /*
1308 * Stop i82586 dead in its tracks.
1309 */
1310 if (i82586_start_cmd(sc, IE_RUC_ABORT | IE_CUC_ABORT, 0, 0, 0))
1311 aprint_error_dev(&sc->sc_dev, "abort commands timed out\n");
1312
1313 /*
1314 * This can really slow down the i82586_reset() on some cards, but it's
1315 * necessary to unwedge other ones (eg, the Sun VME ones) from certain
1316 * lockups.
1317 */
1318 if (hard && sc->hwreset)
1319 (sc->hwreset)(sc, CARD_RESET);
1320
1321 delay(100);
1322 ie_ack(sc, IE_ST_WHENCE);
1323
1324 if ((sc->sc_ethercom.ec_if.if_flags & IFF_UP) != 0) {
1325 int retries=0; /* XXX - find out why init sometimes fails */
1326 while (retries++ < 2)
1327 if (i82586_init(&sc->sc_ethercom.ec_if) == 0)
1328 break;
1329 }
1330
1331 splx(s);
1332 }
1333
1334
1335 static void
1336 setup_simple_command(sc, cmd, cmdbuf)
1337 struct ie_softc *sc;
1338 int cmd;
1339 int cmdbuf;
1340 {
1341 /* Setup a simple command */
1342 sc->ie_bus_write16(sc, IE_CMD_COMMON_STATUS(cmdbuf), 0);
1343 sc->ie_bus_write16(sc, IE_CMD_COMMON_CMD(cmdbuf), cmd | IE_CMD_LAST);
1344 sc->ie_bus_write16(sc, IE_CMD_COMMON_LINK(cmdbuf), 0xffff);
1345
1346 /* Assign the command buffer to the SCB command list */
1347 sc->ie_bus_write16(sc, IE_SCB_CMDLST(sc->scb), cmdbuf);
1348 }
1349
1350 /*
1351 * Run the time-domain reflectometer.
1352 */
1353 static void
1354 ie_run_tdr(sc, cmd)
1355 struct ie_softc *sc;
1356 int cmd;
1357 {
1358 int result;
1359
1360 setup_simple_command(sc, IE_CMD_TDR, cmd);
1361 sc->ie_bus_write16(sc, IE_CMD_TDR_TIME(cmd), 0);
1362
1363 if (i82586_start_cmd(sc, IE_CUC_START, cmd, IE_STAT_COMPL, 0) ||
1364 (sc->ie_bus_read16(sc, IE_CMD_COMMON_STATUS(cmd)) & IE_STAT_OK) == 0)
1365 result = 0x10000; /* XXX */
1366 else
1367 result = sc->ie_bus_read16(sc, IE_CMD_TDR_TIME(cmd));
1368
1369 /* Squash any pending interrupts */
1370 ie_ack(sc, IE_ST_WHENCE);
1371
1372 if (result & IE_TDR_SUCCESS)
1373 return;
1374
1375 if (result & 0x10000)
1376 aprint_error_dev(&sc->sc_dev, "TDR command failed\n");
1377 else if (result & IE_TDR_XCVR)
1378 aprint_error_dev(&sc->sc_dev, "transceiver problem\n");
1379 else if (result & IE_TDR_OPEN)
1380 aprint_error_dev(&sc->sc_dev, "TDR detected incorrect termination %d clocks away\n",
1381 result & IE_TDR_TIME);
1382 else if (result & IE_TDR_SHORT)
1383 aprint_error_dev(&sc->sc_dev, "TDR detected a short circuit %d clocks away\n",
1384 result & IE_TDR_TIME);
1385 else
1386 aprint_error_dev(&sc->sc_dev, "TDR returned unknown status 0x%x\n",
1387 result);
1388 }
1389
1390
1391 /*
1392 * i82586_setup_bufs: set up the buffers
1393 *
1394 * We have a block of KVA at sc->buf_area which is of size sc->buf_area_sz.
1395 * this is to be used for the buffers. The chip indexs its control data
1396 * structures with 16 bit offsets, and it indexes actual buffers with
1397 * 24 bit addresses. So we should allocate control buffers first so that
1398 * we don't overflow the 16 bit offset field. The number of transmit
1399 * buffers is fixed at compile time.
1400 *
1401 */
1402 static void
1403 i82586_setup_bufs(sc)
1404 struct ie_softc *sc;
1405 {
1406 int ptr = sc->buf_area; /* memory pool */
1407 int n, r;
1408
1409 /*
1410 * step 0: zero memory and figure out how many recv buffers and
1411 * frames we can have.
1412 */
1413 ptr = (ptr + 3) & ~3; /* set alignment and stick with it */
1414
1415
1416 /*
1417 * step 1: lay out data structures in the shared-memory area
1418 */
1419
1420 /* The no-op commands; used if "nop-chaining" is in effect */
1421 sc->nop_cmds = ptr;
1422 ptr += NTXBUF * IE_CMD_NOP_SZ;
1423
1424 /* The transmit commands */
1425 sc->xmit_cmds = ptr;
1426 ptr += NTXBUF * IE_CMD_XMIT_SZ;
1427
1428 /* The transmit buffers descriptors */
1429 sc->xbds = ptr;
1430 ptr += NTXBUF * IE_XBD_SZ;
1431
1432 /* The transmit buffers */
1433 sc->xbufs = ptr;
1434 ptr += NTXBUF * IE_TBUF_SIZE;
1435
1436 ptr = (ptr + 3) & ~3; /* re-align.. just in case */
1437
1438 /* Compute free space for RECV stuff */
1439 n = sc->buf_area_sz - (ptr - sc->buf_area);
1440
1441 /* Compute size of one RECV frame */
1442 r = IE_RFRAME_SZ + ((IE_RBD_SZ + IE_RBUF_SIZE) * B_PER_F);
1443
1444 sc->nframes = n / r;
1445
1446 if (sc->nframes <= 0)
1447 panic("ie: bogus buffer calc");
1448
1449 sc->nrxbuf = sc->nframes * B_PER_F;
1450
1451 /* The receive frame descriptors */
1452 sc->rframes = ptr;
1453 ptr += sc->nframes * IE_RFRAME_SZ;
1454
1455 /* The receive buffer descriptors */
1456 sc->rbds = ptr;
1457 ptr += sc->nrxbuf * IE_RBD_SZ;
1458
1459 /* The receive buffers */
1460 sc->rbufs = ptr;
1461 ptr += sc->nrxbuf * IE_RBUF_SIZE;
1462
1463 #if I82586_DEBUG
1464 printf("%s: %d frames %d bufs\n", device_xname(&sc->sc_dev), sc->nframes,
1465 sc->nrxbuf);
1466 #endif
1467
1468 /*
1469 * step 2: link together the recv frames and set EOL on last one
1470 */
1471 for (n = 0; n < sc->nframes; n++) {
1472 int m = (n == sc->nframes - 1) ? 0 : n + 1;
1473
1474 /* Clear status */
1475 sc->ie_bus_write16(sc, IE_RFRAME_STATUS(sc->rframes,n), 0);
1476
1477 /* RBD link = NULL */
1478 sc->ie_bus_write16(sc, IE_RFRAME_BUFDESC(sc->rframes,n),
1479 0xffff);
1480
1481 /* Make a circular list */
1482 sc->ie_bus_write16(sc, IE_RFRAME_NEXT(sc->rframes,n),
1483 IE_RFRAME_ADDR(sc->rframes,m));
1484
1485 /* Mark last as EOL */
1486 sc->ie_bus_write16(sc, IE_RFRAME_LAST(sc->rframes,n),
1487 ((m==0)? (IE_FD_EOL|IE_FD_SUSP) : 0));
1488 }
1489
1490 /*
1491 * step 3: link the RBDs and set EOL on last one
1492 */
1493 for (n = 0; n < sc->nrxbuf; n++) {
1494 int m = (n == sc->nrxbuf - 1) ? 0 : n + 1;
1495
1496 /* Clear status */
1497 sc->ie_bus_write16(sc, IE_RBD_STATUS(sc->rbds,n), 0);
1498
1499 /* Make a circular list */
1500 sc->ie_bus_write16(sc, IE_RBD_NEXT(sc->rbds,n),
1501 IE_RBD_ADDR(sc->rbds,m));
1502
1503 /* Link to data buffers */
1504 sc->ie_bus_write24(sc, IE_RBD_BUFADDR(sc->rbds, n),
1505 IE_RBUF_ADDR(sc, n));
1506 sc->ie_bus_write16(sc, IE_RBD_BUFLEN(sc->rbds,n),
1507 IE_RBUF_SIZE | ((m==0)?IE_RBD_EOL:0));
1508 }
1509
1510 /*
1511 * step 4: all xmit no-op commands loopback onto themselves
1512 */
1513 for (n = 0; n < NTXBUF; n++) {
1514 sc->ie_bus_write16(sc, IE_CMD_NOP_STATUS(sc->nop_cmds, n), 0);
1515
1516 sc->ie_bus_write16(sc, IE_CMD_NOP_CMD(sc->nop_cmds, n),
1517 IE_CMD_NOP);
1518
1519 sc->ie_bus_write16(sc, IE_CMD_NOP_LINK(sc->nop_cmds, n),
1520 IE_CMD_NOP_ADDR(sc->nop_cmds, n));
1521 }
1522
1523
1524 /*
1525 * step 6: set the head and tail pointers on receive to keep track of
1526 * the order in which RFDs and RBDs are used.
1527 */
1528
1529 /* Pointers to last packet sent and next available transmit buffer. */
1530 sc->xchead = sc->xctail = 0;
1531
1532 /* Clear transmit-busy flag and set number of free transmit buffers. */
1533 sc->xmit_busy = 0;
1534
1535 /*
1536 * Pointers to first and last receive frame.
1537 * The RFD pointed to by rftail is the only one that has EOL set.
1538 */
1539 sc->rfhead = 0;
1540 sc->rftail = sc->nframes - 1;
1541
1542 /*
1543 * Pointers to first and last receive descriptor buffer.
1544 * The RBD pointed to by rbtail is the only one that has EOL set.
1545 */
1546 sc->rbhead = 0;
1547 sc->rbtail = sc->nrxbuf - 1;
1548
1549 /* link in recv frames * and buffer into the scb. */
1550 #if I82586_DEBUG
1551 printf("%s: reserved %d bytes\n",
1552 device_xname(&sc->sc_dev), ptr - sc->buf_area);
1553 #endif
1554 }
1555
1556 static int
1557 ie_cfg_setup(sc, cmd, promiscuous, manchester)
1558 struct ie_softc *sc;
1559 int cmd;
1560 int promiscuous, manchester;
1561 {
1562 int cmdresult, status;
1563 u_int8_t buf[IE_CMD_CFG_SZ]; /* XXX malloc? */
1564
1565 *IE_CMD_CFG_CNT(buf) = 0x0c;
1566 *IE_CMD_CFG_FIFO(buf) = 8;
1567 *IE_CMD_CFG_SAVEBAD(buf) = 0x40;
1568 *IE_CMD_CFG_ADDRLEN(buf) = 0x2e;
1569 *IE_CMD_CFG_PRIORITY(buf) = 0;
1570 *IE_CMD_CFG_IFS(buf) = 0x60;
1571 *IE_CMD_CFG_SLOT_LOW(buf) = 0;
1572 *IE_CMD_CFG_SLOT_HIGH(buf) = 0xf2;
1573 *IE_CMD_CFG_PROMISC(buf) = !!promiscuous | manchester << 2;
1574 *IE_CMD_CFG_CRSCDT(buf) = 0;
1575 *IE_CMD_CFG_MINLEN(buf) = 64;
1576 *IE_CMD_CFG_JUNK(buf) = 0xff;
1577 sc->memcopyout(sc, buf, cmd, IE_CMD_CFG_SZ);
1578 setup_simple_command(sc, IE_CMD_CONFIG, cmd);
1579 IE_BUS_BARRIER(sc, cmd, IE_CMD_CFG_SZ, BUS_SPACE_BARRIER_WRITE);
1580
1581 cmdresult = i82586_start_cmd(sc, IE_CUC_START, cmd, IE_STAT_COMPL, 0);
1582 status = sc->ie_bus_read16(sc, IE_CMD_COMMON_STATUS(cmd));
1583 if (cmdresult != 0) {
1584 aprint_error_dev(&sc->sc_dev, "configure command timed out; status %x\n", status);
1585 return (0);
1586 }
1587 if ((status & IE_STAT_OK) == 0) {
1588 aprint_error_dev(&sc->sc_dev, "configure command failed; status %x\n", status);
1589 return (0);
1590 }
1591
1592 /* Squash any pending interrupts */
1593 ie_ack(sc, IE_ST_WHENCE);
1594 return (1);
1595 }
1596
1597 static int
1598 ie_ia_setup(sc, cmdbuf)
1599 struct ie_softc *sc;
1600 int cmdbuf;
1601 {
1602 int cmdresult, status;
1603 struct ifnet *ifp = &sc->sc_ethercom.ec_if;
1604
1605 setup_simple_command(sc, IE_CMD_IASETUP, cmdbuf);
1606
1607 (sc->memcopyout)(sc, CLLADDR(ifp->if_sadl),
1608 IE_CMD_IAS_EADDR(cmdbuf), ETHER_ADDR_LEN);
1609
1610 cmdresult = i82586_start_cmd(sc, IE_CUC_START, cmdbuf, IE_STAT_COMPL, 0);
1611 status = sc->ie_bus_read16(sc, IE_CMD_COMMON_STATUS(cmdbuf));
1612 if (cmdresult != 0) {
1613 aprint_error_dev(&sc->sc_dev, "individual address command timed out; status %x\n", status);
1614 return (0);
1615 }
1616 if ((status & IE_STAT_OK) == 0) {
1617 aprint_error_dev(&sc->sc_dev, "individual address command failed; status %x\n", status);
1618 return (0);
1619 }
1620
1621 /* Squash any pending interrupts */
1622 ie_ack(sc, IE_ST_WHENCE);
1623 return (1);
1624 }
1625
1626 /*
1627 * Run the multicast setup command.
1628 * Called at splnet().
1629 */
1630 static int
1631 ie_mc_setup(sc, cmdbuf)
1632 struct ie_softc *sc;
1633 int cmdbuf;
1634 {
1635 int cmdresult, status;
1636
1637 if (sc->mcast_count == 0)
1638 return (1);
1639
1640 setup_simple_command(sc, IE_CMD_MCAST, cmdbuf);
1641
1642 (sc->memcopyout)(sc, (void *)sc->mcast_addrs,
1643 IE_CMD_MCAST_MADDR(cmdbuf),
1644 sc->mcast_count * ETHER_ADDR_LEN);
1645
1646 sc->ie_bus_write16(sc, IE_CMD_MCAST_BYTES(cmdbuf),
1647 sc->mcast_count * ETHER_ADDR_LEN);
1648
1649 /* Start the command */
1650 cmdresult = i82586_start_cmd(sc, IE_CUC_START, cmdbuf, IE_STAT_COMPL, 0);
1651 status = sc->ie_bus_read16(sc, IE_CMD_COMMON_STATUS(cmdbuf));
1652 if (cmdresult != 0) {
1653 aprint_error_dev(&sc->sc_dev, "multicast setup command timed out; status %x\n", status);
1654 return (0);
1655 }
1656 if ((status & IE_STAT_OK) == 0) {
1657 aprint_error_dev(&sc->sc_dev, "multicast setup command failed; status %x\n",
1658 status);
1659 return (0);
1660 }
1661
1662 /* Squash any pending interrupts */
1663 ie_ack(sc, IE_ST_WHENCE);
1664 return (1);
1665 }
1666
1667 /*
1668 * This routine takes the environment generated by check_ie_present() and adds
1669 * to it all the other structures we need to operate the adapter. This
1670 * includes executing the CONFIGURE, IA-SETUP, and MC-SETUP commands, starting
1671 * the receiver unit, and clearing interrupts.
1672 *
1673 * THIS ROUTINE MUST BE CALLED AT splnet() OR HIGHER.
1674 */
1675 int
1676 i82586_init(ifp)
1677 struct ifnet *ifp;
1678 {
1679 struct ie_softc *sc = ifp->if_softc;
1680 int cmd;
1681
1682 sc->async_cmd_inprogress = 0;
1683
1684 cmd = sc->buf_area;
1685
1686 /*
1687 * Send the configure command first.
1688 */
1689 if (ie_cfg_setup(sc, cmd, sc->promisc, 0) == 0)
1690 return EIO;
1691
1692 /*
1693 * Send the Individual Address Setup command.
1694 */
1695 if (ie_ia_setup(sc, cmd) == 0)
1696 return EIO;
1697
1698 /*
1699 * Run the time-domain reflectometer.
1700 */
1701 ie_run_tdr(sc, cmd);
1702
1703 /*
1704 * Set the multi-cast filter, if any
1705 */
1706 if (ie_mc_setup(sc, cmd) == 0)
1707 return EIO;
1708
1709 /*
1710 * Acknowledge any interrupts we have generated thus far.
1711 */
1712 ie_ack(sc, IE_ST_WHENCE);
1713
1714 /*
1715 * Set up the transmit and recv buffers.
1716 */
1717 i82586_setup_bufs(sc);
1718
1719 if (sc->hwinit)
1720 (sc->hwinit)(sc);
1721
1722 ifp->if_flags |= IFF_RUNNING;
1723 ifp->if_flags &= ~IFF_OACTIVE;
1724
1725 if (NTXBUF < 2)
1726 sc->do_xmitnopchain = 0;
1727
1728 i82586_start_transceiver(sc);
1729 return (0);
1730 }
1731
1732 /*
1733 * Start the RU and possibly the CU unit
1734 */
1735 static void
1736 i82586_start_transceiver(sc)
1737 struct ie_softc *sc;
1738 {
1739
1740 /*
1741 * Start RU at current position in frame & RBD lists.
1742 */
1743 sc->ie_bus_write16(sc, IE_RFRAME_BUFDESC(sc->rframes,sc->rfhead),
1744 IE_RBD_ADDR(sc->rbds, sc->rbhead));
1745
1746 sc->ie_bus_write16(sc, IE_SCB_RCVLST(sc->scb),
1747 IE_RFRAME_ADDR(sc->rframes,sc->rfhead));
1748
1749 if (sc->do_xmitnopchain) {
1750 /* Stop transmit command chain */
1751 if (i82586_start_cmd(sc, IE_CUC_SUSPEND|IE_RUC_SUSPEND, 0, 0, 0))
1752 aprint_error_dev(&sc->sc_dev, "CU/RU stop command timed out\n");
1753
1754 /* Start the receiver & transmitter chain */
1755 /* sc->scb->ie_command_list =
1756 IEADDR(sc->nop_cmds[(sc->xctail+NTXBUF-1) % NTXBUF]);*/
1757 sc->ie_bus_write16(sc, IE_SCB_CMDLST(sc->scb),
1758 IE_CMD_NOP_ADDR(
1759 sc->nop_cmds,
1760 (sc->xctail + NTXBUF - 1) % NTXBUF));
1761
1762 if (i82586_start_cmd(sc, IE_CUC_START|IE_RUC_START, 0, 0, 0))
1763 aprint_error_dev(&sc->sc_dev, "CU/RU command timed out\n");
1764 } else {
1765 if (i82586_start_cmd(sc, IE_RUC_START, 0, 0, 0))
1766 aprint_error_dev(&sc->sc_dev, "RU command timed out\n");
1767 }
1768 }
1769
1770 void
1771 i82586_stop(
1772 struct ifnet *ifp,
1773 int disable)
1774 {
1775 struct ie_softc *sc = ifp->if_softc;
1776
1777 if (i82586_start_cmd(sc, IE_RUC_SUSPEND | IE_CUC_SUSPEND, 0, 0, 0))
1778 aprint_error_dev(&sc->sc_dev, "iestop: disable commands timed out\n");
1779 }
1780
1781 int
1782 i82586_ioctl(ifp, cmd, data)
1783 struct ifnet *ifp;
1784 u_long cmd;
1785 void *data;
1786 {
1787 struct ie_softc *sc = ifp->if_softc;
1788 struct ifreq *ifr = (struct ifreq *)data;
1789 int s, error = 0;
1790
1791 s = splnet();
1792 switch(cmd) {
1793 case SIOCGIFMEDIA:
1794 case SIOCSIFMEDIA:
1795 error = ifmedia_ioctl(ifp, ifr, &sc->sc_media, cmd);
1796 break;
1797 default:
1798 error = ether_ioctl(ifp, cmd, data);
1799 if (error == ENETRESET) {
1800 /*
1801 * Multicast list has changed; set the hardware filter
1802 * accordingly.
1803 */
1804 if (ifp->if_flags & IFF_RUNNING)
1805 ie_mc_reset(sc);
1806 error = 0;
1807 }
1808 break;
1809 }
1810 #if I82586_DEBUG
1811 if (cmd == SIOCSIFFLAGS)
1812 sc->sc_debug = (ifp->if_flags & IFF_DEBUG) ? IED_ALL : 0;
1813 #endif
1814 splx(s);
1815 return (error);
1816 }
1817
1818 static void
1819 ie_mc_reset(sc)
1820 struct ie_softc *sc;
1821 {
1822 struct ether_multi *enm;
1823 struct ether_multistep step;
1824 int size;
1825
1826 /*
1827 * Step through the list of addresses.
1828 */
1829 again:
1830 size = 0;
1831 sc->mcast_count = 0;
1832 ETHER_FIRST_MULTI(step, &sc->sc_ethercom, enm);
1833 while (enm) {
1834 size += 6;
1835 if (sc->mcast_count >= IE_MAXMCAST ||
1836 memcmp(enm->enm_addrlo, enm->enm_addrhi, 6) != 0) {
1837 sc->sc_ethercom.ec_if.if_flags |= IFF_ALLMULTI;
1838 i82586_ioctl(&sc->sc_ethercom.ec_if,
1839 SIOCSIFFLAGS, (void *)0);
1840 return;
1841 }
1842 ETHER_NEXT_MULTI(step, enm);
1843 }
1844
1845 if (size > sc->mcast_addrs_size) {
1846 /* Need to allocate more space */
1847 if (sc->mcast_addrs_size)
1848 free(sc->mcast_addrs, M_IFMADDR);
1849 sc->mcast_addrs = (char *)
1850 malloc(size, M_IFMADDR, M_WAITOK);
1851 sc->mcast_addrs_size = size;
1852 }
1853
1854 /*
1855 * We've got the space; now copy the addresses
1856 */
1857 ETHER_FIRST_MULTI(step, &sc->sc_ethercom, enm);
1858 while (enm) {
1859 if (sc->mcast_count >= IE_MAXMCAST)
1860 goto again; /* Just in case */
1861
1862 memcpy(&sc->mcast_addrs[sc->mcast_count], enm->enm_addrlo, 6);
1863 sc->mcast_count++;
1864 ETHER_NEXT_MULTI(step, enm);
1865 }
1866 sc->want_mcsetup = 1;
1867 }
1868
1869 /*
1870 * Media change callback.
1871 */
1872 int
1873 i82586_mediachange(ifp)
1874 struct ifnet *ifp;
1875 {
1876 struct ie_softc *sc = ifp->if_softc;
1877
1878 if (sc->sc_mediachange)
1879 return ((*sc->sc_mediachange)(sc));
1880 return (0);
1881 }
1882
1883 /*
1884 * Media status callback.
1885 */
1886 void
1887 i82586_mediastatus(ifp, ifmr)
1888 struct ifnet *ifp;
1889 struct ifmediareq *ifmr;
1890 {
1891 struct ie_softc *sc = ifp->if_softc;
1892
1893 if (sc->sc_mediastatus)
1894 (*sc->sc_mediastatus)(sc, ifmr);
1895 }
1896
1897 #if I82586_DEBUG
1898 void
1899 print_rbd(sc, n)
1900 struct ie_softc *sc;
1901 int n;
1902 {
1903
1904 printf("RBD at %08x:\n status %04x, next %04x, buffer %lx\n"
1905 "length/EOL %04x\n", IE_RBD_ADDR(sc->rbds,n),
1906 sc->ie_bus_read16(sc, IE_RBD_STATUS(sc->rbds,n)),
1907 sc->ie_bus_read16(sc, IE_RBD_NEXT(sc->rbds,n)),
1908 (u_long)0,/*bus_space_read_4(sc->bt, sc->bh, IE_RBD_BUFADDR(sc->rbds,n)),-* XXX */
1909 sc->ie_bus_read16(sc, IE_RBD_BUFLEN(sc->rbds,n)));
1910 }
1911 #endif
1912