if_de.c revision 131651
1/*	$NetBSD: if_de.c,v 1.86 1999/06/01 19:17:59 thorpej Exp $	*/
2/*-
3 * Copyright (c) 1994-1997 Matt Thomas (matt@3am-software.com)
4 * All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:
9 * 1. Redistributions of source code must retain the above copyright
10 *    notice, this list of conditions and the following disclaimer.
11 * 2. The name of the author may not be used to endorse or promote products
12 *    derived from this software without specific prior written permission
13 *
14 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
15 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
16 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
17 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
18 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
19 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
20 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
21 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
23 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24 *
25 * Id: if_de.c,v 1.94 1997/07/03 16:55:07 thomas Exp
26 */
27
28/*
29 * DEC 21040 PCI Ethernet Controller
30 *
31 * Written by Matt Thomas
32 * BPF support code stolen directly from if_ec.c
33 *
34 *   This driver supports the DEC DE435 or any other PCI
35 *   board which support 21040, 21041, or 21140 (mostly).
36 */
37
38#include <sys/cdefs.h>
39__FBSDID("$FreeBSD: head/sys/dev/de/if_de.c 131651 2004-07-05 22:27:26Z bms $");
40
41#define	TULIP_HDR_DATA
42
43#include <sys/param.h>
44#include <sys/systm.h>
45#include <sys/endian.h>
46#include <sys/mbuf.h>
47#include <sys/socket.h>
48#include <sys/sockio.h>
49#include <sys/malloc.h>
50#include <sys/kernel.h>
51#include <sys/module.h>
52#include <sys/eventhandler.h>
53#include <machine/bus.h>
54#include <machine/resource.h>
55#include <sys/bus.h>
56#include <sys/rman.h>
57
58#include <net/if.h>
59#include <net/if_arp.h>
60#include <net/ethernet.h>
61#include <net/if_media.h>
62#include <net/if_dl.h>
63#ifdef TULIP_USE_SOFTINTR
64#include <net/netisr.h>
65#endif
66
67#include <net/bpf.h>
68
69#ifdef INET
70#include <netinet/in.h>
71#include <netinet/if_ether.h>
72#endif
73
74#include <vm/vm.h>
75
76#include <net/if_var.h>
77#include <vm/pmap.h>
78#include <dev/pci/pcivar.h>
79#include <dev/pci/pcireg.h>
80#include <pci/dc21040reg.h>
81
82/*
83 * Intel CPUs should use I/O mapped access.
84 */
85#if defined(__i386__)
86#define	TULIP_IOMAPPED
87#endif
88
89#if 0
90/*
91 * This turns on all sort of debugging stuff and make the
92 * driver much larger.
93 */
94#define TULIP_DEBUG
95#endif
96
97#if 0
98#define	TULIP_PERFSTATS
99#endif
100
101#if 0
102#define	TULIP_USE_SOFTINTR
103#endif
104
105#define	TULIP_HZ	10
106
107#include <pci/if_devar.h>
108
109/*
110 * This module supports
111 *	the DEC 21040 PCI Ethernet Controller.
112 *	the DEC 21041 PCI Ethernet Controller.
113 *	the DEC 21140 PCI Fast Ethernet Controller.
114 */
115static void	tulip_addr_filter(tulip_softc_t * const sc);
116static void	tulip_ifinit(void *);
117static int	tulip_ifmedia_change(struct ifnet * const ifp);
118static void	tulip_ifmedia_status(struct ifnet * const ifp,
119		    struct ifmediareq *req);
120static void	tulip_ifstart_one(struct ifnet *ifp);
121static void	tulip_ifstart(struct ifnet *ifp);
122static void	tulip_init(tulip_softc_t * const sc);
123static void	tulip_intr_shared(void *arg);
124static void	tulip_intr_normal(void *arg);
125static void	tulip_mii_autonegotiate(tulip_softc_t * const sc,
126		    const unsigned phyaddr);
127static int	tulip_mii_map_abilities(tulip_softc_t * const sc,
128		    unsigned abilities);
129static tulip_media_t
130		tulip_mii_phy_readspecific(tulip_softc_t * const sc);
131static unsigned	tulip_mii_readreg(tulip_softc_t * const sc, unsigned devaddr,
132		    unsigned regno);
133static void	tulip_mii_writereg(tulip_softc_t * const sc, unsigned devaddr,
134		    unsigned regno, unsigned data);
135static void	tulip_reset(tulip_softc_t * const sc);
136static void	tulip_rx_intr(tulip_softc_t * const sc);
137static int	tulip_srom_decode(tulip_softc_t * const sc);
138static struct mbuf *
139		tulip_txput(tulip_softc_t * const sc, struct mbuf *m);
140static void	tulip_txput_setup(tulip_softc_t * const sc);
141
142static void
143tulip_timeout_callback(
144    void *arg)
145{
146    tulip_softc_t * const sc = arg;
147    int s = splimp();
148
149    TULIP_PERFSTART(timeout)
150
151    sc->tulip_flags &= ~TULIP_TIMEOUTPENDING;
152    sc->tulip_probe_timeout -= 1000 / TULIP_HZ;
153    (sc->tulip_boardsw->bd_media_poll)(sc, TULIP_MEDIAPOLL_TIMER);
154
155    TULIP_PERFEND(timeout);
156    splx(s);
157}
158
159static void
160tulip_timeout(
161    tulip_softc_t * const sc)
162{
163    if (sc->tulip_flags & TULIP_TIMEOUTPENDING)
164	return;
165    sc->tulip_flags |= TULIP_TIMEOUTPENDING;
166    timeout(tulip_timeout_callback, sc, (hz + TULIP_HZ / 2) / TULIP_HZ);
167}
168
169#if defined(TULIP_NEED_FASTTIMEOUT)
170static void
171tulip_fasttimeout_callback(
172    void *arg)
173{
174    tulip_softc_t * const sc = arg;
175    int s = splimp();
176
177    sc->tulip_flags &= ~TULIP_FASTTIMEOUTPENDING;
178    (sc->tulip_boardsw->bd_media_poll)(sc, TULIP_MEDIAPOLL_FASTTIMER);
179    splx(s);
180}
181
182static void
183tulip_fasttimeout(
184    tulip_softc_t * const sc)
185{
186    if (sc->tulip_flags & TULIP_FASTTIMEOUTPENDING)
187	return;
188    sc->tulip_flags |= TULIP_FASTTIMEOUTPENDING;
189    timeout(tulip_fasttimeout_callback, sc, 1);
190}
191#endif
192
193static int
194tulip_txprobe(
195    tulip_softc_t * const sc)
196{
197    struct mbuf *m;
198    /*
199     * Before we are sure this is the right media we need
200     * to send a small packet to make sure there's carrier.
201     * Strangely, BNC and AUI will "see" receive data if
202     * either is connected so the transmit is the only way
203     * to verify the connectivity.
204     */
205    MGETHDR(m, M_DONTWAIT, MT_DATA);
206    if (m == NULL)
207	return 0;
208    /*
209     * Construct a LLC TEST message which will point to ourselves.
210     */
211    bcopy(sc->tulip_enaddr, mtod(m, struct ether_header *)->ether_dhost, 6);
212    bcopy(sc->tulip_enaddr, mtod(m, struct ether_header *)->ether_shost, 6);
213    mtod(m, struct ether_header *)->ether_type = htons(3);
214    mtod(m, unsigned char *)[14] = 0;
215    mtod(m, unsigned char *)[15] = 0;
216    mtod(m, unsigned char *)[16] = 0xE3;	/* LLC Class1 TEST (no poll) */
217    m->m_len = m->m_pkthdr.len = sizeof(struct ether_header) + 3;
218    /*
219     * send it!
220     */
221    sc->tulip_cmdmode |= TULIP_CMD_TXRUN;
222    sc->tulip_intrmask |= TULIP_STS_TXINTR;
223    sc->tulip_flags |= TULIP_TXPROBE_ACTIVE;
224    TULIP_CSR_WRITE(sc, csr_command, sc->tulip_cmdmode);
225    TULIP_CSR_WRITE(sc, csr_intr, sc->tulip_intrmask);
226    if ((m = tulip_txput(sc, m)) != NULL)
227	m_freem(m);
228    sc->tulip_probe.probe_txprobes++;
229    return 1;
230}
231
232#ifdef BIG_PACKET
233#define TULIP_SIAGEN_WATCHDOG	(sc->tulip_if.if_mtu > ETHERMTU ? TULIP_WATCHDOG_RXDISABLE|TULIP_WATCHDOG_TXDISABLE : 0)
234#else
235#define	TULIP_SIAGEN_WATCHDOG	0
236#endif
237
238static void
239tulip_media_set(
240    tulip_softc_t * const sc,
241    tulip_media_t media)
242{
243    const tulip_media_info_t *mi = sc->tulip_mediums[media];
244
245    if (mi == NULL)
246	return;
247
248    /*
249     * If we are switching media, make sure we don't think there's
250     * any stale RX activity
251     */
252    sc->tulip_flags &= ~TULIP_RXACT;
253    if (mi->mi_type == TULIP_MEDIAINFO_SIA) {
254	TULIP_CSR_WRITE(sc, csr_sia_connectivity, TULIP_SIACONN_RESET);
255	TULIP_CSR_WRITE(sc, csr_sia_tx_rx,        mi->mi_sia_tx_rx);
256	if (sc->tulip_features & TULIP_HAVE_SIAGP) {
257	    TULIP_CSR_WRITE(sc, csr_sia_general,  mi->mi_sia_gp_control|mi->mi_sia_general|TULIP_SIAGEN_WATCHDOG);
258	    DELAY(50);
259	    TULIP_CSR_WRITE(sc, csr_sia_general,  mi->mi_sia_gp_data|mi->mi_sia_general|TULIP_SIAGEN_WATCHDOG);
260	} else {
261	    TULIP_CSR_WRITE(sc, csr_sia_general,  mi->mi_sia_general|TULIP_SIAGEN_WATCHDOG);
262	}
263	TULIP_CSR_WRITE(sc, csr_sia_connectivity, mi->mi_sia_connectivity);
264    } else if (mi->mi_type == TULIP_MEDIAINFO_GPR) {
265#define	TULIP_GPR_CMDBITS	(TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION|TULIP_CMD_SCRAMBLER|TULIP_CMD_TXTHRSHLDCTL)
266	/*
267	 * If the cmdmode bits don't match the currently operating mode,
268	 * set the cmdmode appropriately and reset the chip.
269	 */
270	if (((mi->mi_cmdmode ^ TULIP_CSR_READ(sc, csr_command)) & TULIP_GPR_CMDBITS) != 0) {
271	    sc->tulip_cmdmode &= ~TULIP_GPR_CMDBITS;
272	    sc->tulip_cmdmode |= mi->mi_cmdmode;
273	    tulip_reset(sc);
274	}
275	TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_PINSET|sc->tulip_gpinit);
276	DELAY(10);
277	TULIP_CSR_WRITE(sc, csr_gp, (u_int8_t) mi->mi_gpdata);
278    } else if (mi->mi_type == TULIP_MEDIAINFO_SYM) {
279	/*
280	 * If the cmdmode bits don't match the currently operating mode,
281	 * set the cmdmode appropriately and reset the chip.
282	 */
283	if (((mi->mi_cmdmode ^ TULIP_CSR_READ(sc, csr_command)) & TULIP_GPR_CMDBITS) != 0) {
284	    sc->tulip_cmdmode &= ~TULIP_GPR_CMDBITS;
285	    sc->tulip_cmdmode |= mi->mi_cmdmode;
286	    tulip_reset(sc);
287	}
288	TULIP_CSR_WRITE(sc, csr_sia_general, mi->mi_gpcontrol);
289	TULIP_CSR_WRITE(sc, csr_sia_general, mi->mi_gpdata);
290    } else if (mi->mi_type == TULIP_MEDIAINFO_MII
291	       && sc->tulip_probe_state != TULIP_PROBE_INACTIVE) {
292	int idx;
293	if (sc->tulip_features & TULIP_HAVE_SIAGP) {
294	    const u_int8_t *dp;
295	    dp = &sc->tulip_rombuf[mi->mi_reset_offset];
296	    for (idx = 0; idx < mi->mi_reset_length; idx++, dp += 2) {
297		DELAY(10);
298		TULIP_CSR_WRITE(sc, csr_sia_general, (dp[0] + 256 * dp[1]) << 16);
299	    }
300	    sc->tulip_phyaddr = mi->mi_phyaddr;
301	    dp = &sc->tulip_rombuf[mi->mi_gpr_offset];
302	    for (idx = 0; idx < mi->mi_gpr_length; idx++, dp += 2) {
303		DELAY(10);
304		TULIP_CSR_WRITE(sc, csr_sia_general, (dp[0] + 256 * dp[1]) << 16);
305	    }
306	} else {
307	    for (idx = 0; idx < mi->mi_reset_length; idx++) {
308		DELAY(10);
309		TULIP_CSR_WRITE(sc, csr_gp, sc->tulip_rombuf[mi->mi_reset_offset + idx]);
310	    }
311	    sc->tulip_phyaddr = mi->mi_phyaddr;
312	    for (idx = 0; idx < mi->mi_gpr_length; idx++) {
313		DELAY(10);
314		TULIP_CSR_WRITE(sc, csr_gp, sc->tulip_rombuf[mi->mi_gpr_offset + idx]);
315	    }
316	}
317	if (sc->tulip_flags & TULIP_TRYNWAY) {
318	    tulip_mii_autonegotiate(sc, sc->tulip_phyaddr);
319	} else if ((sc->tulip_flags & TULIP_DIDNWAY) == 0) {
320	    u_int32_t data = tulip_mii_readreg(sc, sc->tulip_phyaddr, PHYREG_CONTROL);
321	    data &= ~(PHYCTL_SELECT_100MB|PHYCTL_FULL_DUPLEX|PHYCTL_AUTONEG_ENABLE);
322	    sc->tulip_flags &= ~TULIP_DIDNWAY;
323	    if (TULIP_IS_MEDIA_FD(media))
324		data |= PHYCTL_FULL_DUPLEX;
325	    if (TULIP_IS_MEDIA_100MB(media))
326		data |= PHYCTL_SELECT_100MB;
327	    tulip_mii_writereg(sc, sc->tulip_phyaddr, PHYREG_CONTROL, data);
328	}
329    }
330}
331
332static void
333tulip_linkup(
334    tulip_softc_t * const sc,
335    tulip_media_t media)
336{
337    if ((sc->tulip_flags & TULIP_LINKUP) == 0)
338	sc->tulip_flags |= TULIP_PRINTLINKUP;
339    sc->tulip_flags |= TULIP_LINKUP;
340    sc->tulip_if.if_flags &= ~IFF_OACTIVE;
341#if 0 /* XXX how does with work with ifmedia? */
342    if ((sc->tulip_flags & TULIP_DIDNWAY) == 0) {
343	if (sc->tulip_if.if_flags & IFF_FULLDUPLEX) {
344	    if (TULIP_CAN_MEDIA_FD(media)
345		    && sc->tulip_mediums[TULIP_FD_MEDIA_OF(media)] != NULL)
346		media = TULIP_FD_MEDIA_OF(media);
347	} else {
348	    if (TULIP_IS_MEDIA_FD(media)
349		    && sc->tulip_mediums[TULIP_HD_MEDIA_OF(media)] != NULL)
350		media = TULIP_HD_MEDIA_OF(media);
351	}
352    }
353#endif
354    if (sc->tulip_media != media) {
355#ifdef TULIP_DEBUG
356	sc->tulip_dbg.dbg_last_media = sc->tulip_media;
357#endif
358	sc->tulip_media = media;
359	sc->tulip_flags |= TULIP_PRINTMEDIA;
360	if (TULIP_IS_MEDIA_FD(sc->tulip_media)) {
361	    sc->tulip_cmdmode |= TULIP_CMD_FULLDUPLEX;
362	} else if (sc->tulip_chipid != TULIP_21041 || (sc->tulip_flags & TULIP_DIDNWAY) == 0) {
363	    sc->tulip_cmdmode &= ~TULIP_CMD_FULLDUPLEX;
364	}
365    }
366    /*
367     * We could set probe_timeout to 0 but setting to 3000 puts this
368     * in one central place and the only matters is tulip_link is
369     * followed by a tulip_timeout.  Therefore setting it should not
370     * result in aberrant behavour.
371     */
372    sc->tulip_probe_timeout = 3000;
373    sc->tulip_probe_state = TULIP_PROBE_INACTIVE;
374    sc->tulip_flags &= ~(TULIP_TXPROBE_ACTIVE|TULIP_TRYNWAY);
375    if (sc->tulip_flags & TULIP_INRESET) {
376	tulip_media_set(sc, sc->tulip_media);
377    } else if (sc->tulip_probe_media != sc->tulip_media) {
378	/*
379	 * No reason to change media if we have the right media.
380	 */
381	tulip_reset(sc);
382    }
383    tulip_init(sc);
384}
385
386static void
387tulip_media_print(
388    tulip_softc_t * const sc)
389{
390    if ((sc->tulip_flags & TULIP_LINKUP) == 0)
391	return;
392    if (sc->tulip_flags & TULIP_PRINTMEDIA) {
393	printf("%s: enabling %s port\n",
394	       sc->tulip_xname,
395	       tulip_mediums[sc->tulip_media]);
396	sc->tulip_flags &= ~(TULIP_PRINTMEDIA|TULIP_PRINTLINKUP);
397    } else if (sc->tulip_flags & TULIP_PRINTLINKUP) {
398	printf("%s: link up\n", sc->tulip_xname);
399	sc->tulip_flags &= ~TULIP_PRINTLINKUP;
400    }
401}
402
403#if defined(TULIP_DO_GPR_SENSE)
404static tulip_media_t
405tulip_21140_gpr_media_sense(
406    tulip_softc_t * const sc)
407{
408    tulip_media_t maybe_media = TULIP_MEDIA_UNKNOWN;
409    tulip_media_t last_media = TULIP_MEDIA_UNKNOWN;
410    tulip_media_t media;
411
412    /*
413     * If one of the media blocks contained a default media flag,
414     * use that.
415     */
416    for (media = TULIP_MEDIA_UNKNOWN; media < TULIP_MEDIA_MAX; media++) {
417	const tulip_media_info_t *mi;
418	/*
419	 * Media is not supported (or is full-duplex).
420	 */
421	if ((mi = sc->tulip_mediums[media]) == NULL || TULIP_IS_MEDIA_FD(media))
422	    continue;
423	if (mi->mi_type != TULIP_MEDIAINFO_GPR)
424	    continue;
425
426	/*
427	 * Remember the media is this is the "default" media.
428	 */
429	if (mi->mi_default && maybe_media == TULIP_MEDIA_UNKNOWN)
430	    maybe_media = media;
431
432	/*
433	 * No activity mask?  Can't see if it is active if there's no mask.
434	 */
435	if (mi->mi_actmask == 0)
436	    continue;
437
438	/*
439	 * Does the activity data match?
440	 */
441	if ((TULIP_CSR_READ(sc, csr_gp) & mi->mi_actmask) != mi->mi_actdata)
442	    continue;
443
444#if defined(TULIP_DEBUG)
445	printf("%s: gpr_media_sense: %s: 0x%02x & 0x%02x == 0x%02x\n",
446	       sc->tulip_xname, tulip_mediums[media],
447	       TULIP_CSR_READ(sc, csr_gp) & 0xFF,
448	       mi->mi_actmask, mi->mi_actdata);
449#endif
450	/*
451	 * It does!  If this is the first media we detected, then
452	 * remember this media.  If isn't the first, then there were
453	 * multiple matches which we equate to no match (since we don't
454	 * which to select (if any).
455	 */
456	if (last_media == TULIP_MEDIA_UNKNOWN) {
457	    last_media = media;
458	} else if (last_media != media) {
459	    last_media = TULIP_MEDIA_UNKNOWN;
460	}
461    }
462    return (last_media != TULIP_MEDIA_UNKNOWN) ? last_media : maybe_media;
463}
464#endif /* TULIP_DO_GPR_SENSE */
465
466static tulip_link_status_t
467tulip_media_link_monitor(
468    tulip_softc_t * const sc)
469{
470    const tulip_media_info_t * const mi = sc->tulip_mediums[sc->tulip_media];
471    tulip_link_status_t linkup = TULIP_LINK_DOWN;
472
473    if (mi == NULL) {
474#if defined(DIAGNOSTIC) || defined(TULIP_DEBUG)
475	panic("tulip_media_link_monitor: %s: botch at line %d\n",
476	      tulip_mediums[sc->tulip_media],__LINE__);
477#else
478	return TULIP_LINK_UNKNOWN;
479#endif
480    }
481
482
483    /*
484     * Have we seen some packets?  If so, the link must be good.
485     */
486    if ((sc->tulip_flags & (TULIP_RXACT|TULIP_LINKUP)) == (TULIP_RXACT|TULIP_LINKUP)) {
487	sc->tulip_flags &= ~TULIP_RXACT;
488	sc->tulip_probe_timeout = 3000;
489	return TULIP_LINK_UP;
490    }
491
492    sc->tulip_flags &= ~TULIP_RXACT;
493    if (mi->mi_type == TULIP_MEDIAINFO_MII) {
494	u_int32_t status;
495	/*
496	 * Read the PHY status register.
497	 */
498	status = tulip_mii_readreg(sc, sc->tulip_phyaddr, PHYREG_STATUS);
499	if (status & PHYSTS_AUTONEG_DONE) {
500	    /*
501	     * If the PHY has completed autonegotiation, see the if the
502	     * remote systems abilities have changed.  If so, upgrade or
503	     * downgrade as appropriate.
504	     */
505	    u_int32_t abilities = tulip_mii_readreg(sc, sc->tulip_phyaddr, PHYREG_AUTONEG_ABILITIES);
506	    abilities = (abilities << 6) & status;
507	    if (abilities != sc->tulip_abilities) {
508#if defined(TULIP_DEBUG)
509		loudprintf("%s(phy%d): autonegotiation changed: 0x%04x -> 0x%04x\n",
510			   sc->tulip_xname, sc->tulip_phyaddr,
511			   sc->tulip_abilities, abilities);
512#endif
513		if (tulip_mii_map_abilities(sc, abilities)) {
514		    tulip_linkup(sc, sc->tulip_probe_media);
515		    return TULIP_LINK_UP;
516		}
517		/*
518		 * if we had selected media because of autonegotiation,
519		 * we need to probe for the new media.
520		 */
521		sc->tulip_probe_state = TULIP_PROBE_INACTIVE;
522		if (sc->tulip_flags & TULIP_DIDNWAY)
523		    return TULIP_LINK_DOWN;
524	    }
525	}
526	/*
527	 * The link is now up.  If was down, say its back up.
528	 */
529	if ((status & (PHYSTS_LINK_UP|PHYSTS_REMOTE_FAULT)) == PHYSTS_LINK_UP)
530	    linkup = TULIP_LINK_UP;
531    } else if (mi->mi_type == TULIP_MEDIAINFO_GPR) {
532	/*
533	 * No activity sensor?  Assume all's well.
534	 */
535	if (mi->mi_actmask == 0)
536	    return TULIP_LINK_UNKNOWN;
537	/*
538	 * Does the activity data match?
539	 */
540	if ((TULIP_CSR_READ(sc, csr_gp) & mi->mi_actmask) == mi->mi_actdata)
541	    linkup = TULIP_LINK_UP;
542    } else if (mi->mi_type == TULIP_MEDIAINFO_SIA) {
543	/*
544	 * Assume non TP ok for now.
545	 */
546	if (!TULIP_IS_MEDIA_TP(sc->tulip_media))
547	    return TULIP_LINK_UNKNOWN;
548	if ((TULIP_CSR_READ(sc, csr_sia_status) & TULIP_SIASTS_LINKFAIL) == 0)
549	    linkup = TULIP_LINK_UP;
550#if defined(TULIP_DEBUG)
551	if (sc->tulip_probe_timeout <= 0)
552	    printf("%s: sia status = 0x%08x\n", sc->tulip_xname,
553		    TULIP_CSR_READ(sc, csr_sia_status));
554#endif
555    } else if (mi->mi_type == TULIP_MEDIAINFO_SYM) {
556	return TULIP_LINK_UNKNOWN;
557    }
558    /*
559     * We will wait for 3 seconds until the link goes into suspect mode.
560     */
561    if (sc->tulip_flags & TULIP_LINKUP) {
562	if (linkup == TULIP_LINK_UP)
563	    sc->tulip_probe_timeout = 3000;
564	if (sc->tulip_probe_timeout > 0)
565	    return TULIP_LINK_UP;
566
567	sc->tulip_flags &= ~TULIP_LINKUP;
568	printf("%s: link down: cable problem?\n", sc->tulip_xname);
569    }
570#if defined(TULIP_DEBUG)
571    sc->tulip_dbg.dbg_link_downed++;
572#endif
573    return TULIP_LINK_DOWN;
574}
575
576static void
577tulip_media_poll(
578    tulip_softc_t * const sc,
579    tulip_mediapoll_event_t event)
580{
581#if defined(TULIP_DEBUG)
582    sc->tulip_dbg.dbg_events[event]++;
583#endif
584    if (sc->tulip_probe_state == TULIP_PROBE_INACTIVE
585	    && event == TULIP_MEDIAPOLL_TIMER) {
586	switch (tulip_media_link_monitor(sc)) {
587	    case TULIP_LINK_DOWN: {
588		/*
589		 * Link Monitor failed.  Probe for new media.
590		 */
591		event = TULIP_MEDIAPOLL_LINKFAIL;
592		break;
593	    }
594	    case TULIP_LINK_UP: {
595		/*
596		 * Check again soon.
597		 */
598		tulip_timeout(sc);
599		return;
600	    }
601	    case TULIP_LINK_UNKNOWN: {
602		/*
603		 * We can't tell so don't bother.
604		 */
605		return;
606	    }
607	}
608    }
609
610    if (event == TULIP_MEDIAPOLL_LINKFAIL) {
611	if (sc->tulip_probe_state == TULIP_PROBE_INACTIVE) {
612	    if (TULIP_DO_AUTOSENSE(sc)) {
613#if defined(TULIP_DEBUG)
614		sc->tulip_dbg.dbg_link_failures++;
615#endif
616		sc->tulip_media = TULIP_MEDIA_UNKNOWN;
617		if (sc->tulip_if.if_flags & IFF_UP)
618		    tulip_reset(sc);	/* restart probe */
619	    }
620	    return;
621	}
622#if defined(TULIP_DEBUG)
623	sc->tulip_dbg.dbg_link_pollintrs++;
624#endif
625    }
626
627    if (event == TULIP_MEDIAPOLL_START) {
628	sc->tulip_if.if_flags |= IFF_OACTIVE;
629	if (sc->tulip_probe_state != TULIP_PROBE_INACTIVE)
630	    return;
631	sc->tulip_probe_mediamask = 0;
632	sc->tulip_probe_passes = 0;
633#if defined(TULIP_DEBUG)
634	sc->tulip_dbg.dbg_media_probes++;
635#endif
636	/*
637	 * If the SROM contained an explicit media to use, use it.
638	 */
639	sc->tulip_cmdmode &= ~(TULIP_CMD_RXRUN|TULIP_CMD_FULLDUPLEX);
640	sc->tulip_flags |= TULIP_TRYNWAY|TULIP_PROBE1STPASS;
641	sc->tulip_flags &= ~(TULIP_DIDNWAY|TULIP_PRINTMEDIA|TULIP_PRINTLINKUP);
642	/*
643	 * connidx is defaulted to a media_unknown type.
644	 */
645	sc->tulip_probe_media = tulip_srom_conninfo[sc->tulip_connidx].sc_media;
646	if (sc->tulip_probe_media != TULIP_MEDIA_UNKNOWN) {
647	    tulip_linkup(sc, sc->tulip_probe_media);
648	    tulip_timeout(sc);
649	    return;
650	}
651
652	if (sc->tulip_features & TULIP_HAVE_GPR) {
653	    sc->tulip_probe_state = TULIP_PROBE_GPRTEST;
654	    sc->tulip_probe_timeout = 2000;
655	} else {
656	    sc->tulip_probe_media = TULIP_MEDIA_MAX;
657	    sc->tulip_probe_timeout = 0;
658	    sc->tulip_probe_state = TULIP_PROBE_MEDIATEST;
659	}
660    }
661
662    /*
663     * Ignore txprobe failures or spurious callbacks.
664     */
665    if (event == TULIP_MEDIAPOLL_TXPROBE_FAILED
666	    && sc->tulip_probe_state != TULIP_PROBE_MEDIATEST) {
667	sc->tulip_flags &= ~TULIP_TXPROBE_ACTIVE;
668	return;
669    }
670
671    /*
672     * If we really transmitted a packet, then that's the media we'll use.
673     */
674    if (event == TULIP_MEDIAPOLL_TXPROBE_OK || event == TULIP_MEDIAPOLL_LINKPASS) {
675	if (event == TULIP_MEDIAPOLL_LINKPASS) {
676	    /* XXX Check media status just to be sure */
677	    sc->tulip_probe_media = TULIP_MEDIA_10BASET;
678#if defined(TULIP_DEBUG)
679	} else {
680	    sc->tulip_dbg.dbg_txprobes_ok[sc->tulip_probe_media]++;
681#endif
682	}
683	tulip_linkup(sc, sc->tulip_probe_media);
684	tulip_timeout(sc);
685	return;
686    }
687
688    if (sc->tulip_probe_state == TULIP_PROBE_GPRTEST) {
689#if defined(TULIP_DO_GPR_SENSE)
690	/*
691	 * Check for media via the general purpose register.
692	 *
693	 * Try to sense the media via the GPR.  If the same value
694	 * occurs 3 times in a row then just use that.
695	 */
696	if (sc->tulip_probe_timeout > 0) {
697	    tulip_media_t new_probe_media = tulip_21140_gpr_media_sense(sc);
698#if defined(TULIP_DEBUG)
699	    printf("%s: media_poll: gpr sensing = %s\n",
700		   sc->tulip_xname, tulip_mediums[new_probe_media]);
701#endif
702	    if (new_probe_media != TULIP_MEDIA_UNKNOWN) {
703		if (new_probe_media == sc->tulip_probe_media) {
704		    if (--sc->tulip_probe_count == 0)
705			tulip_linkup(sc, sc->tulip_probe_media);
706		} else {
707		    sc->tulip_probe_count = 10;
708		}
709	    }
710	    sc->tulip_probe_media = new_probe_media;
711	    tulip_timeout(sc);
712	    return;
713	}
714#endif /* TULIP_DO_GPR_SENSE */
715	/*
716	 * Brute force.  We cycle through each of the media types
717	 * and try to transmit a packet.
718	 */
719	sc->tulip_probe_state = TULIP_PROBE_MEDIATEST;
720	sc->tulip_probe_media = TULIP_MEDIA_MAX;
721	sc->tulip_probe_timeout = 0;
722	tulip_timeout(sc);
723	return;
724    }
725
726    if (sc->tulip_probe_state != TULIP_PROBE_MEDIATEST
727	   && (sc->tulip_features & TULIP_HAVE_MII)) {
728	tulip_media_t old_media = sc->tulip_probe_media;
729	tulip_mii_autonegotiate(sc, sc->tulip_phyaddr);
730	switch (sc->tulip_probe_state) {
731	    case TULIP_PROBE_FAILED:
732	    case TULIP_PROBE_MEDIATEST: {
733		/*
734		 * Try the next media.
735		 */
736		sc->tulip_probe_mediamask |= sc->tulip_mediums[sc->tulip_probe_media]->mi_mediamask;
737		sc->tulip_probe_timeout = 0;
738#ifdef notyet
739		if (sc->tulip_probe_state == TULIP_PROBE_FAILED)
740		    break;
741		if (sc->tulip_probe_media != tulip_mii_phy_readspecific(sc))
742		    break;
743		sc->tulip_probe_timeout = TULIP_IS_MEDIA_TP(sc->tulip_probe_media) ? 2500 : 300;
744#endif
745		break;
746	    }
747	    case TULIP_PROBE_PHYAUTONEG: {
748		return;
749	    }
750	    case TULIP_PROBE_INACTIVE: {
751		/*
752		 * Only probe if we autonegotiated a media that hasn't failed.
753		 */
754		sc->tulip_probe_timeout = 0;
755		if (sc->tulip_probe_mediamask & TULIP_BIT(sc->tulip_probe_media)) {
756		    sc->tulip_probe_media = old_media;
757		    break;
758		}
759		tulip_linkup(sc, sc->tulip_probe_media);
760		tulip_timeout(sc);
761		return;
762	    }
763	    default: {
764#if defined(DIAGNOSTIC) || defined(TULIP_DEBUG)
765		panic("tulip_media_poll: botch at line %d\n", __LINE__);
766#endif
767		break;
768	    }
769	}
770    }
771
772    if (event == TULIP_MEDIAPOLL_TXPROBE_FAILED) {
773#if defined(TULIP_DEBUG)
774	sc->tulip_dbg.dbg_txprobes_failed[sc->tulip_probe_media]++;
775#endif
776	sc->tulip_flags &= ~TULIP_TXPROBE_ACTIVE;
777	return;
778    }
779
780    /*
781     * switch to another media if we tried this one enough.
782     */
783    if (/* event == TULIP_MEDIAPOLL_TXPROBE_FAILED || */ sc->tulip_probe_timeout <= 0) {
784#if defined(TULIP_DEBUG)
785	if (sc->tulip_probe_media == TULIP_MEDIA_UNKNOWN) {
786	    printf("%s: poll media unknown!\n",
787		   sc->tulip_xname);
788	    sc->tulip_probe_media = TULIP_MEDIA_MAX;
789	}
790#endif
791	/*
792	 * Find the next media type to check for.  Full Duplex
793	 * types are not allowed.
794	 */
795	do {
796	    sc->tulip_probe_media -= 1;
797	    if (sc->tulip_probe_media == TULIP_MEDIA_UNKNOWN) {
798		if (++sc->tulip_probe_passes == 3) {
799		    printf("%s: autosense failed: cable problem?\n",
800			   sc->tulip_xname);
801		    if ((sc->tulip_if.if_flags & IFF_UP) == 0) {
802			sc->tulip_if.if_flags &= ~IFF_RUNNING;
803			sc->tulip_probe_state = TULIP_PROBE_INACTIVE;
804			return;
805		    }
806		}
807		sc->tulip_flags ^= TULIP_TRYNWAY;	/* XXX */
808		sc->tulip_probe_mediamask = 0;
809		sc->tulip_probe_media = TULIP_MEDIA_MAX - 1;
810	    }
811	} while (sc->tulip_mediums[sc->tulip_probe_media] == NULL
812		 || (sc->tulip_probe_mediamask & TULIP_BIT(sc->tulip_probe_media))
813		 || TULIP_IS_MEDIA_FD(sc->tulip_probe_media));
814
815#if defined(TULIP_DEBUG)
816	printf("%s: %s: probing %s\n", sc->tulip_xname,
817	       event == TULIP_MEDIAPOLL_TXPROBE_FAILED ? "txprobe failed" : "timeout",
818	       tulip_mediums[sc->tulip_probe_media]);
819#endif
820	sc->tulip_probe_timeout = TULIP_IS_MEDIA_TP(sc->tulip_probe_media) ? 2500 : 1000;
821	sc->tulip_probe_state = TULIP_PROBE_MEDIATEST;
822	sc->tulip_probe.probe_txprobes = 0;
823	tulip_reset(sc);
824	tulip_media_set(sc, sc->tulip_probe_media);
825	sc->tulip_flags &= ~TULIP_TXPROBE_ACTIVE;
826    }
827    tulip_timeout(sc);
828
829    /*
830     * If this is hanging off a phy, we know are doing NWAY and we have
831     * forced the phy to a specific speed.  Wait for link up before
832     * before sending a packet.
833     */
834    switch (sc->tulip_mediums[sc->tulip_probe_media]->mi_type) {
835	case TULIP_MEDIAINFO_MII: {
836	    if (sc->tulip_probe_media != tulip_mii_phy_readspecific(sc))
837		return;
838	    break;
839	}
840	case TULIP_MEDIAINFO_SIA: {
841	    if (TULIP_IS_MEDIA_TP(sc->tulip_probe_media)) {
842		if (TULIP_CSR_READ(sc, csr_sia_status) & TULIP_SIASTS_LINKFAIL)
843		    return;
844		tulip_linkup(sc, sc->tulip_probe_media);
845#ifdef notyet
846		if (sc->tulip_features & TULIP_HAVE_MII)
847		    tulip_timeout(sc);
848#endif
849		return;
850	    }
851	    break;
852	}
853	case TULIP_MEDIAINFO_RESET:
854	case TULIP_MEDIAINFO_SYM:
855	case TULIP_MEDIAINFO_NONE:
856	case TULIP_MEDIAINFO_GPR: {
857	    break;
858	}
859    }
860    /*
861     * Try to send a packet.
862     */
863    tulip_txprobe(sc);
864}
865
866static void
867tulip_media_select(
868    tulip_softc_t * const sc)
869{
870    if (sc->tulip_features & TULIP_HAVE_GPR) {
871	TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_PINSET|sc->tulip_gpinit);
872	DELAY(10);
873	TULIP_CSR_WRITE(sc, csr_gp, sc->tulip_gpdata);
874    }
875    /*
876     * If this board has no media, just return
877     */
878    if (sc->tulip_features & TULIP_HAVE_NOMEDIA)
879	return;
880
881    if (sc->tulip_media == TULIP_MEDIA_UNKNOWN) {
882	TULIP_CSR_WRITE(sc, csr_intr, sc->tulip_intrmask);
883	(*sc->tulip_boardsw->bd_media_poll)(sc, TULIP_MEDIAPOLL_START);
884    } else {
885	tulip_media_set(sc, sc->tulip_media);
886    }
887}
888
889static void
890tulip_21040_mediainfo_init(
891    tulip_softc_t * const sc,
892    tulip_media_t media)
893{
894    sc->tulip_cmdmode |= TULIP_CMD_CAPTREFFCT|TULIP_CMD_THRSHLD160
895	|TULIP_CMD_BACKOFFCTR;
896    sc->tulip_if.if_baudrate = 10000000;
897
898    if (media == TULIP_MEDIA_10BASET || media == TULIP_MEDIA_UNKNOWN) {
899	TULIP_MEDIAINFO_SIA_INIT(sc, &sc->tulip_mediainfo[0], 21040, 10BASET);
900	TULIP_MEDIAINFO_SIA_INIT(sc, &sc->tulip_mediainfo[1], 21040, 10BASET_FD);
901	sc->tulip_intrmask |= TULIP_STS_LINKPASS|TULIP_STS_LINKFAIL;
902    }
903
904    if (media == TULIP_MEDIA_AUIBNC || media == TULIP_MEDIA_UNKNOWN) {
905	TULIP_MEDIAINFO_SIA_INIT(sc, &sc->tulip_mediainfo[2], 21040, AUIBNC);
906    }
907
908    if (media == TULIP_MEDIA_UNKNOWN) {
909	TULIP_MEDIAINFO_SIA_INIT(sc, &sc->tulip_mediainfo[3], 21040, EXTSIA);
910    }
911}
912
913static void
914tulip_21040_media_probe(
915    tulip_softc_t * const sc)
916{
917    tulip_21040_mediainfo_init(sc, TULIP_MEDIA_UNKNOWN);
918    return;
919}
920
921static void
922tulip_21040_10baset_only_media_probe(
923    tulip_softc_t * const sc)
924{
925    tulip_21040_mediainfo_init(sc, TULIP_MEDIA_10BASET);
926    tulip_media_set(sc, TULIP_MEDIA_10BASET);
927    sc->tulip_media = TULIP_MEDIA_10BASET;
928}
929
930static void
931tulip_21040_10baset_only_media_select(
932    tulip_softc_t * const sc)
933{
934    sc->tulip_flags |= TULIP_LINKUP;
935    if (sc->tulip_media == TULIP_MEDIA_10BASET_FD) {
936	sc->tulip_cmdmode |= TULIP_CMD_FULLDUPLEX;
937	sc->tulip_flags &= ~TULIP_SQETEST;
938    } else {
939	sc->tulip_cmdmode &= ~TULIP_CMD_FULLDUPLEX;
940	sc->tulip_flags |= TULIP_SQETEST;
941    }
942    tulip_media_set(sc, sc->tulip_media);
943}
944
945static void
946tulip_21040_auibnc_only_media_probe(
947    tulip_softc_t * const sc)
948{
949    tulip_21040_mediainfo_init(sc, TULIP_MEDIA_AUIBNC);
950    sc->tulip_flags |= TULIP_SQETEST|TULIP_LINKUP;
951    tulip_media_set(sc, TULIP_MEDIA_AUIBNC);
952    sc->tulip_media = TULIP_MEDIA_AUIBNC;
953}
954
955static void
956tulip_21040_auibnc_only_media_select(
957    tulip_softc_t * const sc)
958{
959    tulip_media_set(sc, TULIP_MEDIA_AUIBNC);
960    sc->tulip_cmdmode &= ~TULIP_CMD_FULLDUPLEX;
961}
962
963static const tulip_boardsw_t tulip_21040_boardsw = {
964    TULIP_21040_GENERIC,
965    tulip_21040_media_probe,
966    tulip_media_select,
967    tulip_media_poll,
968};
969
970static const tulip_boardsw_t tulip_21040_10baset_only_boardsw = {
971    TULIP_21040_GENERIC,
972    tulip_21040_10baset_only_media_probe,
973    tulip_21040_10baset_only_media_select,
974    NULL,
975};
976
977static const tulip_boardsw_t tulip_21040_auibnc_only_boardsw = {
978    TULIP_21040_GENERIC,
979    tulip_21040_auibnc_only_media_probe,
980    tulip_21040_auibnc_only_media_select,
981    NULL,
982};
983
984static void
985tulip_21041_mediainfo_init(
986    tulip_softc_t * const sc)
987{
988    tulip_media_info_t * const mi = sc->tulip_mediainfo;
989
990#ifdef notyet
991    if (sc->tulip_revinfo >= 0x20) {
992	TULIP_MEDIAINFO_SIA_INIT(sc, &mi[0], 21041P2, 10BASET);
993	TULIP_MEDIAINFO_SIA_INIT(sc, &mi[1], 21041P2, 10BASET_FD);
994	TULIP_MEDIAINFO_SIA_INIT(sc, &mi[0], 21041P2, AUI);
995	TULIP_MEDIAINFO_SIA_INIT(sc, &mi[1], 21041P2, BNC);
996	return;
997    }
998#endif
999    TULIP_MEDIAINFO_SIA_INIT(sc, &mi[0], 21041, 10BASET);
1000    TULIP_MEDIAINFO_SIA_INIT(sc, &mi[1], 21041, 10BASET_FD);
1001    TULIP_MEDIAINFO_SIA_INIT(sc, &mi[2], 21041, AUI);
1002    TULIP_MEDIAINFO_SIA_INIT(sc, &mi[3], 21041, BNC);
1003}
1004
1005static void
1006tulip_21041_media_probe(
1007    tulip_softc_t * const sc)
1008{
1009    sc->tulip_if.if_baudrate = 10000000;
1010    sc->tulip_cmdmode |= TULIP_CMD_CAPTREFFCT|TULIP_CMD_ENHCAPTEFFCT
1011	|TULIP_CMD_THRSHLD160|TULIP_CMD_BACKOFFCTR;
1012    sc->tulip_intrmask |= TULIP_STS_LINKPASS|TULIP_STS_LINKFAIL;
1013    tulip_21041_mediainfo_init(sc);
1014}
1015
1016static void
1017tulip_21041_media_poll(
1018    tulip_softc_t * const sc,
1019    const tulip_mediapoll_event_t event)
1020{
1021    u_int32_t sia_status;
1022
1023#if defined(TULIP_DEBUG)
1024    sc->tulip_dbg.dbg_events[event]++;
1025#endif
1026
1027    if (event == TULIP_MEDIAPOLL_LINKFAIL) {
1028	if (sc->tulip_probe_state != TULIP_PROBE_INACTIVE
1029		|| !TULIP_DO_AUTOSENSE(sc))
1030	    return;
1031	sc->tulip_media = TULIP_MEDIA_UNKNOWN;
1032	tulip_reset(sc);	/* start probe */
1033	return;
1034    }
1035
1036    /*
1037     * If we've been been asked to start a poll or link change interrupt
1038     * restart the probe (and reset the tulip to a known state).
1039     */
1040    if (event == TULIP_MEDIAPOLL_START) {
1041	sc->tulip_if.if_flags |= IFF_OACTIVE;
1042	sc->tulip_cmdmode &= ~(TULIP_CMD_FULLDUPLEX|TULIP_CMD_RXRUN);
1043#ifdef notyet
1044	if (sc->tulip_revinfo >= 0x20) {
1045	    sc->tulip_cmdmode |= TULIP_CMD_FULLDUPLEX;
1046	    sc->tulip_flags |= TULIP_DIDNWAY;
1047	}
1048#endif
1049	TULIP_CSR_WRITE(sc, csr_command, sc->tulip_cmdmode);
1050	sc->tulip_probe_state = TULIP_PROBE_MEDIATEST;
1051	sc->tulip_probe_media = TULIP_MEDIA_10BASET;
1052	sc->tulip_probe_timeout = TULIP_21041_PROBE_10BASET_TIMEOUT;
1053	tulip_media_set(sc, TULIP_MEDIA_10BASET);
1054	tulip_timeout(sc);
1055	return;
1056    }
1057
1058    if (sc->tulip_probe_state == TULIP_PROBE_INACTIVE)
1059	return;
1060
1061    if (event == TULIP_MEDIAPOLL_TXPROBE_OK) {
1062#if defined(TULIP_DEBUG)
1063	sc->tulip_dbg.dbg_txprobes_ok[sc->tulip_probe_media]++;
1064#endif
1065	tulip_linkup(sc, sc->tulip_probe_media);
1066	return;
1067    }
1068
1069    sia_status = TULIP_CSR_READ(sc, csr_sia_status);
1070    TULIP_CSR_WRITE(sc, csr_sia_status, sia_status);
1071    if ((sia_status & TULIP_SIASTS_LINKFAIL) == 0) {
1072	if (sc->tulip_revinfo >= 0x20) {
1073	    if (sia_status & (PHYSTS_10BASET_FD << (16 - 6)))
1074		sc->tulip_probe_media = TULIP_MEDIA_10BASET_FD;
1075	}
1076	/*
1077	 * If the link has passed LinkPass, 10baseT is the
1078	 * proper media to use.
1079	 */
1080	tulip_linkup(sc, sc->tulip_probe_media);
1081	return;
1082    }
1083
1084    /*
1085     * wait for up to 2.4 seconds for the link to reach pass state.
1086     * Only then start scanning the other media for activity.
1087     * choose media with receive activity over those without.
1088     */
1089    if (sc->tulip_probe_media == TULIP_MEDIA_10BASET) {
1090	if (event != TULIP_MEDIAPOLL_TIMER)
1091	    return;
1092	if (sc->tulip_probe_timeout > 0
1093		&& (sia_status & TULIP_SIASTS_OTHERRXACTIVITY) == 0) {
1094	    tulip_timeout(sc);
1095	    return;
1096	}
1097	sc->tulip_probe_timeout = TULIP_21041_PROBE_AUIBNC_TIMEOUT;
1098	sc->tulip_flags |= TULIP_WANTRXACT;
1099	if (sia_status & TULIP_SIASTS_OTHERRXACTIVITY) {
1100	    sc->tulip_probe_media = TULIP_MEDIA_BNC;
1101	} else {
1102	    sc->tulip_probe_media = TULIP_MEDIA_AUI;
1103	}
1104	tulip_media_set(sc, sc->tulip_probe_media);
1105	tulip_timeout(sc);
1106	return;
1107    }
1108
1109    /*
1110     * If we failed, clear the txprobe active flag.
1111     */
1112    if (event == TULIP_MEDIAPOLL_TXPROBE_FAILED)
1113	sc->tulip_flags &= ~TULIP_TXPROBE_ACTIVE;
1114
1115
1116    if (event == TULIP_MEDIAPOLL_TIMER) {
1117	/*
1118	 * If we've received something, then that's our link!
1119	 */
1120	if (sc->tulip_flags & TULIP_RXACT) {
1121	    tulip_linkup(sc, sc->tulip_probe_media);
1122	    return;
1123	}
1124	/*
1125	 * if no txprobe active
1126	 */
1127	if ((sc->tulip_flags & TULIP_TXPROBE_ACTIVE) == 0
1128		&& ((sc->tulip_flags & TULIP_WANTRXACT) == 0
1129		    || (sia_status & TULIP_SIASTS_RXACTIVITY))) {
1130	    sc->tulip_probe_timeout = TULIP_21041_PROBE_AUIBNC_TIMEOUT;
1131	    tulip_txprobe(sc);
1132	    tulip_timeout(sc);
1133	    return;
1134	}
1135	/*
1136	 * Take 2 passes through before deciding to not
1137	 * wait for receive activity.  Then take another
1138	 * two passes before spitting out a warning.
1139	 */
1140	if (sc->tulip_probe_timeout <= 0) {
1141	    if (sc->tulip_flags & TULIP_WANTRXACT) {
1142		sc->tulip_flags &= ~TULIP_WANTRXACT;
1143		sc->tulip_probe_timeout = TULIP_21041_PROBE_AUIBNC_TIMEOUT;
1144	    } else {
1145		printf("%s: autosense failed: cable problem?\n",
1146		       sc->tulip_xname);
1147		if ((sc->tulip_if.if_flags & IFF_UP) == 0) {
1148		    sc->tulip_if.if_flags &= ~IFF_RUNNING;
1149		    sc->tulip_probe_state = TULIP_PROBE_INACTIVE;
1150		    return;
1151		}
1152	    }
1153	}
1154    }
1155
1156    /*
1157     * Since this media failed to probe, try the other one.
1158     */
1159    sc->tulip_probe_timeout = TULIP_21041_PROBE_AUIBNC_TIMEOUT;
1160    if (sc->tulip_probe_media == TULIP_MEDIA_AUI) {
1161	sc->tulip_probe_media = TULIP_MEDIA_BNC;
1162    } else {
1163	sc->tulip_probe_media = TULIP_MEDIA_AUI;
1164    }
1165    tulip_media_set(sc, sc->tulip_probe_media);
1166    sc->tulip_flags &= ~TULIP_TXPROBE_ACTIVE;
1167    tulip_timeout(sc);
1168}
1169
1170static const tulip_boardsw_t tulip_21041_boardsw = {
1171    TULIP_21041_GENERIC,
1172    tulip_21041_media_probe,
1173    tulip_media_select,
1174    tulip_21041_media_poll
1175};
1176
1177static const tulip_phy_attr_t tulip_mii_phy_attrlist[] = {
1178    { 0x20005c00, 0,		/* 08-00-17 */
1179      {
1180	{ 0x19, 0x0040, 0x0040 },	/* 10TX */
1181	{ 0x19, 0x0040, 0x0000 },	/* 100TX */
1182      },
1183#if defined(TULIP_DEBUG)
1184      "NS DP83840",
1185#endif
1186    },
1187    { 0x0281F400, 0,		/* 00-A0-7D */
1188      {
1189	{ 0x12, 0x0010, 0x0000 },	/* 10T */
1190	{ },				/* 100TX */
1191	{ 0x12, 0x0010, 0x0010 },	/* 100T4 */
1192	{ 0x12, 0x0008, 0x0008 },	/* FULL_DUPLEX */
1193      },
1194#if defined(TULIP_DEBUG)
1195      "Seeq 80C240"
1196#endif
1197    },
1198#if 0
1199    { 0x0015F420, 0,	/* 00-A0-7D */
1200      {
1201	{ 0x12, 0x0010, 0x0000 },	/* 10T */
1202	{ },				/* 100TX */
1203	{ 0x12, 0x0010, 0x0010 },	/* 100T4 */
1204	{ 0x12, 0x0008, 0x0008 },	/* FULL_DUPLEX */
1205      },
1206#if defined(TULIP_DEBUG)
1207      "Broadcom BCM5000"
1208#endif
1209    },
1210#endif
1211    { 0x0281F400, 0,		/* 00-A0-BE */
1212      {
1213	{ 0x11, 0x8000, 0x0000 },	/* 10T */
1214	{ 0x11, 0x8000, 0x8000 },	/* 100TX */
1215	{ },				/* 100T4 */
1216	{ 0x11, 0x4000, 0x4000 },	/* FULL_DUPLEX */
1217      },
1218#if defined(TULIP_DEBUG)
1219      "ICS 1890"
1220#endif
1221    },
1222    { 0 }
1223};
1224
1225static tulip_media_t
1226tulip_mii_phy_readspecific(
1227    tulip_softc_t * const sc)
1228{
1229    const tulip_phy_attr_t *attr;
1230    u_int16_t data;
1231    u_int32_t id;
1232    unsigned idx = 0;
1233    static const tulip_media_t table[] = {
1234	TULIP_MEDIA_UNKNOWN,
1235	TULIP_MEDIA_10BASET,
1236	TULIP_MEDIA_100BASETX,
1237	TULIP_MEDIA_100BASET4,
1238	TULIP_MEDIA_UNKNOWN,
1239	TULIP_MEDIA_10BASET_FD,
1240	TULIP_MEDIA_100BASETX_FD,
1241	TULIP_MEDIA_UNKNOWN
1242    };
1243
1244    /*
1245     * Don't read phy specific registers if link is not up.
1246     */
1247    data = tulip_mii_readreg(sc, sc->tulip_phyaddr, PHYREG_STATUS);
1248    if ((data & (PHYSTS_LINK_UP|PHYSTS_EXTENDED_REGS)) != (PHYSTS_LINK_UP|PHYSTS_EXTENDED_REGS))
1249	return TULIP_MEDIA_UNKNOWN;
1250
1251    id = (tulip_mii_readreg(sc, sc->tulip_phyaddr, PHYREG_IDLOW) << 16) |
1252	tulip_mii_readreg(sc, sc->tulip_phyaddr, PHYREG_IDHIGH);
1253    for (attr = tulip_mii_phy_attrlist;; attr++) {
1254	if (attr->attr_id == 0)
1255	    return TULIP_MEDIA_UNKNOWN;
1256	if ((id & ~0x0F) == attr->attr_id)
1257	    break;
1258    }
1259
1260    if (attr->attr_modes[PHY_MODE_100TX].pm_regno) {
1261	const tulip_phy_modedata_t * const pm = &attr->attr_modes[PHY_MODE_100TX];
1262	data = tulip_mii_readreg(sc, sc->tulip_phyaddr, pm->pm_regno);
1263	if ((data & pm->pm_mask) == pm->pm_value)
1264	    idx = 2;
1265    }
1266    if (idx == 0 && attr->attr_modes[PHY_MODE_100T4].pm_regno) {
1267	const tulip_phy_modedata_t * const pm = &attr->attr_modes[PHY_MODE_100T4];
1268	data = tulip_mii_readreg(sc, sc->tulip_phyaddr, pm->pm_regno);
1269	if ((data & pm->pm_mask) == pm->pm_value)
1270	    idx = 3;
1271    }
1272    if (idx == 0 && attr->attr_modes[PHY_MODE_10T].pm_regno) {
1273	const tulip_phy_modedata_t * const pm = &attr->attr_modes[PHY_MODE_10T];
1274	data = tulip_mii_readreg(sc, sc->tulip_phyaddr, pm->pm_regno);
1275	if ((data & pm->pm_mask) == pm->pm_value)
1276	    idx = 1;
1277    }
1278    if (idx != 0 && attr->attr_modes[PHY_MODE_FULLDUPLEX].pm_regno) {
1279	const tulip_phy_modedata_t * const pm = &attr->attr_modes[PHY_MODE_FULLDUPLEX];
1280	data = tulip_mii_readreg(sc, sc->tulip_phyaddr, pm->pm_regno);
1281	idx += ((data & pm->pm_mask) == pm->pm_value ? 4 : 0);
1282    }
1283    return table[idx];
1284}
1285
1286static unsigned
1287tulip_mii_get_phyaddr(
1288    tulip_softc_t * const sc,
1289    unsigned offset)
1290{
1291    unsigned phyaddr;
1292
1293    for (phyaddr = 1; phyaddr < 32; phyaddr++) {
1294	unsigned status = tulip_mii_readreg(sc, phyaddr, PHYREG_STATUS);
1295	if (status == 0 || status == 0xFFFF || status < PHYSTS_10BASET)
1296	    continue;
1297	if (offset == 0)
1298	    return phyaddr;
1299	offset--;
1300    }
1301    if (offset == 0) {
1302	unsigned status = tulip_mii_readreg(sc, 0, PHYREG_STATUS);
1303	if (status == 0 || status == 0xFFFF || status < PHYSTS_10BASET)
1304	    return TULIP_MII_NOPHY;
1305	return 0;
1306    }
1307    return TULIP_MII_NOPHY;
1308}
1309
1310static int
1311tulip_mii_map_abilities(
1312    tulip_softc_t * const sc,
1313    unsigned abilities)
1314{
1315    sc->tulip_abilities = abilities;
1316    if (abilities & PHYSTS_100BASETX_FD) {
1317	sc->tulip_probe_media = TULIP_MEDIA_100BASETX_FD;
1318    } else if (abilities & PHYSTS_100BASET4) {
1319	sc->tulip_probe_media = TULIP_MEDIA_100BASET4;
1320    } else if (abilities & PHYSTS_100BASETX) {
1321	sc->tulip_probe_media = TULIP_MEDIA_100BASETX;
1322    } else if (abilities & PHYSTS_10BASET_FD) {
1323	sc->tulip_probe_media = TULIP_MEDIA_10BASET_FD;
1324    } else if (abilities & PHYSTS_10BASET) {
1325	sc->tulip_probe_media = TULIP_MEDIA_10BASET;
1326    } else {
1327	sc->tulip_probe_state = TULIP_PROBE_MEDIATEST;
1328	return 0;
1329    }
1330    sc->tulip_probe_state = TULIP_PROBE_INACTIVE;
1331    return 1;
1332}
1333
1334static void
1335tulip_mii_autonegotiate(
1336    tulip_softc_t * const sc,
1337    const unsigned phyaddr)
1338{
1339    switch (sc->tulip_probe_state) {
1340        case TULIP_PROBE_MEDIATEST:
1341        case TULIP_PROBE_INACTIVE: {
1342	    sc->tulip_flags |= TULIP_DIDNWAY;
1343	    tulip_mii_writereg(sc, phyaddr, PHYREG_CONTROL, PHYCTL_RESET);
1344	    sc->tulip_probe_timeout = 3000;
1345	    sc->tulip_intrmask |= TULIP_STS_ABNRMLINTR|TULIP_STS_NORMALINTR;
1346	    sc->tulip_probe_state = TULIP_PROBE_PHYRESET;
1347	}
1348        /* FALLTHROUGH */
1349        case TULIP_PROBE_PHYRESET: {
1350	    u_int32_t status;
1351	    u_int32_t data = tulip_mii_readreg(sc, phyaddr, PHYREG_CONTROL);
1352	    if (data & PHYCTL_RESET) {
1353		if (sc->tulip_probe_timeout > 0) {
1354		    tulip_timeout(sc);
1355		    return;
1356		}
1357		printf("%s(phy%d): error: reset of PHY never completed!\n",
1358			   sc->tulip_xname, phyaddr);
1359		sc->tulip_flags &= ~TULIP_TXPROBE_ACTIVE;
1360		sc->tulip_probe_state = TULIP_PROBE_FAILED;
1361		sc->tulip_if.if_flags &= ~(IFF_UP|IFF_RUNNING);
1362		return;
1363	    }
1364	    status = tulip_mii_readreg(sc, phyaddr, PHYREG_STATUS);
1365	    if ((status & PHYSTS_CAN_AUTONEG) == 0) {
1366#if defined(TULIP_DEBUG)
1367		loudprintf("%s(phy%d): autonegotiation disabled\n",
1368			   sc->tulip_xname, phyaddr);
1369#endif
1370		sc->tulip_flags &= ~TULIP_DIDNWAY;
1371		sc->tulip_probe_state = TULIP_PROBE_MEDIATEST;
1372		return;
1373	    }
1374	    if (tulip_mii_readreg(sc, phyaddr, PHYREG_AUTONEG_ADVERTISEMENT) != ((status >> 6) | 0x01))
1375		tulip_mii_writereg(sc, phyaddr, PHYREG_AUTONEG_ADVERTISEMENT, (status >> 6) | 0x01);
1376	    tulip_mii_writereg(sc, phyaddr, PHYREG_CONTROL, data|PHYCTL_AUTONEG_RESTART|PHYCTL_AUTONEG_ENABLE);
1377	    data = tulip_mii_readreg(sc, phyaddr, PHYREG_CONTROL);
1378#if defined(TULIP_DEBUG)
1379	    if ((data & PHYCTL_AUTONEG_ENABLE) == 0)
1380		loudprintf("%s(phy%d): oops: enable autonegotiation failed: 0x%04x\n",
1381			   sc->tulip_xname, phyaddr, data);
1382	    else
1383		loudprintf("%s(phy%d): autonegotiation restarted: 0x%04x\n",
1384			   sc->tulip_xname, phyaddr, data);
1385	    sc->tulip_dbg.dbg_nway_starts++;
1386#endif
1387	    sc->tulip_probe_state = TULIP_PROBE_PHYAUTONEG;
1388	    sc->tulip_probe_timeout = 3000;
1389	}
1390        /* FALLTHROUGH */
1391        case TULIP_PROBE_PHYAUTONEG: {
1392	    u_int32_t status = tulip_mii_readreg(sc, phyaddr, PHYREG_STATUS);
1393	    u_int32_t data;
1394	    if ((status & PHYSTS_AUTONEG_DONE) == 0) {
1395		if (sc->tulip_probe_timeout > 0) {
1396		    tulip_timeout(sc);
1397		    return;
1398		}
1399#if defined(TULIP_DEBUG)
1400		loudprintf("%s(phy%d): autonegotiation timeout: sts=0x%04x, ctl=0x%04x\n",
1401			   sc->tulip_xname, phyaddr, status,
1402			   tulip_mii_readreg(sc, phyaddr, PHYREG_CONTROL));
1403#endif
1404		sc->tulip_flags &= ~TULIP_DIDNWAY;
1405		sc->tulip_probe_state = TULIP_PROBE_MEDIATEST;
1406		return;
1407	    }
1408	    data = tulip_mii_readreg(sc, phyaddr, PHYREG_AUTONEG_ABILITIES);
1409#if defined(TULIP_DEBUG)
1410	    loudprintf("%s(phy%d): autonegotiation complete: 0x%04x\n",
1411		       sc->tulip_xname, phyaddr, data);
1412#endif
1413	    data = (data << 6) & status;
1414	    if (!tulip_mii_map_abilities(sc, data))
1415		sc->tulip_flags &= ~TULIP_DIDNWAY;
1416	    return;
1417	}
1418	default: {
1419#if defined(DIAGNOSTIC)
1420	    panic("tulip_media_poll: botch at line %d\n", __LINE__);
1421#endif
1422	    break;
1423	}
1424    }
1425#if defined(TULIP_DEBUG)
1426    loudprintf("%s(phy%d): autonegotiation failure: state = %d\n",
1427	       sc->tulip_xname, phyaddr, sc->tulip_probe_state);
1428	    sc->tulip_dbg.dbg_nway_failures++;
1429#endif
1430}
1431
1432static void
1433tulip_2114x_media_preset(
1434    tulip_softc_t * const sc)
1435{
1436    const tulip_media_info_t *mi = NULL;
1437    tulip_media_t media = sc->tulip_media;
1438
1439    if (sc->tulip_probe_state == TULIP_PROBE_INACTIVE)
1440	media = sc->tulip_media;
1441    else
1442	media = sc->tulip_probe_media;
1443
1444    sc->tulip_cmdmode &= ~TULIP_CMD_PORTSELECT;
1445    sc->tulip_flags &= ~TULIP_SQETEST;
1446    if (media != TULIP_MEDIA_UNKNOWN && media != TULIP_MEDIA_MAX) {
1447#if defined(TULIP_DEBUG)
1448	if (media < TULIP_MEDIA_MAX && sc->tulip_mediums[media] != NULL) {
1449#endif
1450	    mi = sc->tulip_mediums[media];
1451	    if (mi->mi_type == TULIP_MEDIAINFO_MII) {
1452		sc->tulip_cmdmode |= TULIP_CMD_PORTSELECT;
1453	    } else if (mi->mi_type == TULIP_MEDIAINFO_GPR
1454		       || mi->mi_type == TULIP_MEDIAINFO_SYM) {
1455		sc->tulip_cmdmode &= ~TULIP_GPR_CMDBITS;
1456		sc->tulip_cmdmode |= mi->mi_cmdmode;
1457	    } else if (mi->mi_type == TULIP_MEDIAINFO_SIA) {
1458		TULIP_CSR_WRITE(sc, csr_sia_connectivity, TULIP_SIACONN_RESET);
1459	    }
1460#if defined(TULIP_DEBUG)
1461	} else {
1462	    printf("%s: preset: bad media %d!\n",
1463		   sc->tulip_xname, media);
1464	}
1465#endif
1466    }
1467    switch (media) {
1468	case TULIP_MEDIA_BNC:
1469	case TULIP_MEDIA_AUI:
1470	case TULIP_MEDIA_10BASET: {
1471	    sc->tulip_cmdmode &= ~TULIP_CMD_FULLDUPLEX;
1472	    sc->tulip_cmdmode |= TULIP_CMD_TXTHRSHLDCTL;
1473	    sc->tulip_if.if_baudrate = 10000000;
1474	    sc->tulip_flags |= TULIP_SQETEST;
1475	    break;
1476	}
1477	case TULIP_MEDIA_10BASET_FD: {
1478	    sc->tulip_cmdmode |= TULIP_CMD_FULLDUPLEX|TULIP_CMD_TXTHRSHLDCTL;
1479	    sc->tulip_if.if_baudrate = 10000000;
1480	    break;
1481	}
1482	case TULIP_MEDIA_100BASEFX:
1483	case TULIP_MEDIA_100BASET4:
1484	case TULIP_MEDIA_100BASETX: {
1485	    sc->tulip_cmdmode &= ~(TULIP_CMD_FULLDUPLEX|TULIP_CMD_TXTHRSHLDCTL);
1486	    sc->tulip_cmdmode |= TULIP_CMD_PORTSELECT;
1487	    sc->tulip_if.if_baudrate = 100000000;
1488	    break;
1489	}
1490	case TULIP_MEDIA_100BASEFX_FD:
1491	case TULIP_MEDIA_100BASETX_FD: {
1492	    sc->tulip_cmdmode |= TULIP_CMD_FULLDUPLEX|TULIP_CMD_PORTSELECT;
1493	    sc->tulip_cmdmode &= ~TULIP_CMD_TXTHRSHLDCTL;
1494	    sc->tulip_if.if_baudrate = 100000000;
1495	    break;
1496	}
1497	default: {
1498	    break;
1499	}
1500    }
1501    TULIP_CSR_WRITE(sc, csr_command, sc->tulip_cmdmode);
1502}
1503
1504/*
1505 ********************************************************************
1506 *  Start of 21140/21140A support which does not use the MII interface
1507 */
1508
1509static void
1510tulip_null_media_poll(
1511    tulip_softc_t * const sc,
1512    tulip_mediapoll_event_t event)
1513{
1514#if defined(TULIP_DEBUG)
1515    sc->tulip_dbg.dbg_events[event]++;
1516#endif
1517#if defined(DIAGNOSTIC)
1518    printf("%s: botch(media_poll) at line %d\n",
1519	   sc->tulip_xname, __LINE__);
1520#endif
1521}
1522
1523__inline static void
1524tulip_21140_mediainit(
1525    tulip_softc_t * const sc,
1526    tulip_media_info_t * const mip,
1527    tulip_media_t const media,
1528    unsigned gpdata,
1529    unsigned cmdmode)
1530{
1531    sc->tulip_mediums[media] = mip;
1532    mip->mi_type = TULIP_MEDIAINFO_GPR;
1533    mip->mi_cmdmode = cmdmode;
1534    mip->mi_gpdata = gpdata;
1535}
1536
1537static void
1538tulip_21140_evalboard_media_probe(
1539    tulip_softc_t * const sc)
1540{
1541    tulip_media_info_t *mip = sc->tulip_mediainfo;
1542
1543    sc->tulip_gpinit = TULIP_GP_EB_PINS;
1544    sc->tulip_gpdata = TULIP_GP_EB_INIT;
1545    TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_EB_PINS);
1546    TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_EB_INIT);
1547    TULIP_CSR_WRITE(sc, csr_command,
1548	TULIP_CSR_READ(sc, csr_command) | TULIP_CMD_PORTSELECT |
1549	TULIP_CMD_PCSFUNCTION | TULIP_CMD_SCRAMBLER | TULIP_CMD_MUSTBEONE);
1550    TULIP_CSR_WRITE(sc, csr_command,
1551	TULIP_CSR_READ(sc, csr_command) & ~TULIP_CMD_TXTHRSHLDCTL);
1552    DELAY(1000000);
1553    if ((TULIP_CSR_READ(sc, csr_gp) & TULIP_GP_EB_OK100) != 0) {
1554	sc->tulip_media = TULIP_MEDIA_10BASET;
1555    } else {
1556	sc->tulip_media = TULIP_MEDIA_100BASETX;
1557    }
1558    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_10BASET,
1559			  TULIP_GP_EB_INIT,
1560			  TULIP_CMD_TXTHRSHLDCTL);
1561    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_10BASET_FD,
1562			  TULIP_GP_EB_INIT,
1563			  TULIP_CMD_TXTHRSHLDCTL|TULIP_CMD_FULLDUPLEX);
1564    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_100BASETX,
1565			  TULIP_GP_EB_INIT,
1566			  TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION
1567			      |TULIP_CMD_SCRAMBLER);
1568    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_100BASETX_FD,
1569			  TULIP_GP_EB_INIT,
1570			  TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION
1571			      |TULIP_CMD_SCRAMBLER|TULIP_CMD_FULLDUPLEX);
1572}
1573
1574static const tulip_boardsw_t tulip_21140_eb_boardsw = {
1575    TULIP_21140_DEC_EB,
1576    tulip_21140_evalboard_media_probe,
1577    tulip_media_select,
1578    tulip_null_media_poll,
1579    tulip_2114x_media_preset,
1580};
1581
1582static void
1583tulip_21140_accton_media_probe(
1584    tulip_softc_t * const sc)
1585{
1586    tulip_media_info_t *mip = sc->tulip_mediainfo;
1587    unsigned gpdata;
1588
1589    sc->tulip_gpinit = TULIP_GP_EB_PINS;
1590    sc->tulip_gpdata = TULIP_GP_EB_INIT;
1591    TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_EB_PINS);
1592    TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_EB_INIT);
1593    TULIP_CSR_WRITE(sc, csr_command,
1594	TULIP_CSR_READ(sc, csr_command) | TULIP_CMD_PORTSELECT |
1595	TULIP_CMD_PCSFUNCTION | TULIP_CMD_SCRAMBLER | TULIP_CMD_MUSTBEONE);
1596    TULIP_CSR_WRITE(sc, csr_command,
1597	TULIP_CSR_READ(sc, csr_command) & ~TULIP_CMD_TXTHRSHLDCTL);
1598    DELAY(1000000);
1599    gpdata = TULIP_CSR_READ(sc, csr_gp);
1600    if ((gpdata & TULIP_GP_EN1207_UTP_INIT) == 0) {
1601	sc->tulip_media = TULIP_MEDIA_10BASET;
1602    } else {
1603	if ((gpdata & TULIP_GP_EN1207_BNC_INIT) == 0) {
1604		sc->tulip_media = TULIP_MEDIA_BNC;
1605        } else {
1606		sc->tulip_media = TULIP_MEDIA_100BASETX;
1607        }
1608    }
1609    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_BNC,
1610			  TULIP_GP_EN1207_BNC_INIT,
1611			  TULIP_CMD_TXTHRSHLDCTL);
1612    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_10BASET,
1613			  TULIP_GP_EN1207_UTP_INIT,
1614			  TULIP_CMD_TXTHRSHLDCTL);
1615    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_10BASET_FD,
1616			  TULIP_GP_EN1207_UTP_INIT,
1617			  TULIP_CMD_TXTHRSHLDCTL|TULIP_CMD_FULLDUPLEX);
1618    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_100BASETX,
1619			  TULIP_GP_EN1207_100_INIT,
1620			  TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION
1621			      |TULIP_CMD_SCRAMBLER);
1622    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_100BASETX_FD,
1623			  TULIP_GP_EN1207_100_INIT,
1624			  TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION
1625			      |TULIP_CMD_SCRAMBLER|TULIP_CMD_FULLDUPLEX);
1626}
1627
1628static const tulip_boardsw_t tulip_21140_accton_boardsw = {
1629    TULIP_21140_EN1207,
1630    tulip_21140_accton_media_probe,
1631    tulip_media_select,
1632    tulip_null_media_poll,
1633    tulip_2114x_media_preset,
1634};
1635
1636static void
1637tulip_21140_smc9332_media_probe(
1638    tulip_softc_t * const sc)
1639{
1640    tulip_media_info_t *mip = sc->tulip_mediainfo;
1641    int idx, cnt = 0;
1642
1643    TULIP_CSR_WRITE(sc, csr_command, TULIP_CMD_PORTSELECT|TULIP_CMD_MUSTBEONE);
1644    TULIP_CSR_WRITE(sc, csr_busmode, TULIP_BUSMODE_SWRESET);
1645    DELAY(10);	/* Wait 10 microseconds (actually 50 PCI cycles but at
1646		   33MHz that comes to two microseconds but wait a
1647		   bit longer anyways) */
1648    TULIP_CSR_WRITE(sc, csr_command, TULIP_CMD_PORTSELECT |
1649	TULIP_CMD_PCSFUNCTION | TULIP_CMD_SCRAMBLER | TULIP_CMD_MUSTBEONE);
1650    sc->tulip_gpinit = TULIP_GP_SMC_9332_PINS;
1651    sc->tulip_gpdata = TULIP_GP_SMC_9332_INIT;
1652    TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_SMC_9332_PINS|TULIP_GP_PINSET);
1653    TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_SMC_9332_INIT);
1654    DELAY(200000);
1655    for (idx = 1000; idx > 0; idx--) {
1656	u_int32_t csr = TULIP_CSR_READ(sc, csr_gp);
1657	if ((csr & (TULIP_GP_SMC_9332_OK10|TULIP_GP_SMC_9332_OK100)) == (TULIP_GP_SMC_9332_OK10|TULIP_GP_SMC_9332_OK100)) {
1658	    if (++cnt > 100)
1659		break;
1660	} else if ((csr & TULIP_GP_SMC_9332_OK10) == 0) {
1661	    break;
1662	} else {
1663	    cnt = 0;
1664	}
1665	DELAY(1000);
1666    }
1667    sc->tulip_media = cnt > 100 ? TULIP_MEDIA_100BASETX : TULIP_MEDIA_10BASET;
1668    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_100BASETX,
1669			  TULIP_GP_SMC_9332_INIT,
1670			  TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION
1671			      |TULIP_CMD_SCRAMBLER);
1672    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_100BASETX_FD,
1673			  TULIP_GP_SMC_9332_INIT,
1674			  TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION
1675			      |TULIP_CMD_SCRAMBLER|TULIP_CMD_FULLDUPLEX);
1676    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_10BASET,
1677			  TULIP_GP_SMC_9332_INIT,
1678			  TULIP_CMD_TXTHRSHLDCTL);
1679    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_10BASET_FD,
1680			  TULIP_GP_SMC_9332_INIT,
1681			  TULIP_CMD_TXTHRSHLDCTL|TULIP_CMD_FULLDUPLEX);
1682}
1683
1684static const tulip_boardsw_t tulip_21140_smc9332_boardsw = {
1685    TULIP_21140_SMC_9332,
1686    tulip_21140_smc9332_media_probe,
1687    tulip_media_select,
1688    tulip_null_media_poll,
1689    tulip_2114x_media_preset,
1690};
1691
1692static void
1693tulip_21140_cogent_em100_media_probe(
1694    tulip_softc_t * const sc)
1695{
1696    tulip_media_info_t *mip = sc->tulip_mediainfo;
1697    u_int32_t cmdmode = TULIP_CSR_READ(sc, csr_command);
1698
1699    sc->tulip_gpinit = TULIP_GP_EM100_PINS;
1700    sc->tulip_gpdata = TULIP_GP_EM100_INIT;
1701    TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_EM100_PINS);
1702    TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_EM100_INIT);
1703
1704    cmdmode = TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION|TULIP_CMD_MUSTBEONE;
1705    cmdmode &= ~(TULIP_CMD_TXTHRSHLDCTL|TULIP_CMD_SCRAMBLER);
1706    if (sc->tulip_rombuf[32] == TULIP_COGENT_EM100FX_ID) {
1707	TULIP_CSR_WRITE(sc, csr_command, cmdmode);
1708	sc->tulip_media = TULIP_MEDIA_100BASEFX;
1709
1710	tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_100BASEFX,
1711			  TULIP_GP_EM100_INIT,
1712			  TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION);
1713	tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_100BASEFX_FD,
1714			  TULIP_GP_EM100_INIT,
1715			  TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION
1716			      |TULIP_CMD_FULLDUPLEX);
1717    } else {
1718	TULIP_CSR_WRITE(sc, csr_command, cmdmode|TULIP_CMD_SCRAMBLER);
1719	sc->tulip_media = TULIP_MEDIA_100BASETX;
1720	tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_100BASETX,
1721			  TULIP_GP_EM100_INIT,
1722			  TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION
1723			      |TULIP_CMD_SCRAMBLER);
1724	tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_100BASETX_FD,
1725			  TULIP_GP_EM100_INIT,
1726			  TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION
1727			      |TULIP_CMD_SCRAMBLER|TULIP_CMD_FULLDUPLEX);
1728    }
1729}
1730
1731static const tulip_boardsw_t tulip_21140_cogent_em100_boardsw = {
1732    TULIP_21140_COGENT_EM100,
1733    tulip_21140_cogent_em100_media_probe,
1734    tulip_media_select,
1735    tulip_null_media_poll,
1736    tulip_2114x_media_preset
1737};
1738
1739static void
1740tulip_21140_znyx_zx34x_media_probe(
1741    tulip_softc_t * const sc)
1742{
1743    tulip_media_info_t *mip = sc->tulip_mediainfo;
1744    int cnt10 = 0, cnt100 = 0, idx;
1745
1746    sc->tulip_gpinit = TULIP_GP_ZX34X_PINS;
1747    sc->tulip_gpdata = TULIP_GP_ZX34X_INIT;
1748    TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_ZX34X_PINS);
1749    TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_ZX34X_INIT);
1750    TULIP_CSR_WRITE(sc, csr_command,
1751	TULIP_CSR_READ(sc, csr_command) | TULIP_CMD_PORTSELECT |
1752	TULIP_CMD_PCSFUNCTION | TULIP_CMD_SCRAMBLER | TULIP_CMD_MUSTBEONE);
1753    TULIP_CSR_WRITE(sc, csr_command,
1754	TULIP_CSR_READ(sc, csr_command) & ~TULIP_CMD_TXTHRSHLDCTL);
1755
1756    DELAY(200000);
1757    for (idx = 1000; idx > 0; idx--) {
1758	u_int32_t csr = TULIP_CSR_READ(sc, csr_gp);
1759	if ((csr & (TULIP_GP_ZX34X_LNKFAIL|TULIP_GP_ZX34X_SYMDET|TULIP_GP_ZX34X_SIGDET)) == (TULIP_GP_ZX34X_LNKFAIL|TULIP_GP_ZX34X_SYMDET|TULIP_GP_ZX34X_SIGDET)) {
1760	    if (++cnt100 > 100)
1761		break;
1762	} else if ((csr & TULIP_GP_ZX34X_LNKFAIL) == 0) {
1763	    if (++cnt10 > 100)
1764		break;
1765	} else {
1766	    cnt10 = 0;
1767	    cnt100 = 0;
1768	}
1769	DELAY(1000);
1770    }
1771    sc->tulip_media = cnt100 > 100 ? TULIP_MEDIA_100BASETX : TULIP_MEDIA_10BASET;
1772    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_10BASET,
1773			  TULIP_GP_ZX34X_INIT,
1774			  TULIP_CMD_TXTHRSHLDCTL);
1775    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_10BASET_FD,
1776			  TULIP_GP_ZX34X_INIT,
1777			  TULIP_CMD_TXTHRSHLDCTL|TULIP_CMD_FULLDUPLEX);
1778    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_100BASETX,
1779			  TULIP_GP_ZX34X_INIT,
1780			  TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION
1781			      |TULIP_CMD_SCRAMBLER);
1782    tulip_21140_mediainit(sc, mip++, TULIP_MEDIA_100BASETX_FD,
1783			  TULIP_GP_ZX34X_INIT,
1784			  TULIP_CMD_PORTSELECT|TULIP_CMD_PCSFUNCTION
1785			      |TULIP_CMD_SCRAMBLER|TULIP_CMD_FULLDUPLEX);
1786}
1787
1788static const tulip_boardsw_t tulip_21140_znyx_zx34x_boardsw = {
1789    TULIP_21140_ZNYX_ZX34X,
1790    tulip_21140_znyx_zx34x_media_probe,
1791    tulip_media_select,
1792    tulip_null_media_poll,
1793    tulip_2114x_media_preset,
1794};
1795
1796static void
1797tulip_2114x_media_probe(
1798    tulip_softc_t * const sc)
1799{
1800    sc->tulip_cmdmode |= TULIP_CMD_MUSTBEONE
1801	|TULIP_CMD_BACKOFFCTR|TULIP_CMD_THRSHLD72;
1802}
1803
1804static const tulip_boardsw_t tulip_2114x_isv_boardsw = {
1805    TULIP_21140_ISV,
1806    tulip_2114x_media_probe,
1807    tulip_media_select,
1808    tulip_media_poll,
1809    tulip_2114x_media_preset,
1810};
1811
1812/*
1813 * ******** END of chip-specific handlers. ***********
1814 */
1815
1816/*
1817 * Code the read the SROM and MII bit streams (I2C)
1818 */
1819#define EMIT    do { TULIP_CSR_WRITE(sc, csr_srom_mii, csr); DELAY(1); } while (0)
1820
1821static void
1822tulip_srom_idle(
1823    tulip_softc_t * const sc)
1824{
1825    unsigned bit, csr;
1826
1827    csr  = SROMSEL ; EMIT;
1828    csr  = SROMSEL | SROMRD; EMIT;
1829    csr ^= SROMCS; EMIT;
1830    csr ^= SROMCLKON; EMIT;
1831
1832    /*
1833     * Write 25 cycles of 0 which will force the SROM to be idle.
1834     */
1835    for (bit = 3 + SROM_BITWIDTH + 16; bit > 0; bit--) {
1836        csr ^= SROMCLKOFF; EMIT;    /* clock low; data not valid */
1837        csr ^= SROMCLKON; EMIT;     /* clock high; data valid */
1838    }
1839    csr ^= SROMCLKOFF; EMIT;
1840    csr ^= SROMCS; EMIT;
1841    csr  = 0; EMIT;
1842}
1843
1844
1845static void
1846tulip_srom_read(
1847    tulip_softc_t * const sc)
1848{
1849    unsigned idx;
1850    const unsigned bitwidth = SROM_BITWIDTH;
1851    const unsigned cmdmask = (SROMCMD_RD << bitwidth);
1852    const unsigned msb = 1 << (bitwidth + 3 - 1);
1853    unsigned lastidx = (1 << bitwidth) - 1;
1854
1855    tulip_srom_idle(sc);
1856
1857    for (idx = 0; idx <= lastidx; idx++) {
1858        unsigned lastbit, data, bits, bit, csr;
1859	csr  = SROMSEL ;	        EMIT;
1860        csr  = SROMSEL | SROMRD;        EMIT;
1861        csr ^= SROMCSON;                EMIT;
1862        csr ^=            SROMCLKON;    EMIT;
1863
1864        lastbit = 0;
1865        for (bits = idx|cmdmask, bit = bitwidth + 3; bit > 0; bit--, bits <<= 1) {
1866            const unsigned thisbit = bits & msb;
1867            csr ^= SROMCLKOFF; EMIT;    /* clock low; data not valid */
1868            if (thisbit != lastbit) {
1869                csr ^= SROMDOUT; EMIT;  /* clock low; invert data */
1870            } else {
1871		EMIT;
1872	    }
1873            csr ^= SROMCLKON; EMIT;     /* clock high; data valid */
1874            lastbit = thisbit;
1875        }
1876        csr ^= SROMCLKOFF; EMIT;
1877
1878        for (data = 0, bits = 0; bits < 16; bits++) {
1879            data <<= 1;
1880            csr ^= SROMCLKON; EMIT;     /* clock high; data valid */
1881            data |= TULIP_CSR_READ(sc, csr_srom_mii) & SROMDIN ? 1 : 0;
1882            csr ^= SROMCLKOFF; EMIT;    /* clock low; data not valid */
1883        }
1884	sc->tulip_rombuf[idx*2] = data & 0xFF;
1885	sc->tulip_rombuf[idx*2+1] = data >> 8;
1886	csr  = SROMSEL | SROMRD; EMIT;
1887	csr  = 0; EMIT;
1888    }
1889    tulip_srom_idle(sc);
1890}
1891
1892#define MII_EMIT    do { TULIP_CSR_WRITE(sc, csr_srom_mii, csr); DELAY(1); } while (0)
1893
1894static void
1895tulip_mii_writebits(
1896    tulip_softc_t * const sc,
1897    unsigned data,
1898    unsigned bits)
1899{
1900    unsigned msb = 1 << (bits - 1);
1901    unsigned csr = TULIP_CSR_READ(sc, csr_srom_mii) & (MII_RD|MII_DOUT|MII_CLK);
1902    unsigned lastbit = (csr & MII_DOUT) ? msb : 0;
1903
1904    csr |= MII_WR; MII_EMIT;  		/* clock low; assert write */
1905
1906    for (; bits > 0; bits--, data <<= 1) {
1907	const unsigned thisbit = data & msb;
1908	if (thisbit != lastbit) {
1909	    csr ^= MII_DOUT; MII_EMIT;  /* clock low; invert data */
1910	}
1911	csr ^= MII_CLKON; MII_EMIT;     /* clock high; data valid */
1912	lastbit = thisbit;
1913	csr ^= MII_CLKOFF; MII_EMIT;    /* clock low; data not valid */
1914    }
1915}
1916
1917static void
1918tulip_mii_turnaround(
1919    tulip_softc_t * const sc,
1920    unsigned cmd)
1921{
1922    unsigned csr = TULIP_CSR_READ(sc, csr_srom_mii) & (MII_RD|MII_DOUT|MII_CLK);
1923
1924    if (cmd == MII_WRCMD) {
1925	csr |= MII_DOUT; MII_EMIT;	/* clock low; change data */
1926	csr ^= MII_CLKON; MII_EMIT;	/* clock high; data valid */
1927	csr ^= MII_CLKOFF; MII_EMIT;	/* clock low; data not valid */
1928	csr ^= MII_DOUT; MII_EMIT;	/* clock low; change data */
1929    } else {
1930	csr |= MII_RD; MII_EMIT;	/* clock low; switch to read */
1931    }
1932    csr ^= MII_CLKON; MII_EMIT;		/* clock high; data valid */
1933    csr ^= MII_CLKOFF; MII_EMIT;	/* clock low; data not valid */
1934}
1935
1936static unsigned
1937tulip_mii_readbits(
1938    tulip_softc_t * const sc)
1939{
1940    unsigned data;
1941    unsigned csr = TULIP_CSR_READ(sc, csr_srom_mii) & (MII_RD|MII_DOUT|MII_CLK);
1942    int idx;
1943
1944    for (idx = 0, data = 0; idx < 16; idx++) {
1945	data <<= 1;	/* this is NOOP on the first pass through */
1946	csr ^= MII_CLKON; MII_EMIT;	/* clock high; data valid */
1947	if (TULIP_CSR_READ(sc, csr_srom_mii) & MII_DIN)
1948	    data |= 1;
1949	csr ^= MII_CLKOFF; MII_EMIT;	/* clock low; data not valid */
1950    }
1951    csr ^= MII_RD; MII_EMIT;		/* clock low; turn off read */
1952
1953    return data;
1954}
1955
1956static unsigned
1957tulip_mii_readreg(
1958    tulip_softc_t * const sc,
1959    unsigned devaddr,
1960    unsigned regno)
1961{
1962    unsigned csr = TULIP_CSR_READ(sc, csr_srom_mii) & (MII_RD|MII_DOUT|MII_CLK);
1963    unsigned data;
1964
1965    csr &= ~(MII_RD|MII_CLK); MII_EMIT;
1966    tulip_mii_writebits(sc, MII_PREAMBLE, 32);
1967    tulip_mii_writebits(sc, MII_RDCMD, 8);
1968    tulip_mii_writebits(sc, devaddr, 5);
1969    tulip_mii_writebits(sc, regno, 5);
1970    tulip_mii_turnaround(sc, MII_RDCMD);
1971
1972    data = tulip_mii_readbits(sc);
1973#if defined(TULIP_DEBUG)
1974    sc->tulip_dbg.dbg_phyregs[regno][0] = data;
1975    sc->tulip_dbg.dbg_phyregs[regno][1]++;
1976#endif
1977    return data;
1978}
1979
1980static void
1981tulip_mii_writereg(
1982    tulip_softc_t * const sc,
1983    unsigned devaddr,
1984    unsigned regno,
1985    unsigned data)
1986{
1987    unsigned csr = TULIP_CSR_READ(sc, csr_srom_mii) & (MII_RD|MII_DOUT|MII_CLK);
1988    csr &= ~(MII_RD|MII_CLK); MII_EMIT;
1989    tulip_mii_writebits(sc, MII_PREAMBLE, 32);
1990    tulip_mii_writebits(sc, MII_WRCMD, 8);
1991    tulip_mii_writebits(sc, devaddr, 5);
1992    tulip_mii_writebits(sc, regno, 5);
1993    tulip_mii_turnaround(sc, MII_WRCMD);
1994    tulip_mii_writebits(sc, data, 16);
1995#if defined(TULIP_DEBUG)
1996    sc->tulip_dbg.dbg_phyregs[regno][2] = data;
1997    sc->tulip_dbg.dbg_phyregs[regno][3]++;
1998#endif
1999}
2000
2001#define	tulip_mchash(mca)	(ether_crc32_le(mca, 6) & 0x1FF)
2002#define	tulip_srom_crcok(databuf)	( \
2003    ((ether_crc32_le(databuf, 126) & 0xFFFFU) ^ 0xFFFFU) == \
2004     ((databuf)[126] | ((databuf)[127] << 8)))
2005
2006static void
2007tulip_identify_dec_nic(
2008    tulip_softc_t * const sc)
2009{
2010    strcpy(sc->tulip_boardid, "DEC ");
2011#define D0	4
2012    if (sc->tulip_chipid <= TULIP_21040)
2013	return;
2014    if (bcmp(sc->tulip_rombuf + 29, "DE500", 5) == 0
2015	|| bcmp(sc->tulip_rombuf + 29, "DE450", 5) == 0) {
2016	bcopy(sc->tulip_rombuf + 29, &sc->tulip_boardid[D0], 8);
2017	sc->tulip_boardid[D0+8] = ' ';
2018    }
2019#undef D0
2020}
2021
2022static void
2023tulip_identify_znyx_nic(
2024    tulip_softc_t * const sc)
2025{
2026    unsigned id = 0;
2027    strcpy(sc->tulip_boardid, "ZNYX ZX3XX ");
2028    if (sc->tulip_chipid == TULIP_21140 || sc->tulip_chipid == TULIP_21140A) {
2029	unsigned znyx_ptr;
2030	sc->tulip_boardid[8] = '4';
2031	znyx_ptr = sc->tulip_rombuf[124] + 256 * sc->tulip_rombuf[125];
2032	if (znyx_ptr < 26 || znyx_ptr > 116) {
2033	    sc->tulip_boardsw = &tulip_21140_znyx_zx34x_boardsw;
2034	    return;
2035	}
2036	/* ZX344 = 0010 .. 0013FF
2037	 */
2038	if (sc->tulip_rombuf[znyx_ptr] == 0x4A
2039		&& sc->tulip_rombuf[znyx_ptr + 1] == 0x52
2040		&& sc->tulip_rombuf[znyx_ptr + 2] == 0x01) {
2041	    id = sc->tulip_rombuf[znyx_ptr + 5] + 256 * sc->tulip_rombuf[znyx_ptr + 4];
2042	    if ((id >> 8) == (TULIP_ZNYX_ID_ZX342 >> 8)) {
2043		sc->tulip_boardid[9] = '2';
2044		if (id == TULIP_ZNYX_ID_ZX342B) {
2045		    sc->tulip_boardid[10] = 'B';
2046		    sc->tulip_boardid[11] = ' ';
2047		}
2048		sc->tulip_boardsw = &tulip_21140_znyx_zx34x_boardsw;
2049	    } else if (id == TULIP_ZNYX_ID_ZX344) {
2050		sc->tulip_boardid[10] = '4';
2051		sc->tulip_boardsw = &tulip_21140_znyx_zx34x_boardsw;
2052	    } else if (id == TULIP_ZNYX_ID_ZX345) {
2053		sc->tulip_boardid[9] = (sc->tulip_rombuf[19] > 1) ? '8' : '5';
2054	    } else if (id == TULIP_ZNYX_ID_ZX346) {
2055		sc->tulip_boardid[9] = '6';
2056	    } else if (id == TULIP_ZNYX_ID_ZX351) {
2057		sc->tulip_boardid[8] = '5';
2058		sc->tulip_boardid[9] = '1';
2059	    }
2060	}
2061	if (id == 0) {
2062	    /*
2063	     * Assume it's a ZX342...
2064	     */
2065	    sc->tulip_boardsw = &tulip_21140_znyx_zx34x_boardsw;
2066	}
2067	return;
2068    }
2069    sc->tulip_boardid[8] = '1';
2070    if (sc->tulip_chipid == TULIP_21041) {
2071	sc->tulip_boardid[10] = '1';
2072	return;
2073    }
2074    if (sc->tulip_rombuf[32] == 0x4A && sc->tulip_rombuf[33] == 0x52) {
2075	id = sc->tulip_rombuf[37] + 256 * sc->tulip_rombuf[36];
2076	if (id == TULIP_ZNYX_ID_ZX312T) {
2077	    sc->tulip_boardid[9] = '2';
2078	    sc->tulip_boardid[10] = 'T';
2079	    sc->tulip_boardid[11] = ' ';
2080	    sc->tulip_boardsw = &tulip_21040_10baset_only_boardsw;
2081	} else if (id == TULIP_ZNYX_ID_ZX314_INTA) {
2082	    sc->tulip_boardid[9] = '4';
2083	    sc->tulip_boardsw = &tulip_21040_10baset_only_boardsw;
2084	    sc->tulip_features |= TULIP_HAVE_SHAREDINTR|TULIP_HAVE_BASEROM;
2085	} else if (id == TULIP_ZNYX_ID_ZX314) {
2086	    sc->tulip_boardid[9] = '4';
2087	    sc->tulip_boardsw = &tulip_21040_10baset_only_boardsw;
2088	    sc->tulip_features |= TULIP_HAVE_BASEROM;
2089	} else if (id == TULIP_ZNYX_ID_ZX315_INTA) {
2090	    sc->tulip_boardid[9] = '5';
2091	    sc->tulip_features |= TULIP_HAVE_SHAREDINTR|TULIP_HAVE_BASEROM;
2092	} else if (id == TULIP_ZNYX_ID_ZX315) {
2093	    sc->tulip_boardid[9] = '5';
2094	    sc->tulip_features |= TULIP_HAVE_BASEROM;
2095	} else {
2096	    id = 0;
2097	}
2098    }
2099    if (id == 0) {
2100	if ((sc->tulip_enaddr[3] & ~3) == 0xF0 && (sc->tulip_enaddr[5] & 2) == 0) {
2101	    sc->tulip_boardid[9] = '4';
2102	    sc->tulip_boardsw = &tulip_21040_10baset_only_boardsw;
2103	    sc->tulip_features |= TULIP_HAVE_SHAREDINTR|TULIP_HAVE_BASEROM;
2104	} else if ((sc->tulip_enaddr[3] & ~3) == 0xF4 && (sc->tulip_enaddr[5] & 1) == 0) {
2105	    sc->tulip_boardid[9] = '5';
2106	    sc->tulip_boardsw = &tulip_21040_boardsw;
2107	    sc->tulip_features |= TULIP_HAVE_SHAREDINTR|TULIP_HAVE_BASEROM;
2108	} else if ((sc->tulip_enaddr[3] & ~3) == 0xEC) {
2109	    sc->tulip_boardid[9] = '2';
2110	    sc->tulip_boardsw = &tulip_21040_boardsw;
2111	}
2112    }
2113}
2114
2115static void
2116tulip_identify_smc_nic(
2117    tulip_softc_t * const sc)
2118{
2119    u_int32_t id1, id2, ei;
2120    int auibnc = 0, utp = 0;
2121    char *cp;
2122
2123    strcpy(sc->tulip_boardid, "SMC ");
2124    if (sc->tulip_chipid == TULIP_21041)
2125	return;
2126    if (sc->tulip_chipid != TULIP_21040) {
2127	if (sc->tulip_boardsw != &tulip_2114x_isv_boardsw) {
2128	    strcpy(&sc->tulip_boardid[4], "9332DST ");
2129	    sc->tulip_boardsw = &tulip_21140_smc9332_boardsw;
2130	} else if (sc->tulip_features & (TULIP_HAVE_BASEROM|TULIP_HAVE_SLAVEDROM)) {
2131	    strcpy(&sc->tulip_boardid[4], "9334BDT ");
2132	} else {
2133	    strcpy(&sc->tulip_boardid[4], "9332BDT ");
2134	}
2135	return;
2136    }
2137    id1 = sc->tulip_rombuf[0x60] | (sc->tulip_rombuf[0x61] << 8);
2138    id2 = sc->tulip_rombuf[0x62] | (sc->tulip_rombuf[0x63] << 8);
2139    ei  = sc->tulip_rombuf[0x66] | (sc->tulip_rombuf[0x67] << 8);
2140
2141    strcpy(&sc->tulip_boardid[4], "8432");
2142    cp = &sc->tulip_boardid[8];
2143    if ((id1 & 1) == 0)
2144	*cp++ = 'B', auibnc = 1;
2145    if ((id1 & 0xFF) > 0x32)
2146	*cp++ = 'T', utp = 1;
2147    if ((id1 & 0x4000) == 0)
2148	*cp++ = 'A', auibnc = 1;
2149    if (id2 == 0x15) {
2150	sc->tulip_boardid[7] = '4';
2151	*cp++ = '-';
2152	*cp++ = 'C';
2153	*cp++ = 'H';
2154	*cp++ = (ei ? '2' : '1');
2155    }
2156    *cp++ = ' ';
2157    *cp = '\0';
2158    if (utp && !auibnc)
2159	sc->tulip_boardsw = &tulip_21040_10baset_only_boardsw;
2160    else if (!utp && auibnc)
2161	sc->tulip_boardsw = &tulip_21040_auibnc_only_boardsw;
2162}
2163
2164static void
2165tulip_identify_cogent_nic(
2166    tulip_softc_t * const sc)
2167{
2168    strcpy(sc->tulip_boardid, "Cogent ");
2169    if (sc->tulip_chipid == TULIP_21140 || sc->tulip_chipid == TULIP_21140A) {
2170	if (sc->tulip_rombuf[32] == TULIP_COGENT_EM100TX_ID) {
2171	    strcat(sc->tulip_boardid, "EM100TX ");
2172	    sc->tulip_boardsw = &tulip_21140_cogent_em100_boardsw;
2173#if defined(TULIP_COGENT_EM110TX_ID)
2174	} else if (sc->tulip_rombuf[32] == TULIP_COGENT_EM110TX_ID) {
2175	    strcat(sc->tulip_boardid, "EM110TX ");
2176	    sc->tulip_boardsw = &tulip_21140_cogent_em100_boardsw;
2177#endif
2178	} else if (sc->tulip_rombuf[32] == TULIP_COGENT_EM100FX_ID) {
2179	    strcat(sc->tulip_boardid, "EM100FX ");
2180	    sc->tulip_boardsw = &tulip_21140_cogent_em100_boardsw;
2181	}
2182	/*
2183	 * Magic number (0x24001109U) is the SubVendor (0x2400) and
2184	 * SubDevId (0x1109) for the ANA6944TX (EM440TX).
2185	 */
2186	if (*(u_int32_t *) sc->tulip_rombuf == 0x24001109U
2187		&& (sc->tulip_features & TULIP_HAVE_BASEROM)) {
2188	    /*
2189	     * Cogent (Adaptec) is still mapping all INTs to INTA of
2190	     * first 21140.  Dumb!  Dumb!
2191	     */
2192	    strcat(sc->tulip_boardid, "EM440TX ");
2193	    sc->tulip_features |= TULIP_HAVE_SHAREDINTR;
2194	}
2195    } else if (sc->tulip_chipid == TULIP_21040) {
2196	sc->tulip_features |= TULIP_HAVE_SHAREDINTR|TULIP_HAVE_BASEROM;
2197    }
2198}
2199
2200static void
2201tulip_identify_accton_nic(
2202    tulip_softc_t * const sc)
2203{
2204    strcpy(sc->tulip_boardid, "ACCTON ");
2205    switch (sc->tulip_chipid) {
2206	case TULIP_21140A:
2207	    strcat(sc->tulip_boardid, "EN1207 ");
2208	    if (sc->tulip_boardsw != &tulip_2114x_isv_boardsw)
2209		sc->tulip_boardsw = &tulip_21140_accton_boardsw;
2210	    break;
2211	case TULIP_21140:
2212	    strcat(sc->tulip_boardid, "EN1207TX ");
2213	    if (sc->tulip_boardsw != &tulip_2114x_isv_boardsw)
2214		sc->tulip_boardsw = &tulip_21140_eb_boardsw;
2215            break;
2216        case TULIP_21040:
2217	    strcat(sc->tulip_boardid, "EN1203 ");
2218            sc->tulip_boardsw = &tulip_21040_boardsw;
2219            break;
2220        case TULIP_21041:
2221	    strcat(sc->tulip_boardid, "EN1203 ");
2222            sc->tulip_boardsw = &tulip_21041_boardsw;
2223            break;
2224	default:
2225            sc->tulip_boardsw = &tulip_2114x_isv_boardsw;
2226            break;
2227    }
2228}
2229
2230static void
2231tulip_identify_asante_nic(
2232    tulip_softc_t * const sc)
2233{
2234    strcpy(sc->tulip_boardid, "Asante ");
2235    if ((sc->tulip_chipid == TULIP_21140 || sc->tulip_chipid == TULIP_21140A)
2236	    && sc->tulip_boardsw != &tulip_2114x_isv_boardsw) {
2237	tulip_media_info_t *mi = sc->tulip_mediainfo;
2238	int idx;
2239	/*
2240	 * The Asante Fast Ethernet doesn't always ship with a valid
2241	 * new format SROM.  So if isn't in the new format, we cheat
2242	 * set it up as if we had.
2243	 */
2244
2245	sc->tulip_gpinit = TULIP_GP_ASANTE_PINS;
2246	sc->tulip_gpdata = 0;
2247
2248	TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_ASANTE_PINS|TULIP_GP_PINSET);
2249	TULIP_CSR_WRITE(sc, csr_gp, TULIP_GP_ASANTE_PHYRESET);
2250	DELAY(100);
2251	TULIP_CSR_WRITE(sc, csr_gp, 0);
2252
2253	mi->mi_type = TULIP_MEDIAINFO_MII;
2254	mi->mi_gpr_length = 0;
2255	mi->mi_gpr_offset = 0;
2256	mi->mi_reset_length = 0;
2257	mi->mi_reset_offset = 0;;
2258
2259	mi->mi_phyaddr = TULIP_MII_NOPHY;
2260	for (idx = 20; idx > 0 && mi->mi_phyaddr == TULIP_MII_NOPHY; idx--) {
2261	    DELAY(10000);
2262	    mi->mi_phyaddr = tulip_mii_get_phyaddr(sc, 0);
2263	}
2264	if (mi->mi_phyaddr == TULIP_MII_NOPHY) {
2265	    printf("%s: can't find phy 0\n", sc->tulip_xname);
2266	    return;
2267	}
2268
2269	sc->tulip_features |= TULIP_HAVE_MII;
2270	mi->mi_capabilities  = PHYSTS_10BASET|PHYSTS_10BASET_FD|PHYSTS_100BASETX|PHYSTS_100BASETX_FD;
2271	mi->mi_advertisement = PHYSTS_10BASET|PHYSTS_10BASET_FD|PHYSTS_100BASETX|PHYSTS_100BASETX_FD;
2272	mi->mi_full_duplex   = PHYSTS_10BASET_FD|PHYSTS_100BASETX_FD;
2273	mi->mi_tx_threshold  = PHYSTS_10BASET|PHYSTS_10BASET_FD;
2274	TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 100BASETX_FD);
2275	TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 100BASETX);
2276	TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 100BASET4);
2277	TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 10BASET_FD);
2278	TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 10BASET);
2279	mi->mi_phyid = (tulip_mii_readreg(sc, mi->mi_phyaddr, PHYREG_IDLOW) << 16) |
2280	    tulip_mii_readreg(sc, mi->mi_phyaddr, PHYREG_IDHIGH);
2281
2282	sc->tulip_boardsw = &tulip_2114x_isv_boardsw;
2283    }
2284}
2285
2286static void
2287tulip_identify_compex_nic(
2288    tulip_softc_t * const sc)
2289{
2290    strcpy(sc->tulip_boardid, "COMPEX ");
2291    if (sc->tulip_chipid == TULIP_21140A) {
2292	int root_unit;
2293	tulip_softc_t *root_sc = NULL;
2294
2295	strcat(sc->tulip_boardid, "400TX/PCI ");
2296	/*
2297	 * All 4 chips on these boards share an interrupt.  This code
2298	 * copied from tulip_read_macaddr.
2299	 */
2300	sc->tulip_features |= TULIP_HAVE_SHAREDINTR;
2301	for (root_unit = sc->tulip_unit - 1; root_unit >= 0; root_unit--) {
2302	    root_sc = tulips[root_unit];
2303	    if (root_sc == NULL
2304		|| !(root_sc->tulip_features & TULIP_HAVE_SLAVEDINTR))
2305		break;
2306	    root_sc = NULL;
2307	}
2308	if (root_sc != NULL
2309	    && root_sc->tulip_chipid == sc->tulip_chipid
2310	    && root_sc->tulip_pci_busno == sc->tulip_pci_busno) {
2311	    sc->tulip_features |= TULIP_HAVE_SLAVEDINTR;
2312	    sc->tulip_slaves = root_sc->tulip_slaves;
2313	    root_sc->tulip_slaves = sc;
2314	} else if(sc->tulip_features & TULIP_HAVE_SLAVEDINTR) {
2315	    printf("\nCannot find master device for %s interrupts",
2316		   sc->tulip_xname);
2317	}
2318    } else {
2319	strcat(sc->tulip_boardid, "unknown ");
2320    }
2321    /*      sc->tulip_boardsw = &tulip_21140_eb_boardsw; */
2322    return;
2323}
2324
2325static int
2326tulip_srom_decode(
2327    tulip_softc_t * const sc)
2328{
2329    unsigned idx1, idx2, idx3;
2330
2331    const tulip_srom_header_t *shp = (const tulip_srom_header_t *) &sc->tulip_rombuf[0];
2332    const tulip_srom_adapter_info_t *saip = (const tulip_srom_adapter_info_t *) (shp + 1);
2333    tulip_srom_media_t srom_media;
2334    tulip_media_info_t *mi = sc->tulip_mediainfo;
2335    const u_int8_t *dp;
2336    u_int32_t leaf_offset, blocks, data;
2337
2338    for (idx1 = 0; idx1 < shp->sh_adapter_count; idx1++, saip++) {
2339	if (shp->sh_adapter_count == 1)
2340	    break;
2341	if (saip->sai_device == sc->tulip_pci_devno)
2342	    break;
2343    }
2344    /*
2345     * Didn't find the right media block for this card.
2346     */
2347    if (idx1 == shp->sh_adapter_count)
2348	return 0;
2349
2350    /*
2351     * Save the hardware address.
2352     */
2353    bcopy(shp->sh_ieee802_address, sc->tulip_enaddr, 6);
2354    /*
2355     * If this is a multiple port card, add the adapter index to the last
2356     * byte of the hardware address.  (if it isn't multiport, adding 0
2357     * won't hurt.
2358     */
2359    sc->tulip_enaddr[5] += idx1;
2360
2361    leaf_offset = saip->sai_leaf_offset_lowbyte
2362	+ saip->sai_leaf_offset_highbyte * 256;
2363    dp = sc->tulip_rombuf + leaf_offset;
2364
2365    sc->tulip_conntype = (tulip_srom_connection_t) (dp[0] + dp[1] * 256); dp += 2;
2366
2367    for (idx2 = 0;; idx2++) {
2368	if (tulip_srom_conninfo[idx2].sc_type == sc->tulip_conntype
2369	        || tulip_srom_conninfo[idx2].sc_type == TULIP_SROM_CONNTYPE_NOT_USED)
2370	    break;
2371    }
2372    sc->tulip_connidx = idx2;
2373
2374    if (sc->tulip_chipid == TULIP_21041) {
2375	blocks = *dp++;
2376	for (idx2 = 0; idx2 < blocks; idx2++) {
2377	    tulip_media_t media;
2378	    data = *dp++;
2379	    srom_media = (tulip_srom_media_t) (data & 0x3F);
2380	    for (idx3 = 0; tulip_srom_mediums[idx3].sm_type != TULIP_MEDIA_UNKNOWN; idx3++) {
2381		if (tulip_srom_mediums[idx3].sm_srom_type == srom_media)
2382		    break;
2383	    }
2384	    media = tulip_srom_mediums[idx3].sm_type;
2385	    if (media != TULIP_MEDIA_UNKNOWN) {
2386		if (data & TULIP_SROM_21041_EXTENDED) {
2387		    mi->mi_type = TULIP_MEDIAINFO_SIA;
2388		    sc->tulip_mediums[media] = mi;
2389		    mi->mi_sia_connectivity = dp[0] + dp[1] * 256;
2390		    mi->mi_sia_tx_rx        = dp[2] + dp[3] * 256;
2391		    mi->mi_sia_general      = dp[4] + dp[5] * 256;
2392		    mi++;
2393		} else {
2394		    switch (media) {
2395			case TULIP_MEDIA_BNC: {
2396			    TULIP_MEDIAINFO_SIA_INIT(sc, mi, 21041, BNC);
2397			    mi++;
2398			    break;
2399			}
2400			case TULIP_MEDIA_AUI: {
2401			    TULIP_MEDIAINFO_SIA_INIT(sc, mi, 21041, AUI);
2402			    mi++;
2403			    break;
2404			}
2405			case TULIP_MEDIA_10BASET: {
2406			    TULIP_MEDIAINFO_SIA_INIT(sc, mi, 21041, 10BASET);
2407			    mi++;
2408			    break;
2409			}
2410			case TULIP_MEDIA_10BASET_FD: {
2411			    TULIP_MEDIAINFO_SIA_INIT(sc, mi, 21041, 10BASET_FD);
2412			    mi++;
2413			    break;
2414			}
2415			default: {
2416			    break;
2417			}
2418		    }
2419		}
2420	    }
2421	    if (data & TULIP_SROM_21041_EXTENDED)
2422		dp += 6;
2423	}
2424#ifdef notdef
2425	if (blocks == 0) {
2426	    TULIP_MEDIAINFO_SIA_INIT(sc, mi, 21041, BNC); mi++;
2427	    TULIP_MEDIAINFO_SIA_INIT(sc, mi, 21041, AUI); mi++;
2428	    TULIP_MEDIAINFO_SIA_INIT(sc, mi, 21041, 10BASET); mi++;
2429	    TULIP_MEDIAINFO_SIA_INIT(sc, mi, 21041, 10BASET_FD); mi++;
2430	}
2431#endif
2432    } else {
2433	unsigned length, type;
2434	tulip_media_t gp_media = TULIP_MEDIA_UNKNOWN;
2435	if (sc->tulip_features & TULIP_HAVE_GPR)
2436	    sc->tulip_gpinit = *dp++;
2437	blocks = *dp++;
2438	for (idx2 = 0; idx2 < blocks; idx2++) {
2439	    const u_int8_t *ep;
2440	    if ((*dp & 0x80) == 0) {
2441		length = 4;
2442		type = 0;
2443	    } else {
2444		length = (*dp++ & 0x7f) - 1;
2445		type = *dp++ & 0x3f;
2446	    }
2447	    ep = dp + length;
2448	    switch (type & 0x3f) {
2449		case 0: {	/* 21140[A] GPR block */
2450		    tulip_media_t media;
2451		    srom_media = (tulip_srom_media_t)(dp[0] & 0x3f);
2452		    for (idx3 = 0; tulip_srom_mediums[idx3].sm_type != TULIP_MEDIA_UNKNOWN; idx3++) {
2453			if (tulip_srom_mediums[idx3].sm_srom_type == srom_media)
2454			    break;
2455		    }
2456		    media = tulip_srom_mediums[idx3].sm_type;
2457		    if (media == TULIP_MEDIA_UNKNOWN)
2458			break;
2459		    mi->mi_type = TULIP_MEDIAINFO_GPR;
2460		    sc->tulip_mediums[media] = mi;
2461		    mi->mi_gpdata = dp[1];
2462		    if (media > gp_media && !TULIP_IS_MEDIA_FD(media)) {
2463			sc->tulip_gpdata = mi->mi_gpdata;
2464			gp_media = media;
2465		    }
2466		    data = dp[2] + dp[3] * 256;
2467		    mi->mi_cmdmode = TULIP_SROM_2114X_CMDBITS(data);
2468		    if (data & TULIP_SROM_2114X_NOINDICATOR) {
2469			mi->mi_actmask = 0;
2470		    } else {
2471#if 0
2472			mi->mi_default = (data & TULIP_SROM_2114X_DEFAULT) != 0;
2473#endif
2474			mi->mi_actmask = TULIP_SROM_2114X_BITPOS(data);
2475			mi->mi_actdata = (data & TULIP_SROM_2114X_POLARITY) ? 0 : mi->mi_actmask;
2476		    }
2477		    mi++;
2478		    break;
2479		}
2480		case 1: {	/* 21140[A] MII block */
2481		    const unsigned phyno = *dp++;
2482		    mi->mi_type = TULIP_MEDIAINFO_MII;
2483		    mi->mi_gpr_length = *dp++;
2484		    mi->mi_gpr_offset = dp - sc->tulip_rombuf;
2485		    dp += mi->mi_gpr_length;
2486		    mi->mi_reset_length = *dp++;
2487		    mi->mi_reset_offset = dp - sc->tulip_rombuf;
2488		    dp += mi->mi_reset_length;
2489
2490		    /*
2491		     * Before we probe for a PHY, use the GPR information
2492		     * to select it.  If we don't, it may be inaccessible.
2493		     */
2494		    TULIP_CSR_WRITE(sc, csr_gp, sc->tulip_gpinit|TULIP_GP_PINSET);
2495		    for (idx3 = 0; idx3 < mi->mi_reset_length; idx3++) {
2496			DELAY(10);
2497			TULIP_CSR_WRITE(sc, csr_gp, sc->tulip_rombuf[mi->mi_reset_offset + idx3]);
2498		    }
2499		    sc->tulip_phyaddr = mi->mi_phyaddr;
2500		    for (idx3 = 0; idx3 < mi->mi_gpr_length; idx3++) {
2501			DELAY(10);
2502			TULIP_CSR_WRITE(sc, csr_gp, sc->tulip_rombuf[mi->mi_gpr_offset + idx3]);
2503		    }
2504
2505		    /*
2506		     * At least write something!
2507		     */
2508		    if (mi->mi_reset_length == 0 && mi->mi_gpr_length == 0)
2509			TULIP_CSR_WRITE(sc, csr_gp, 0);
2510
2511		    mi->mi_phyaddr = TULIP_MII_NOPHY;
2512		    for (idx3 = 20; idx3 > 0 && mi->mi_phyaddr == TULIP_MII_NOPHY; idx3--) {
2513			DELAY(10000);
2514			mi->mi_phyaddr = tulip_mii_get_phyaddr(sc, phyno);
2515		    }
2516		    if (mi->mi_phyaddr == TULIP_MII_NOPHY) {
2517#if defined(TULIP_DEBUG)
2518			printf("%s: can't find phy %d\n",
2519			       sc->tulip_xname, phyno);
2520#endif
2521			break;
2522		    }
2523		    sc->tulip_features |= TULIP_HAVE_MII;
2524		    mi->mi_capabilities  = dp[0] + dp[1] * 256; dp += 2;
2525		    mi->mi_advertisement = dp[0] + dp[1] * 256; dp += 2;
2526		    mi->mi_full_duplex   = dp[0] + dp[1] * 256; dp += 2;
2527		    mi->mi_tx_threshold  = dp[0] + dp[1] * 256; dp += 2;
2528		    TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 100BASETX_FD);
2529		    TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 100BASETX);
2530		    TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 100BASET4);
2531		    TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 10BASET_FD);
2532		    TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 10BASET);
2533		    mi->mi_phyid = (tulip_mii_readreg(sc, mi->mi_phyaddr, PHYREG_IDLOW) << 16) |
2534			tulip_mii_readreg(sc, mi->mi_phyaddr, PHYREG_IDHIGH);
2535		    mi++;
2536		    break;
2537		}
2538		case 2: {	/* 2114[23] SIA block */
2539		    tulip_media_t media;
2540		    srom_media = (tulip_srom_media_t)(dp[0] & 0x3f);
2541		    for (idx3 = 0; tulip_srom_mediums[idx3].sm_type != TULIP_MEDIA_UNKNOWN; idx3++) {
2542			if (tulip_srom_mediums[idx3].sm_srom_type == srom_media)
2543			    break;
2544		    }
2545		    media = tulip_srom_mediums[idx3].sm_type;
2546		    if (media == TULIP_MEDIA_UNKNOWN)
2547			break;
2548		    mi->mi_type = TULIP_MEDIAINFO_SIA;
2549		    sc->tulip_mediums[media] = mi;
2550		    if (dp[0] & 0x40) {
2551			mi->mi_sia_connectivity = dp[1] + dp[2] * 256;
2552			mi->mi_sia_tx_rx        = dp[3] + dp[4] * 256;
2553			mi->mi_sia_general      = dp[5] + dp[6] * 256;
2554			dp += 6;
2555		    } else {
2556			switch (media) {
2557			    case TULIP_MEDIA_BNC: {
2558				TULIP_MEDIAINFO_SIA_INIT(sc, mi, 21142, BNC);
2559				break;
2560			    }
2561			    case TULIP_MEDIA_AUI: {
2562				TULIP_MEDIAINFO_SIA_INIT(sc, mi, 21142, AUI);
2563				break;
2564			    }
2565			    case TULIP_MEDIA_10BASET: {
2566				TULIP_MEDIAINFO_SIA_INIT(sc, mi, 21142, 10BASET);
2567				sc->tulip_intrmask |= TULIP_STS_LINKPASS|TULIP_STS_LINKFAIL;
2568				break;
2569			    }
2570			    case TULIP_MEDIA_10BASET_FD: {
2571				TULIP_MEDIAINFO_SIA_INIT(sc, mi, 21142, 10BASET_FD);
2572				sc->tulip_intrmask |= TULIP_STS_LINKPASS|TULIP_STS_LINKFAIL;
2573				break;
2574			    }
2575			    default: {
2576				goto bad_media;
2577			    }
2578			}
2579		    }
2580		    mi->mi_sia_gp_control = (dp[1] + dp[2] * 256) << 16;
2581		    mi->mi_sia_gp_data    = (dp[3] + dp[4] * 256) << 16;
2582		    mi++;
2583		  bad_media:
2584		    break;
2585		}
2586		case 3: {	/* 2114[23] MII PHY block */
2587		    const unsigned phyno = *dp++;
2588		    const u_int8_t *dp0;
2589		    mi->mi_type = TULIP_MEDIAINFO_MII;
2590		    mi->mi_gpr_length = *dp++;
2591		    mi->mi_gpr_offset = dp - sc->tulip_rombuf;
2592		    dp += 2 * mi->mi_gpr_length;
2593		    mi->mi_reset_length = *dp++;
2594		    mi->mi_reset_offset = dp - sc->tulip_rombuf;
2595		    dp += 2 * mi->mi_reset_length;
2596
2597		    dp0 = &sc->tulip_rombuf[mi->mi_reset_offset];
2598		    for (idx3 = 0; idx3 < mi->mi_reset_length; idx3++, dp0 += 2) {
2599			DELAY(10);
2600			TULIP_CSR_WRITE(sc, csr_sia_general, (dp0[0] + 256 * dp0[1]) << 16);
2601		    }
2602		    sc->tulip_phyaddr = mi->mi_phyaddr;
2603		    dp0 = &sc->tulip_rombuf[mi->mi_gpr_offset];
2604		    for (idx3 = 0; idx3 < mi->mi_gpr_length; idx3++, dp0 += 2) {
2605			DELAY(10);
2606			TULIP_CSR_WRITE(sc, csr_sia_general, (dp0[0] + 256 * dp0[1]) << 16);
2607		    }
2608
2609		    if (mi->mi_reset_length == 0 && mi->mi_gpr_length == 0)
2610			TULIP_CSR_WRITE(sc, csr_sia_general, 0);
2611
2612		    mi->mi_phyaddr = TULIP_MII_NOPHY;
2613		    for (idx3 = 20; idx3 > 0 && mi->mi_phyaddr == TULIP_MII_NOPHY; idx3--) {
2614			DELAY(10000);
2615			mi->mi_phyaddr = tulip_mii_get_phyaddr(sc, phyno);
2616		    }
2617		    if (mi->mi_phyaddr == TULIP_MII_NOPHY) {
2618#if defined(TULIP_DEBUG)
2619			printf("%s: can't find phy %d\n",
2620			       sc->tulip_xname, phyno);
2621#endif
2622			break;
2623		    }
2624		    sc->tulip_features |= TULIP_HAVE_MII;
2625		    mi->mi_capabilities  = dp[0] + dp[1] * 256; dp += 2;
2626		    mi->mi_advertisement = dp[0] + dp[1] * 256; dp += 2;
2627		    mi->mi_full_duplex   = dp[0] + dp[1] * 256; dp += 2;
2628		    mi->mi_tx_threshold  = dp[0] + dp[1] * 256; dp += 2;
2629		    mi->mi_mii_interrupt = dp[0] + dp[1] * 256; dp += 2;
2630		    TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 100BASETX_FD);
2631		    TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 100BASETX);
2632		    TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 100BASET4);
2633		    TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 10BASET_FD);
2634		    TULIP_MEDIAINFO_ADD_CAPABILITY(sc, mi, 10BASET);
2635		    mi->mi_phyid = (tulip_mii_readreg(sc, mi->mi_phyaddr, PHYREG_IDLOW) << 16) |
2636			tulip_mii_readreg(sc, mi->mi_phyaddr, PHYREG_IDHIGH);
2637		    mi++;
2638		    break;
2639		}
2640		case 4: {	/* 21143 SYM block */
2641		    tulip_media_t media;
2642		    srom_media = (tulip_srom_media_t) dp[0];
2643		    for (idx3 = 0; tulip_srom_mediums[idx3].sm_type != TULIP_MEDIA_UNKNOWN; idx3++) {
2644			if (tulip_srom_mediums[idx3].sm_srom_type == srom_media)
2645			    break;
2646		    }
2647		    media = tulip_srom_mediums[idx3].sm_type;
2648		    if (media == TULIP_MEDIA_UNKNOWN)
2649			break;
2650		    mi->mi_type = TULIP_MEDIAINFO_SYM;
2651		    sc->tulip_mediums[media] = mi;
2652		    mi->mi_gpcontrol = (dp[1] + dp[2] * 256) << 16;
2653		    mi->mi_gpdata    = (dp[3] + dp[4] * 256) << 16;
2654		    data = dp[5] + dp[6] * 256;
2655		    mi->mi_cmdmode = TULIP_SROM_2114X_CMDBITS(data);
2656		    if (data & TULIP_SROM_2114X_NOINDICATOR) {
2657			mi->mi_actmask = 0;
2658		    } else {
2659			mi->mi_default = (data & TULIP_SROM_2114X_DEFAULT) != 0;
2660			mi->mi_actmask = TULIP_SROM_2114X_BITPOS(data);
2661			mi->mi_actdata = (data & TULIP_SROM_2114X_POLARITY) ? 0 : mi->mi_actmask;
2662		    }
2663		    if (TULIP_IS_MEDIA_TP(media))
2664			sc->tulip_intrmask |= TULIP_STS_LINKPASS|TULIP_STS_LINKFAIL;
2665		    mi++;
2666		    break;
2667		}
2668#if 0
2669		case 5: {	/* 21143 Reset block */
2670		    mi->mi_type = TULIP_MEDIAINFO_RESET;
2671		    mi->mi_reset_length = *dp++;
2672		    mi->mi_reset_offset = dp - sc->tulip_rombuf;
2673		    dp += 2 * mi->mi_reset_length;
2674		    mi++;
2675		    break;
2676		}
2677#endif
2678		default: {
2679		}
2680	    }
2681	    dp = ep;
2682	}
2683    }
2684    return mi - sc->tulip_mediainfo;
2685}
2686
2687static const struct {
2688    void (*vendor_identify_nic)(tulip_softc_t * const sc);
2689    unsigned char vendor_oui[3];
2690} tulip_vendors[] = {
2691    { tulip_identify_dec_nic,		{ 0x08, 0x00, 0x2B } },
2692    { tulip_identify_dec_nic,		{ 0x00, 0x00, 0xF8 } },
2693    { tulip_identify_smc_nic,		{ 0x00, 0x00, 0xC0 } },
2694    { tulip_identify_smc_nic,		{ 0x00, 0xE0, 0x29 } },
2695    { tulip_identify_znyx_nic,		{ 0x00, 0xC0, 0x95 } },
2696    { tulip_identify_cogent_nic,	{ 0x00, 0x00, 0x92 } },
2697    { tulip_identify_asante_nic,	{ 0x00, 0x00, 0x94 } },
2698    { tulip_identify_cogent_nic,	{ 0x00, 0x00, 0xD1 } },
2699    { tulip_identify_accton_nic,	{ 0x00, 0x00, 0xE8 } },
2700    { tulip_identify_compex_nic,        { 0x00, 0x80, 0x48 } },
2701    { NULL }
2702};
2703
2704/*
2705 * This deals with the vagaries of the address roms and the
2706 * brain-deadness that various vendors commit in using them.
2707 */
2708static int
2709tulip_read_macaddr(
2710    tulip_softc_t * const sc)
2711{
2712    unsigned cksum, rom_cksum, idx;
2713    u_int32_t csr;
2714    unsigned char tmpbuf[8];
2715    static const u_char testpat[] = { 0xFF, 0, 0x55, 0xAA, 0xFF, 0, 0x55, 0xAA };
2716
2717    sc->tulip_connidx = TULIP_SROM_LASTCONNIDX;
2718
2719    if (sc->tulip_chipid == TULIP_21040) {
2720	TULIP_CSR_WRITE(sc, csr_enetrom, 1);
2721	for (idx = 0; idx < sizeof(sc->tulip_rombuf); idx++) {
2722	    int cnt = 0;
2723	    while (((csr = TULIP_CSR_READ(sc, csr_enetrom)) & 0x80000000L) && cnt < 10000)
2724		cnt++;
2725	    sc->tulip_rombuf[idx] = csr & 0xFF;
2726	}
2727	sc->tulip_boardsw = &tulip_21040_boardsw;
2728    } else {
2729	if (sc->tulip_chipid == TULIP_21041) {
2730	    /*
2731	     * Thankfully all 21041's act the same.
2732	     */
2733	    sc->tulip_boardsw = &tulip_21041_boardsw;
2734	} else {
2735	    /*
2736	     * Assume all 21140 board are compatible with the
2737	     * DEC 10/100 evaluation board.  Not really valid but
2738	     * it's the best we can do until every one switches to
2739	     * the new SROM format.
2740	     */
2741
2742	    sc->tulip_boardsw = &tulip_21140_eb_boardsw;
2743	}
2744	tulip_srom_read(sc);
2745	if (tulip_srom_crcok(sc->tulip_rombuf)) {
2746	    /*
2747	     * SROM CRC is valid therefore it must be in the
2748	     * new format.
2749	     */
2750	    sc->tulip_features |= TULIP_HAVE_ISVSROM|TULIP_HAVE_OKSROM;
2751	} else if (sc->tulip_rombuf[126] == 0xff && sc->tulip_rombuf[127] == 0xFF) {
2752	    /*
2753	     * No checksum is present.  See if the SROM id checks out;
2754	     * the first 18 bytes should be 0 followed by a 1 followed
2755	     * by the number of adapters (which we don't deal with yet).
2756	     */
2757	    for (idx = 0; idx < 18; idx++) {
2758		if (sc->tulip_rombuf[idx] != 0)
2759		    break;
2760	    }
2761	    if (idx == 18 && sc->tulip_rombuf[18] == 1 && sc->tulip_rombuf[19] != 0)
2762		sc->tulip_features |= TULIP_HAVE_ISVSROM;
2763	} else if (sc->tulip_chipid >= TULIP_21142) {
2764	    sc->tulip_features |= TULIP_HAVE_ISVSROM;
2765	    sc->tulip_boardsw = &tulip_2114x_isv_boardsw;
2766	}
2767	if ((sc->tulip_features & TULIP_HAVE_ISVSROM) && tulip_srom_decode(sc)) {
2768	    if (sc->tulip_chipid != TULIP_21041)
2769		sc->tulip_boardsw = &tulip_2114x_isv_boardsw;
2770
2771	    /*
2772	     * If the SROM specifies more than one adapter, tag this as a
2773	     * BASE rom.
2774	     */
2775	    if (sc->tulip_rombuf[19] > 1)
2776		sc->tulip_features |= TULIP_HAVE_BASEROM;
2777	    if (sc->tulip_boardsw == NULL)
2778		return -6;
2779	    goto check_oui;
2780	}
2781    }
2782
2783
2784    if (bcmp(&sc->tulip_rombuf[0], &sc->tulip_rombuf[16], 8) != 0) {
2785	/*
2786	 * Some folks don't use the standard ethernet rom format
2787	 * but instead just put the address in the first 6 bytes
2788	 * of the rom and let the rest be all 0xffs.  (Can we say
2789	 * ZNYX?) (well sometimes they put in a checksum so we'll
2790	 * start at 8).
2791	 */
2792	for (idx = 8; idx < 32; idx++) {
2793	    if (sc->tulip_rombuf[idx] != 0xFF)
2794		return -4;
2795	}
2796	/*
2797	 * Make sure the address is not multicast or locally assigned
2798	 * that the OUI is not 00-00-00.
2799	 */
2800	if ((sc->tulip_rombuf[0] & 3) != 0)
2801	    return -4;
2802	if (sc->tulip_rombuf[0] == 0 && sc->tulip_rombuf[1] == 0
2803		&& sc->tulip_rombuf[2] == 0)
2804	    return -4;
2805	bcopy(sc->tulip_rombuf, sc->tulip_enaddr, 6);
2806	sc->tulip_features |= TULIP_HAVE_OKROM;
2807	goto check_oui;
2808    } else {
2809	/*
2810	 * A number of makers of multiport boards (ZNYX and Cogent)
2811	 * only put on one address ROM on their 21040 boards.  So
2812	 * if the ROM is all zeros (or all 0xFFs), look at the
2813	 * previous configured boards (as long as they are on the same
2814	 * PCI bus and the bus number is non-zero) until we find the
2815	 * master board with address ROM.  We then use its address ROM
2816	 * as the base for this board.  (we add our relative board
2817	 * to the last byte of its address).
2818	 */
2819	for (idx = 0; idx < sizeof(sc->tulip_rombuf); idx++) {
2820	    if (sc->tulip_rombuf[idx] != 0 && sc->tulip_rombuf[idx] != 0xFF)
2821		break;
2822	}
2823	if (idx == sizeof(sc->tulip_rombuf)) {
2824	    int root_unit;
2825	    tulip_softc_t *root_sc = NULL;
2826	    for (root_unit = sc->tulip_unit - 1; root_unit >= 0; root_unit--) {
2827		root_sc = tulips[root_unit];
2828		if (root_sc == NULL || (root_sc->tulip_features & (TULIP_HAVE_OKROM|TULIP_HAVE_SLAVEDROM)) == TULIP_HAVE_OKROM)
2829		    break;
2830		root_sc = NULL;
2831	    }
2832	    if (root_sc != NULL && (root_sc->tulip_features & TULIP_HAVE_BASEROM)
2833		    && root_sc->tulip_chipid == sc->tulip_chipid
2834		    && root_sc->tulip_pci_busno == sc->tulip_pci_busno) {
2835		sc->tulip_features |= TULIP_HAVE_SLAVEDROM;
2836		sc->tulip_boardsw = root_sc->tulip_boardsw;
2837		strcpy(sc->tulip_boardid, root_sc->tulip_boardid);
2838		if (sc->tulip_boardsw->bd_type == TULIP_21140_ISV) {
2839		    bcopy(root_sc->tulip_rombuf, sc->tulip_rombuf,
2840			  sizeof(sc->tulip_rombuf));
2841		    if (!tulip_srom_decode(sc))
2842			return -5;
2843		} else {
2844		    bcopy(root_sc->tulip_enaddr, sc->tulip_enaddr, 6);
2845		    sc->tulip_enaddr[5] += sc->tulip_unit - root_sc->tulip_unit;
2846		}
2847		/*
2848		 * Now for a truly disgusting kludge: all 4 21040s on
2849		 * the ZX314 share the same INTA line so the mapping
2850		 * setup by the BIOS on the PCI bridge is worthless.
2851		 * Rather than reprogramming the value in the config
2852		 * register, we will handle this internally.
2853		 */
2854		if (root_sc->tulip_features & TULIP_HAVE_SHAREDINTR) {
2855		    sc->tulip_slaves = root_sc->tulip_slaves;
2856		    root_sc->tulip_slaves = sc;
2857		    sc->tulip_features |= TULIP_HAVE_SLAVEDINTR;
2858		}
2859		return 0;
2860	    }
2861	}
2862    }
2863
2864    /*
2865     * This is the standard DEC address ROM test.
2866     */
2867
2868    if (bcmp(&sc->tulip_rombuf[24], testpat, 8) != 0)
2869	return -3;
2870
2871    tmpbuf[0] = sc->tulip_rombuf[15]; tmpbuf[1] = sc->tulip_rombuf[14];
2872    tmpbuf[2] = sc->tulip_rombuf[13]; tmpbuf[3] = sc->tulip_rombuf[12];
2873    tmpbuf[4] = sc->tulip_rombuf[11]; tmpbuf[5] = sc->tulip_rombuf[10];
2874    tmpbuf[6] = sc->tulip_rombuf[9];  tmpbuf[7] = sc->tulip_rombuf[8];
2875    if (bcmp(&sc->tulip_rombuf[0], tmpbuf, 8) != 0)
2876	return -2;
2877
2878    bcopy(sc->tulip_rombuf, sc->tulip_enaddr, 6);
2879
2880    cksum = *(u_int16_t *) &sc->tulip_enaddr[0];
2881    cksum *= 2;
2882    if (cksum > 65535) cksum -= 65535;
2883    cksum += *(u_int16_t *) &sc->tulip_enaddr[2];
2884    if (cksum > 65535) cksum -= 65535;
2885    cksum *= 2;
2886    if (cksum > 65535) cksum -= 65535;
2887    cksum += *(u_int16_t *) &sc->tulip_enaddr[4];
2888    if (cksum >= 65535) cksum -= 65535;
2889
2890    rom_cksum = *(u_int16_t *) &sc->tulip_rombuf[6];
2891
2892    if (cksum != rom_cksum)
2893	return -1;
2894
2895  check_oui:
2896    /*
2897     * Check for various boards based on OUI.  Did I say braindead?
2898     */
2899    for (idx = 0; tulip_vendors[idx].vendor_identify_nic != NULL; idx++) {
2900	if (bcmp(sc->tulip_enaddr, tulip_vendors[idx].vendor_oui, 3) == 0) {
2901	    (*tulip_vendors[idx].vendor_identify_nic)(sc);
2902	    break;
2903	}
2904    }
2905
2906    sc->tulip_features |= TULIP_HAVE_OKROM;
2907    return 0;
2908}
2909
2910static void
2911tulip_ifmedia_add(
2912    tulip_softc_t * const sc)
2913{
2914    tulip_media_t media;
2915    int medias = 0;
2916
2917    for (media = TULIP_MEDIA_UNKNOWN; media < TULIP_MEDIA_MAX; media++) {
2918	if (sc->tulip_mediums[media] != NULL) {
2919	    ifmedia_add(&sc->tulip_ifmedia, tulip_media_to_ifmedia[media],
2920			0, 0);
2921	    medias++;
2922	}
2923    }
2924    if (medias == 0) {
2925	sc->tulip_features |= TULIP_HAVE_NOMEDIA;
2926	ifmedia_add(&sc->tulip_ifmedia, IFM_ETHER | IFM_NONE, 0, 0);
2927	ifmedia_set(&sc->tulip_ifmedia, IFM_ETHER | IFM_NONE);
2928    } else if (sc->tulip_media == TULIP_MEDIA_UNKNOWN) {
2929	ifmedia_add(&sc->tulip_ifmedia, IFM_ETHER | IFM_AUTO, 0, 0);
2930	ifmedia_set(&sc->tulip_ifmedia, IFM_ETHER | IFM_AUTO);
2931    } else {
2932	ifmedia_set(&sc->tulip_ifmedia, tulip_media_to_ifmedia[sc->tulip_media]);
2933	sc->tulip_flags |= TULIP_PRINTMEDIA;
2934	tulip_linkup(sc, sc->tulip_media);
2935    }
2936}
2937
2938static int
2939tulip_ifmedia_change(
2940    struct ifnet * const ifp)
2941{
2942    tulip_softc_t * const sc = (tulip_softc_t *)ifp->if_softc;
2943
2944    sc->tulip_flags |= TULIP_NEEDRESET;
2945    sc->tulip_probe_state = TULIP_PROBE_INACTIVE;
2946    sc->tulip_media = TULIP_MEDIA_UNKNOWN;
2947    if (IFM_SUBTYPE(sc->tulip_ifmedia.ifm_media) != IFM_AUTO) {
2948	tulip_media_t media;
2949	for (media = TULIP_MEDIA_UNKNOWN; media < TULIP_MEDIA_MAX; media++) {
2950	    if (sc->tulip_mediums[media] != NULL
2951		&& sc->tulip_ifmedia.ifm_media == tulip_media_to_ifmedia[media]) {
2952		sc->tulip_flags |= TULIP_PRINTMEDIA;
2953		sc->tulip_flags &= ~TULIP_DIDNWAY;
2954		tulip_linkup(sc, media);
2955		return 0;
2956	    }
2957	}
2958    }
2959    sc->tulip_flags &= ~(TULIP_TXPROBE_ACTIVE|TULIP_WANTRXACT);
2960    tulip_reset(sc);
2961    tulip_init(sc);
2962    return 0;
2963}
2964
2965/*
2966 * Media status callback
2967 */
2968static void
2969tulip_ifmedia_status(
2970    struct ifnet * const ifp,
2971    struct ifmediareq *req)
2972{
2973    tulip_softc_t *sc = (tulip_softc_t *)ifp->if_softc;
2974
2975    if (sc->tulip_media == TULIP_MEDIA_UNKNOWN)
2976	return;
2977
2978    req->ifm_status = IFM_AVALID;
2979    if (sc->tulip_flags & TULIP_LINKUP)
2980	req->ifm_status |= IFM_ACTIVE;
2981
2982    req->ifm_active = tulip_media_to_ifmedia[sc->tulip_media];
2983}
2984
2985static void
2986tulip_addr_filter(
2987    tulip_softc_t * const sc)
2988{
2989    struct ifmultiaddr *ifma;
2990    u_char *addrp;
2991    int multicnt;
2992
2993    sc->tulip_flags &= ~(TULIP_WANTHASHPERFECT|TULIP_WANTHASHONLY|TULIP_ALLMULTI);
2994    sc->tulip_flags |= TULIP_WANTSETUP|TULIP_WANTTXSTART;
2995    sc->tulip_cmdmode &= ~TULIP_CMD_RXRUN;
2996    sc->tulip_intrmask &= ~TULIP_STS_RXSTOPPED;
2997#if defined(IFF_ALLMULTI)
2998    if (sc->tulip_if.if_flags & IFF_ALLMULTI)
2999	sc->tulip_flags |= TULIP_ALLMULTI ;
3000#endif
3001
3002    multicnt = 0;
3003    TAILQ_FOREACH(ifma, &sc->tulip_if.if_multiaddrs, ifma_link) {
3004
3005	    if (ifma->ifma_addr->sa_family == AF_LINK)
3006		multicnt++;
3007    }
3008
3009    sc->tulip_if.if_start = tulip_ifstart;	/* so the setup packet gets queued */
3010    if (multicnt > 14) {
3011	u_int32_t *sp = sc->tulip_setupdata;
3012	unsigned hash;
3013	/*
3014	 * Some early passes of the 21140 have broken implementations of
3015	 * hash-perfect mode.  When we get too many multicasts for perfect
3016	 * filtering with these chips, we need to switch into hash-only
3017	 * mode (this is better than all-multicast on network with lots
3018	 * of multicast traffic).
3019	 */
3020	if (sc->tulip_features & TULIP_HAVE_BROKEN_HASH)
3021	    sc->tulip_flags |= TULIP_WANTHASHONLY;
3022	else
3023	    sc->tulip_flags |= TULIP_WANTHASHPERFECT;
3024	/*
3025	 * If we have more than 14 multicasts, we have
3026	 * go into hash perfect mode (512 bit multicast
3027	 * hash and one perfect hardware).
3028	 */
3029	bzero(sc->tulip_setupdata, sizeof(sc->tulip_setupdata));
3030
3031	TAILQ_FOREACH(ifma, &sc->tulip_if.if_multiaddrs, ifma_link) {
3032
3033		if (ifma->ifma_addr->sa_family != AF_LINK)
3034			continue;
3035
3036		hash = tulip_mchash(LLADDR((struct sockaddr_dl *)ifma->ifma_addr));
3037#if BYTE_ORDER == BIG_ENDIAN
3038		sp[hash >> 4] |= bswap32(1 << (hash & 0xF));
3039#else
3040		sp[hash >> 4] |= 1 << (hash & 0xF);
3041#endif
3042	}
3043	/*
3044	 * No reason to use a hash if we are going to be
3045	 * receiving every multicast.
3046	 */
3047	if ((sc->tulip_flags & TULIP_ALLMULTI) == 0) {
3048	    hash = tulip_mchash(sc->tulip_if.if_broadcastaddr);
3049#if BYTE_ORDER == BIG_ENDIAN
3050	    sp[hash >> 4] |= bswap32(1 << (hash & 0xF));
3051#else
3052	    sp[hash >> 4] |= 1 << (hash & 0xF);
3053#endif
3054	    if (sc->tulip_flags & TULIP_WANTHASHONLY) {
3055		hash = tulip_mchash(sc->tulip_enaddr);
3056#if BYTE_ORDER == BIG_ENDIAN
3057		sp[hash >> 4] |= bswap32(1 << (hash & 0xF));
3058#else
3059		sp[hash >> 4] |= 1 << (hash & 0xF);
3060#endif
3061	    } else {
3062#if BYTE_ORDER == BIG_ENDIAN
3063		sp[39] = ((u_int16_t *) sc->tulip_enaddr)[0] << 16;
3064		sp[40] = ((u_int16_t *) sc->tulip_enaddr)[1] << 16;
3065		sp[41] = ((u_int16_t *) sc->tulip_enaddr)[2] << 16;
3066#else
3067		sp[39] = ((u_int16_t *) sc->tulip_enaddr)[0];
3068		sp[40] = ((u_int16_t *) sc->tulip_enaddr)[1];
3069		sp[41] = ((u_int16_t *) sc->tulip_enaddr)[2];
3070#endif
3071	    }
3072	}
3073    }
3074    if ((sc->tulip_flags & (TULIP_WANTHASHPERFECT|TULIP_WANTHASHONLY)) == 0) {
3075	u_int32_t *sp = sc->tulip_setupdata;
3076	int idx = 0;
3077	if ((sc->tulip_flags & TULIP_ALLMULTI) == 0) {
3078	    /*
3079	     * Else can get perfect filtering for 16 addresses.
3080	     */
3081	    TAILQ_FOREACH(ifma, &sc->tulip_if.if_multiaddrs, ifma_link) {
3082		    if (ifma->ifma_addr->sa_family != AF_LINK)
3083			    continue;
3084		    addrp = LLADDR((struct sockaddr_dl *)ifma->ifma_addr);
3085#if BYTE_ORDER == BIG_ENDIAN
3086		    *sp++ = ((u_int16_t *) addrp)[0] << 16;
3087		    *sp++ = ((u_int16_t *) addrp)[1] << 16;
3088		    *sp++ = ((u_int16_t *) addrp)[2] << 16;
3089#else
3090		    *sp++ = ((u_int16_t *) addrp)[0];
3091		    *sp++ = ((u_int16_t *) addrp)[1];
3092		    *sp++ = ((u_int16_t *) addrp)[2];
3093#endif
3094		    idx++;
3095	    }
3096	    /*
3097	     * Add the broadcast address.
3098	     */
3099	    idx++;
3100#if BYTE_ORDER == BIG_ENDIAN
3101	    *sp++ = 0xFFFF << 16;
3102	    *sp++ = 0xFFFF << 16;
3103	    *sp++ = 0xFFFF << 16;
3104#else
3105	    *sp++ = 0xFFFF;
3106	    *sp++ = 0xFFFF;
3107	    *sp++ = 0xFFFF;
3108#endif
3109	}
3110	/*
3111	 * Pad the rest with our hardware address
3112	 */
3113	for (; idx < 16; idx++) {
3114#if BYTE_ORDER == BIG_ENDIAN
3115	    *sp++ = ((u_int16_t *) sc->tulip_enaddr)[0] << 16;
3116	    *sp++ = ((u_int16_t *) sc->tulip_enaddr)[1] << 16;
3117	    *sp++ = ((u_int16_t *) sc->tulip_enaddr)[2] << 16;
3118#else
3119	    *sp++ = ((u_int16_t *) sc->tulip_enaddr)[0];
3120	    *sp++ = ((u_int16_t *) sc->tulip_enaddr)[1];
3121	    *sp++ = ((u_int16_t *) sc->tulip_enaddr)[2];
3122#endif
3123	}
3124    }
3125#if defined(IFF_ALLMULTI)
3126    if (sc->tulip_flags & TULIP_ALLMULTI)
3127	sc->tulip_if.if_flags |= IFF_ALLMULTI;
3128#endif
3129}
3130
3131static void
3132tulip_reset(
3133    tulip_softc_t * const sc)
3134{
3135    tulip_ringinfo_t *ri;
3136    tulip_desc_t *di;
3137    u_int32_t inreset = (sc->tulip_flags & TULIP_INRESET);
3138
3139    /*
3140     * Brilliant.  Simply brilliant.  When switching modes/speeds
3141     * on a 2114*, you need to set the appriopriate MII/PCS/SCL/PS
3142     * bits in CSR6 and then do a software reset to get the 21140
3143     * to properly reset its internal pathways to the right places.
3144     *   Grrrr.
3145     */
3146    if ((sc->tulip_flags & TULIP_DEVICEPROBE) == 0
3147	    && sc->tulip_boardsw->bd_media_preset != NULL)
3148	(*sc->tulip_boardsw->bd_media_preset)(sc);
3149
3150    TULIP_CSR_WRITE(sc, csr_busmode, TULIP_BUSMODE_SWRESET);
3151    DELAY(10);	/* Wait 10 microseconds (actually 50 PCI cycles but at
3152		   33MHz that comes to two microseconds but wait a
3153		   bit longer anyways) */
3154
3155    if (!inreset) {
3156	sc->tulip_flags |= TULIP_INRESET;
3157	sc->tulip_flags &= ~(TULIP_NEEDRESET|TULIP_RXBUFSLOW);
3158	sc->tulip_if.if_flags &= ~IFF_OACTIVE;
3159	sc->tulip_if.if_start = tulip_ifstart;
3160    }
3161
3162#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NOTX)
3163    TULIP_CSR_WRITE(sc, csr_txlist, sc->tulip_txdescmap->dm_segs[0].ds_addr);
3164#else
3165    TULIP_CSR_WRITE(sc, csr_txlist, TULIP_KVATOPHYS(sc, &sc->tulip_txinfo.ri_first[0]));
3166#endif
3167#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NORX)
3168    TULIP_CSR_WRITE(sc, csr_rxlist, sc->tulip_rxdescmap->dm_segs[0].ds_addr);
3169#else
3170    TULIP_CSR_WRITE(sc, csr_rxlist, TULIP_KVATOPHYS(sc, &sc->tulip_rxinfo.ri_first[0]));
3171#endif
3172    TULIP_CSR_WRITE(sc, csr_busmode,
3173		    (1 << (3 /*pci_max_burst_len*/ + 8))
3174		    |TULIP_BUSMODE_CACHE_ALIGN8
3175		    |TULIP_BUSMODE_READMULTIPLE
3176		    |(BYTE_ORDER != LITTLE_ENDIAN ?
3177		      TULIP_BUSMODE_DESC_BIGENDIAN : 0));
3178
3179    sc->tulip_txtimer = 0;
3180    sc->tulip_txq.ifq_maxlen = TULIP_TXDESCS;
3181    /*
3182     * Free all the mbufs that were on the transmit ring.
3183     */
3184    for (;;) {
3185#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NOTX)
3186	bus_dmamap_t map;
3187#endif
3188	struct mbuf *m;
3189	_IF_DEQUEUE(&sc->tulip_txq, m);
3190	if (m == NULL)
3191	    break;
3192#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NOTX)
3193	map = M_GETCTX(m, bus_dmamap_t);
3194	bus_dmamap_unload(sc->tulip_dmatag, map);
3195	sc->tulip_txmaps[sc->tulip_txmaps_free++] = map;
3196#endif
3197	m_freem(m);
3198    }
3199
3200    ri = &sc->tulip_txinfo;
3201    ri->ri_nextin = ri->ri_nextout = ri->ri_first;
3202    ri->ri_free = ri->ri_max;
3203    for (di = ri->ri_first; di < ri->ri_last; di++)
3204	di->d_status = 0;
3205#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NOTX)
3206    bus_dmamap_sync(sc->tulip_dmatag, sc->tulip_txdescmap,
3207		    0, sc->tulip_txdescmap->dm_mapsize,
3208		    BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE);
3209#endif
3210
3211    /*
3212     * We need to collect all the mbufs were on the
3213     * receive ring before we reinit it either to put
3214     * them back on or to know if we have to allocate
3215     * more.
3216     */
3217    ri = &sc->tulip_rxinfo;
3218    ri->ri_nextin = ri->ri_nextout = ri->ri_first;
3219    ri->ri_free = ri->ri_max;
3220    for (di = ri->ri_first; di < ri->ri_last; di++) {
3221	di->d_status = 0;
3222	di->d_length1 = 0; di->d_addr1 = 0;
3223	di->d_length2 = 0; di->d_addr2 = 0;
3224    }
3225#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NORX)
3226    bus_dmamap_sync(sc->tulip_dmatag, sc->tulip_rxdescmap,
3227		    0, sc->tulip_rxdescmap->dm_mapsize,
3228		    BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE);
3229#endif
3230    for (;;) {
3231#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NORX)
3232	bus_dmamap_t map;
3233#endif
3234	struct mbuf *m;
3235	_IF_DEQUEUE(&sc->tulip_rxq, m);
3236	if (m == NULL)
3237	    break;
3238#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NORX)
3239	map = M_GETCTX(m, bus_dmamap_t);
3240	bus_dmamap_unload(sc->tulip_dmatag, map);
3241	sc->tulip_rxmaps[sc->tulip_rxmaps_free++] = map;
3242#endif
3243	m_freem(m);
3244    }
3245
3246    /*
3247     * If tulip_reset is being called recurisvely, exit quickly knowing
3248     * that when the outer tulip_reset returns all the right stuff will
3249     * have happened.
3250     */
3251    if (inreset)
3252	return;
3253
3254    sc->tulip_intrmask |= TULIP_STS_NORMALINTR|TULIP_STS_RXINTR|TULIP_STS_TXINTR
3255	|TULIP_STS_ABNRMLINTR|TULIP_STS_SYSERROR|TULIP_STS_TXSTOPPED
3256	|TULIP_STS_TXUNDERFLOW|TULIP_STS_TXBABBLE
3257	|TULIP_STS_RXSTOPPED;
3258
3259    if ((sc->tulip_flags & TULIP_DEVICEPROBE) == 0)
3260	(*sc->tulip_boardsw->bd_media_select)(sc);
3261#if defined(TULIP_DEBUG)
3262    if ((sc->tulip_flags & TULIP_NEEDRESET) == TULIP_NEEDRESET)
3263	printf("%s: tulip_reset: additional reset needed?!?\n",
3264	       sc->tulip_xname);
3265#endif
3266    tulip_media_print(sc);
3267    if (sc->tulip_features & TULIP_HAVE_DUALSENSE)
3268	TULIP_CSR_WRITE(sc, csr_sia_status, TULIP_CSR_READ(sc, csr_sia_status));
3269
3270    sc->tulip_flags &= ~(TULIP_DOINGSETUP|TULIP_WANTSETUP|TULIP_INRESET
3271			 |TULIP_RXACT);
3272    tulip_addr_filter(sc);
3273}
3274
3275
3276static void
3277tulip_ifinit(
3278    void * sc)
3279{
3280	tulip_init((tulip_softc_t *)sc);
3281}
3282
3283static void
3284tulip_init(
3285    tulip_softc_t * const sc)
3286{
3287    if (sc->tulip_if.if_flags & IFF_UP) {
3288	if ((sc->tulip_if.if_flags & IFF_RUNNING) == 0) {
3289	    /* initialize the media */
3290	    tulip_reset(sc);
3291	}
3292	sc->tulip_if.if_flags |= IFF_RUNNING;
3293	if (sc->tulip_if.if_flags & IFF_PROMISC) {
3294	    sc->tulip_flags |= TULIP_PROMISC;
3295	    sc->tulip_cmdmode |= TULIP_CMD_PROMISCUOUS;
3296	    sc->tulip_intrmask |= TULIP_STS_TXINTR;
3297	} else {
3298	    sc->tulip_flags &= ~TULIP_PROMISC;
3299	    sc->tulip_cmdmode &= ~TULIP_CMD_PROMISCUOUS;
3300	    if (sc->tulip_flags & TULIP_ALLMULTI) {
3301		sc->tulip_cmdmode |= TULIP_CMD_ALLMULTI;
3302	    } else {
3303		sc->tulip_cmdmode &= ~TULIP_CMD_ALLMULTI;
3304	    }
3305	}
3306	sc->tulip_cmdmode |= TULIP_CMD_TXRUN;
3307	if ((sc->tulip_flags & (TULIP_TXPROBE_ACTIVE|TULIP_WANTSETUP)) == 0) {
3308	    tulip_rx_intr(sc);
3309	    sc->tulip_cmdmode |= TULIP_CMD_RXRUN;
3310	    sc->tulip_intrmask |= TULIP_STS_RXSTOPPED;
3311	} else {
3312	    sc->tulip_if.if_flags |= IFF_OACTIVE;
3313	    sc->tulip_cmdmode &= ~TULIP_CMD_RXRUN;
3314	    sc->tulip_intrmask &= ~TULIP_STS_RXSTOPPED;
3315	}
3316	TULIP_CSR_WRITE(sc, csr_intr, sc->tulip_intrmask);
3317	TULIP_CSR_WRITE(sc, csr_command, sc->tulip_cmdmode);
3318	if ((sc->tulip_flags & (TULIP_WANTSETUP|TULIP_TXPROBE_ACTIVE)) == TULIP_WANTSETUP)
3319	    tulip_txput_setup(sc);
3320    } else {
3321	sc->tulip_if.if_flags &= ~IFF_RUNNING;
3322	tulip_reset(sc);
3323    }
3324}
3325
3326static void
3327tulip_rx_intr(
3328    tulip_softc_t * const sc)
3329{
3330    TULIP_PERFSTART(rxintr)
3331    tulip_ringinfo_t * const ri = &sc->tulip_rxinfo;
3332    struct ifnet * const ifp = &sc->tulip_if;
3333    int fillok = 1;
3334#if defined(TULIP_DEBUG)
3335    int cnt = 0;
3336#endif
3337
3338    for (;;) {
3339	TULIP_PERFSTART(rxget)
3340	tulip_desc_t *eop = ri->ri_nextin;
3341	int total_len = 0, last_offset = 0;
3342	struct mbuf *ms = NULL, *me = NULL;
3343	int accept = 0;
3344#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NORX)
3345	bus_dmamap_t map;
3346	int error;
3347#endif
3348
3349	if (fillok && sc->tulip_rxq.ifq_len < TULIP_RXQ_TARGET)
3350	    goto queue_mbuf;
3351
3352#if defined(TULIP_DEBUG)
3353	if (cnt == ri->ri_max)
3354	    break;
3355#endif
3356	/*
3357	 * If the TULIP has no descriptors, there can't be any receive
3358	 * descriptors to process.
3359 	 */
3360	if (eop == ri->ri_nextout)
3361	    break;
3362
3363	/*
3364	 * 90% of the packets will fit in one descriptor.  So we optimize
3365	 * for that case.
3366	 */
3367	TULIP_RXDESC_POSTSYNC(sc, eop, sizeof(*eop));
3368	if ((((volatile tulip_desc_t *) eop)->d_status & (TULIP_DSTS_OWNER|TULIP_DSTS_RxFIRSTDESC|TULIP_DSTS_RxLASTDESC)) == (TULIP_DSTS_RxFIRSTDESC|TULIP_DSTS_RxLASTDESC)) {
3369	    _IF_DEQUEUE(&sc->tulip_rxq, ms);
3370	    me = ms;
3371	} else {
3372	    /*
3373	     * If still owned by the TULIP, don't touch it.
3374	     */
3375	    if (((volatile tulip_desc_t *) eop)->d_status & TULIP_DSTS_OWNER)
3376		break;
3377
3378	    /*
3379	     * It is possible (though improbable unless the BIG_PACKET support
3380	     * is enabled or MCLBYTES < 1518) for a received packet to cross
3381	     * more than one receive descriptor.
3382	     */
3383	    while ((((volatile tulip_desc_t *) eop)->d_status & TULIP_DSTS_RxLASTDESC) == 0) {
3384		if (++eop == ri->ri_last)
3385		    eop = ri->ri_first;
3386		TULIP_RXDESC_POSTSYNC(sc, eop, sizeof(*eop));
3387		if (eop == ri->ri_nextout || ((((volatile tulip_desc_t *) eop)->d_status & TULIP_DSTS_OWNER))) {
3388#if defined(TULIP_DEBUG)
3389		    sc->tulip_dbg.dbg_rxintrs++;
3390		    sc->tulip_dbg.dbg_rxpktsperintr[cnt]++;
3391#endif
3392		    TULIP_PERFEND(rxget);
3393		    TULIP_PERFEND(rxintr);
3394		    return;
3395		}
3396		total_len++;
3397	    }
3398
3399	    /*
3400	     * Dequeue the first buffer for the start of the packet.  Hopefully
3401	     * this will be the only one we need to dequeue.  However, if the
3402	     * packet consumed multiple descriptors, then we need to dequeue
3403	     * those buffers and chain to the starting mbuf.  All buffers but
3404	     * the last buffer have the same length so we can set that now.
3405	     * (we add to last_offset instead of multiplying since we normally
3406	     * won't go into the loop and thereby saving ourselves from
3407	     * doing a multiplication by 0 in the normal case).
3408	     */
3409	    _IF_DEQUEUE(&sc->tulip_rxq, ms);
3410	    for (me = ms; total_len > 0; total_len--) {
3411#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NORX)
3412		map = M_GETCTX(me, bus_dmamap_t);
3413		TULIP_RXMAP_POSTSYNC(sc, map);
3414		bus_dmamap_unload(sc->tulip_dmatag, map);
3415		sc->tulip_rxmaps[sc->tulip_rxmaps_free++] = map;
3416#if defined(DIAGNOSTIC)
3417		M_SETCTX(me, NULL);
3418#endif
3419#endif /* TULIP_BUS_DMA */
3420		me->m_len = TULIP_RX_BUFLEN;
3421		last_offset += TULIP_RX_BUFLEN;
3422		_IF_DEQUEUE(&sc->tulip_rxq, me->m_next);
3423		me = me->m_next;
3424	    }
3425	}
3426
3427	/*
3428	 *  Now get the size of received packet (minus the CRC).
3429	 */
3430	total_len = ((eop->d_status >> 16) & 0x7FFF) - 4;
3431	if ((sc->tulip_flags & TULIP_RXIGNORE) == 0
3432		&& ((eop->d_status & TULIP_DSTS_ERRSUM) == 0
3433#ifdef BIG_PACKET
3434		     || (total_len <= sc->tulip_if.if_mtu + sizeof(struct ether_header) &&
3435			 (eop->d_status & (TULIP_DSTS_RxBADLENGTH|TULIP_DSTS_RxRUNT|
3436					  TULIP_DSTS_RxCOLLSEEN|TULIP_DSTS_RxBADCRC|
3437					  TULIP_DSTS_RxOVERFLOW)) == 0)
3438#endif
3439		)) {
3440	    me->m_len = total_len - last_offset;
3441
3442#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NORX)
3443	    map = M_GETCTX(me, bus_dmamap_t);
3444	    bus_dmamap_sync(sc->tulip_dmatag, map, 0, me->m_len,
3445			    BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE);
3446	    bus_dmamap_unload(sc->tulip_dmatag, map);
3447	    sc->tulip_rxmaps[sc->tulip_rxmaps_free++] = map;
3448#if defined(DIAGNOSTIC)
3449	    M_SETCTX(me, NULL);
3450#endif
3451#endif /* TULIP_BUS_DMA */
3452
3453#ifndef __FreeBSD__
3454	    if (sc->tulip_if.if_bpf != NULL) {
3455		if (me == ms)
3456		    bpf_tap(&sc->tulip_if, mtod(ms, caddr_t), total_len);
3457		else
3458		    bpf_mtap(&sc->tulip_if, ms);
3459	    }
3460#endif
3461	    sc->tulip_flags |= TULIP_RXACT;
3462	    accept = 1;
3463	} else {
3464	    ifp->if_ierrors++;
3465	    if (eop->d_status & (TULIP_DSTS_RxBADLENGTH|TULIP_DSTS_RxOVERFLOW|TULIP_DSTS_RxWATCHDOG)) {
3466		sc->tulip_dot3stats.dot3StatsInternalMacReceiveErrors++;
3467	    } else {
3468#if defined(TULIP_VERBOSE)
3469		const char *error = NULL;
3470#endif
3471		if (eop->d_status & TULIP_DSTS_RxTOOLONG) {
3472		    sc->tulip_dot3stats.dot3StatsFrameTooLongs++;
3473#if defined(TULIP_VERBOSE)
3474		    error = "frame too long";
3475#endif
3476		}
3477		if (eop->d_status & TULIP_DSTS_RxBADCRC) {
3478		    if (eop->d_status & TULIP_DSTS_RxDRBBLBIT) {
3479			sc->tulip_dot3stats.dot3StatsAlignmentErrors++;
3480#if defined(TULIP_VERBOSE)
3481			error = "alignment error";
3482#endif
3483		    } else {
3484			sc->tulip_dot3stats.dot3StatsFCSErrors++;
3485#if defined(TULIP_VERBOSE)
3486			error = "bad crc";
3487#endif
3488		    }
3489		}
3490#if defined(TULIP_VERBOSE)
3491		if (error != NULL && (sc->tulip_flags & TULIP_NOMESSAGES) == 0) {
3492		    printf("%s: receive: %6D: %s\n",
3493			   sc->tulip_xname,
3494			   mtod(ms, u_char *) + 6, ":",
3495			   error);
3496		    sc->tulip_flags |= TULIP_NOMESSAGES;
3497		}
3498#endif
3499	    }
3500
3501#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NORX)
3502	    map = M_GETCTX(me, bus_dmamap_t);
3503	    bus_dmamap_unload(sc->tulip_dmatag, map);
3504	    sc->tulip_rxmaps[sc->tulip_rxmaps_free++] = map;
3505#if defined(DIAGNOSTIC)
3506	    M_SETCTX(me, NULL);
3507#endif
3508#endif /* TULIP_BUS_DMA */
3509	}
3510#if defined(TULIP_DEBUG)
3511	cnt++;
3512#endif
3513	ifp->if_ipackets++;
3514	if (++eop == ri->ri_last)
3515	    eop = ri->ri_first;
3516	ri->ri_nextin = eop;
3517      queue_mbuf:
3518	/*
3519	 * Either we are priming the TULIP with mbufs (m == NULL)
3520	 * or we are about to accept an mbuf for the upper layers
3521	 * so we need to allocate an mbuf to replace it.  If we
3522	 * can't replace it, send up it anyways.  This may cause
3523	 * us to drop packets in the future but that's better than
3524	 * being caught in livelock.
3525	 *
3526	 * Note that if this packet crossed multiple descriptors
3527	 * we don't even try to reallocate all the mbufs here.
3528	 * Instead we rely on the test of the beginning of
3529	 * the loop to refill for the extra consumed mbufs.
3530	 */
3531	if (accept || ms == NULL) {
3532	    struct mbuf *m0;
3533	    MGETHDR(m0, M_DONTWAIT, MT_DATA);
3534	    if (m0 != NULL) {
3535#if defined(TULIP_COPY_RXDATA)
3536		if (!accept || total_len >= (MHLEN - 2)) {
3537#endif
3538		    MCLGET(m0, M_DONTWAIT);
3539		    if ((m0->m_flags & M_EXT) == 0) {
3540			m_freem(m0);
3541			m0 = NULL;
3542		    }
3543#if defined(TULIP_COPY_RXDATA)
3544		}
3545#endif
3546	    }
3547	    if (accept
3548#if defined(TULIP_COPY_RXDATA)
3549		&& m0 != NULL
3550#endif
3551		) {
3552#if !defined(TULIP_COPY_RXDATA)
3553		ms->m_pkthdr.len = total_len;
3554		ms->m_pkthdr.rcvif = ifp;
3555		(*ifp->if_input)(ifp, ms);
3556#else
3557#ifdef BIG_PACKET
3558#error BIG_PACKET is incompatible with TULIP_COPY_RXDATA
3559#endif
3560		m0->m_data += 2;	/* align data after header */
3561		m_copydata(ms, 0, total_len, mtod(m0, caddr_t));
3562		m0->m_len = m0->m_pkthdr.len = total_len;
3563		m0->m_pkthdr.rcvif = ifp;
3564		(*ifp->if_input)(ifp, m0);
3565		m0 = ms;
3566#endif /* ! TULIP_COPY_RXDATA */
3567	    }
3568	    ms = m0;
3569	}
3570	if (ms == NULL) {
3571	    /*
3572	     * Couldn't allocate a new buffer.  Don't bother
3573	     * trying to replenish the receive queue.
3574	     */
3575	    fillok = 0;
3576	    sc->tulip_flags |= TULIP_RXBUFSLOW;
3577#if defined(TULIP_DEBUG)
3578	    sc->tulip_dbg.dbg_rxlowbufs++;
3579#endif
3580	    TULIP_PERFEND(rxget);
3581	    continue;
3582	}
3583	/*
3584	 * Now give the buffer(s) to the TULIP and save in our
3585	 * receive queue.
3586	 */
3587	do {
3588	    tulip_desc_t * const nextout = ri->ri_nextout;
3589#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NORX)
3590	    if (sc->tulip_rxmaps_free > 0) {
3591		map = sc->tulip_rxmaps[--sc->tulip_rxmaps_free];
3592	    } else {
3593		m_freem(ms);
3594		sc->tulip_flags |= TULIP_RXBUFSLOW;
3595#if defined(TULIP_DEBUG)
3596		sc->tulip_dbg.dbg_rxlowbufs++;
3597#endif
3598		break;
3599	    }
3600	    M_SETCTX(ms, map);
3601	    error = bus_dmamap_load(sc->tulip_dmatag, map, mtod(ms, void *),
3602				    TULIP_RX_BUFLEN, NULL, BUS_DMA_NOWAIT);
3603	    if (error) {
3604		printf("%s: unable to load rx map, "
3605		       "error = %d\n", sc->tulip_xname, error);
3606		panic("tulip_rx_intr");		/* XXX */
3607	    }
3608	    nextout->d_addr1 = map->dm_segs[0].ds_addr;
3609	    nextout->d_length1 = map->dm_segs[0].ds_len;
3610	    if (map->dm_nsegs == 2) {
3611		nextout->d_addr2 = map->dm_segs[1].ds_addr;
3612		nextout->d_length2 = map->dm_segs[1].ds_len;
3613	    } else {
3614		nextout->d_addr2 = 0;
3615		nextout->d_length2 = 0;
3616	    }
3617	    TULIP_RXDESC_POSTSYNC(sc, nextout, sizeof(*nextout));
3618#else /* TULIP_BUS_DMA */
3619	    nextout->d_addr1 = TULIP_KVATOPHYS(sc, mtod(ms, caddr_t));
3620	    nextout->d_length1 = TULIP_RX_BUFLEN;
3621#endif /* TULIP_BUS_DMA */
3622	    nextout->d_status = TULIP_DSTS_OWNER;
3623	    TULIP_RXDESC_POSTSYNC(sc, nextout, sizeof(u_int32_t));
3624	    if (++ri->ri_nextout == ri->ri_last)
3625		ri->ri_nextout = ri->ri_first;
3626	    me = ms->m_next;
3627	    ms->m_next = NULL;
3628	    _IF_ENQUEUE(&sc->tulip_rxq, ms);
3629	} while ((ms = me) != NULL);
3630
3631	if (sc->tulip_rxq.ifq_len >= TULIP_RXQ_TARGET)
3632	    sc->tulip_flags &= ~TULIP_RXBUFSLOW;
3633	TULIP_PERFEND(rxget);
3634    }
3635
3636#if defined(TULIP_DEBUG)
3637    sc->tulip_dbg.dbg_rxintrs++;
3638    sc->tulip_dbg.dbg_rxpktsperintr[cnt]++;
3639#endif
3640    TULIP_PERFEND(rxintr);
3641}
3642
3643static int
3644tulip_tx_intr(
3645    tulip_softc_t * const sc)
3646{
3647    TULIP_PERFSTART(txintr)
3648    tulip_ringinfo_t * const ri = &sc->tulip_txinfo;
3649    struct mbuf *m;
3650    int xmits = 0;
3651    int descs = 0;
3652
3653    while (ri->ri_free < ri->ri_max) {
3654	u_int32_t d_flag;
3655
3656	TULIP_TXDESC_POSTSYNC(sc, ri->ri_nextin, sizeof(*ri->ri_nextin));
3657	if (((volatile tulip_desc_t *) ri->ri_nextin)->d_status & TULIP_DSTS_OWNER)
3658	    break;
3659
3660	ri->ri_free++;
3661	descs++;
3662	d_flag = ri->ri_nextin->d_flag;
3663	if (d_flag & TULIP_DFLAG_TxLASTSEG) {
3664	    if (d_flag & TULIP_DFLAG_TxSETUPPKT) {
3665		/*
3666		 * We've just finished processing a setup packet.
3667		 * Mark that we finished it.  If there's not
3668		 * another pending, startup the TULIP receiver.
3669		 * Make sure we ack the RXSTOPPED so we won't get
3670		 * an abormal interrupt indication.
3671		 */
3672		TULIP_TXMAP_POSTSYNC(sc, sc->tulip_setupmap);
3673		sc->tulip_flags &= ~(TULIP_DOINGSETUP|TULIP_HASHONLY);
3674		if (ri->ri_nextin->d_flag & TULIP_DFLAG_TxINVRSFILT)
3675		    sc->tulip_flags |= TULIP_HASHONLY;
3676		if ((sc->tulip_flags & (TULIP_WANTSETUP|TULIP_TXPROBE_ACTIVE)) == 0) {
3677		    tulip_rx_intr(sc);
3678		    sc->tulip_cmdmode |= TULIP_CMD_RXRUN;
3679		    sc->tulip_intrmask |= TULIP_STS_RXSTOPPED;
3680		    TULIP_CSR_WRITE(sc, csr_status, TULIP_STS_RXSTOPPED);
3681		    TULIP_CSR_WRITE(sc, csr_intr, sc->tulip_intrmask);
3682		    TULIP_CSR_WRITE(sc, csr_command, sc->tulip_cmdmode);
3683		}
3684	    } else {
3685		const u_int32_t d_status = ri->ri_nextin->d_status;
3686		_IF_DEQUEUE(&sc->tulip_txq, m);
3687		if (m != NULL) {
3688#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NOTX)
3689		    bus_dmamap_t map = M_GETCTX(m, bus_dmamap_t);
3690		    TULIP_TXMAP_POSTSYNC(sc, map);
3691		    sc->tulip_txmaps[sc->tulip_txmaps_free++] = map;
3692#endif /* TULIP_BUS_DMA */
3693		    m_freem(m);
3694#if defined(TULIP_DEBUG)
3695		} else {
3696		    printf("%s: tx_intr: failed to dequeue mbuf?!?\n",
3697			    sc->tulip_xname);
3698#endif
3699		}
3700		if (sc->tulip_flags & TULIP_TXPROBE_ACTIVE) {
3701		    tulip_mediapoll_event_t event = TULIP_MEDIAPOLL_TXPROBE_OK;
3702		    if (d_status & (TULIP_DSTS_TxNOCARR|TULIP_DSTS_TxEXCCOLL)) {
3703#if defined(TULIP_DEBUG)
3704			if (d_status & TULIP_DSTS_TxNOCARR)
3705			    sc->tulip_dbg.dbg_txprobe_nocarr++;
3706			if (d_status & TULIP_DSTS_TxEXCCOLL)
3707			    sc->tulip_dbg.dbg_txprobe_exccoll++;
3708#endif
3709			event = TULIP_MEDIAPOLL_TXPROBE_FAILED;
3710		    }
3711		    (*sc->tulip_boardsw->bd_media_poll)(sc, event);
3712		    /*
3713		     * Escape from the loop before media poll has reset the TULIP!
3714		     */
3715		    break;
3716		} else {
3717		    xmits++;
3718		    if (d_status & TULIP_DSTS_ERRSUM) {
3719			sc->tulip_if.if_oerrors++;
3720			if (d_status & TULIP_DSTS_TxEXCCOLL)
3721			    sc->tulip_dot3stats.dot3StatsExcessiveCollisions++;
3722			if (d_status & TULIP_DSTS_TxLATECOLL)
3723			    sc->tulip_dot3stats.dot3StatsLateCollisions++;
3724			if (d_status & (TULIP_DSTS_TxNOCARR|TULIP_DSTS_TxCARRLOSS))
3725			    sc->tulip_dot3stats.dot3StatsCarrierSenseErrors++;
3726			if (d_status & (TULIP_DSTS_TxUNDERFLOW|TULIP_DSTS_TxBABBLE))
3727			    sc->tulip_dot3stats.dot3StatsInternalMacTransmitErrors++;
3728			if (d_status & TULIP_DSTS_TxUNDERFLOW)
3729			    sc->tulip_dot3stats.dot3StatsInternalTransmitUnderflows++;
3730			if (d_status & TULIP_DSTS_TxBABBLE)
3731			    sc->tulip_dot3stats.dot3StatsInternalTransmitBabbles++;
3732		    } else {
3733			u_int32_t collisions =
3734			    (d_status & TULIP_DSTS_TxCOLLMASK)
3735				>> TULIP_DSTS_V_TxCOLLCNT;
3736			sc->tulip_if.if_collisions += collisions;
3737			if (collisions == 1)
3738			    sc->tulip_dot3stats.dot3StatsSingleCollisionFrames++;
3739			else if (collisions > 1)
3740			    sc->tulip_dot3stats.dot3StatsMultipleCollisionFrames++;
3741			else if (d_status & TULIP_DSTS_TxDEFERRED)
3742			    sc->tulip_dot3stats.dot3StatsDeferredTransmissions++;
3743			/*
3744			 * SQE is only valid for 10baseT/BNC/AUI when not
3745			 * running in full-duplex.  In order to speed up the
3746			 * test, the corresponding bit in tulip_flags needs to
3747			 * set as well to get us to count SQE Test Errors.
3748			 */
3749			if (d_status & TULIP_DSTS_TxNOHRTBT & sc->tulip_flags)
3750			    sc->tulip_dot3stats.dot3StatsSQETestErrors++;
3751		    }
3752		}
3753	    }
3754	}
3755
3756	if (++ri->ri_nextin == ri->ri_last)
3757	    ri->ri_nextin = ri->ri_first;
3758
3759	if ((sc->tulip_flags & TULIP_TXPROBE_ACTIVE) == 0)
3760	    sc->tulip_if.if_flags &= ~IFF_OACTIVE;
3761    }
3762    /*
3763     * If nothing left to transmit, disable the timer.
3764     * Else if progress, reset the timer back to 2 ticks.
3765     */
3766    if (ri->ri_free == ri->ri_max || (sc->tulip_flags & TULIP_TXPROBE_ACTIVE))
3767	sc->tulip_txtimer = 0;
3768    else if (xmits > 0)
3769	sc->tulip_txtimer = TULIP_TXTIMER;
3770    sc->tulip_if.if_opackets += xmits;
3771    TULIP_PERFEND(txintr);
3772    return descs;
3773}
3774
3775static void
3776tulip_print_abnormal_interrupt(
3777    tulip_softc_t * const sc,
3778    u_int32_t csr)
3779{
3780    const char * const *msgp = tulip_status_bits;
3781    const char *sep;
3782    u_int32_t mask;
3783    const char thrsh[] = "72|128\0\0\0" "96|256\0\0\0" "128|512\0\0" "160|1024";
3784
3785    csr &= (1 << (sizeof(tulip_status_bits)/sizeof(tulip_status_bits[0]))) - 1;
3786    printf("%s: abnormal interrupt:", sc->tulip_xname);
3787    for (sep = " ", mask = 1; mask <= csr; mask <<= 1, msgp++) {
3788	if ((csr & mask) && *msgp != NULL) {
3789	    printf("%s%s", sep, *msgp);
3790	    if (mask == TULIP_STS_TXUNDERFLOW && (sc->tulip_flags & TULIP_NEWTXTHRESH)) {
3791		sc->tulip_flags &= ~TULIP_NEWTXTHRESH;
3792		if (sc->tulip_cmdmode & TULIP_CMD_STOREFWD) {
3793		    printf(" (switching to store-and-forward mode)");
3794		} else {
3795		    printf(" (raising TX threshold to %s)",
3796			   &thrsh[9 * ((sc->tulip_cmdmode & TULIP_CMD_THRESHOLDCTL) >> 14)]);
3797		}
3798	    }
3799	    sep = ", ";
3800	}
3801    }
3802    printf("\n");
3803}
3804
3805static void
3806tulip_intr_handler(
3807    tulip_softc_t * const sc,
3808    int *progress_p)
3809{
3810    TULIP_PERFSTART(intr)
3811    u_int32_t csr;
3812
3813    while ((csr = TULIP_CSR_READ(sc, csr_status)) & sc->tulip_intrmask) {
3814	*progress_p = 1;
3815	TULIP_CSR_WRITE(sc, csr_status, csr);
3816
3817	if (csr & TULIP_STS_SYSERROR) {
3818	    sc->tulip_last_system_error = (csr & TULIP_STS_ERRORMASK) >> TULIP_STS_ERR_SHIFT;
3819	    if (sc->tulip_flags & TULIP_NOMESSAGES) {
3820		sc->tulip_flags |= TULIP_SYSTEMERROR;
3821	    } else {
3822		printf("%s: system error: %s\n",
3823		       sc->tulip_xname,
3824		       tulip_system_errors[sc->tulip_last_system_error]);
3825	    }
3826	    sc->tulip_flags |= TULIP_NEEDRESET;
3827	    sc->tulip_system_errors++;
3828	    break;
3829	}
3830	if (csr & (TULIP_STS_LINKPASS|TULIP_STS_LINKFAIL) & sc->tulip_intrmask) {
3831#if defined(TULIP_DEBUG)
3832	    sc->tulip_dbg.dbg_link_intrs++;
3833#endif
3834	    if (sc->tulip_boardsw->bd_media_poll != NULL) {
3835		(*sc->tulip_boardsw->bd_media_poll)(sc, csr & TULIP_STS_LINKFAIL
3836						    ? TULIP_MEDIAPOLL_LINKFAIL
3837						    : TULIP_MEDIAPOLL_LINKPASS);
3838		csr &= ~TULIP_STS_ABNRMLINTR;
3839	    }
3840	    tulip_media_print(sc);
3841	}
3842	if (csr & (TULIP_STS_RXINTR|TULIP_STS_RXNOBUF)) {
3843	    u_int32_t misses = TULIP_CSR_READ(sc, csr_missed_frames);
3844	    if (csr & TULIP_STS_RXNOBUF)
3845		sc->tulip_dot3stats.dot3StatsMissedFrames += misses & 0xFFFF;
3846	    /*
3847	     * Pass 2.[012] of the 21140A-A[CDE] may hang and/or corrupt data
3848	     * on receive overflows.
3849	     */
3850	    if ((misses & 0x0FFE0000) && (sc->tulip_features & TULIP_HAVE_RXBADOVRFLW)) {
3851		sc->tulip_dot3stats.dot3StatsInternalMacReceiveErrors++;
3852		/*
3853		 * Stop the receiver process and spin until it's stopped.
3854		 * Tell rx_intr to drop the packets it dequeues.
3855		 */
3856		TULIP_CSR_WRITE(sc, csr_command, sc->tulip_cmdmode & ~TULIP_CMD_RXRUN);
3857		while ((TULIP_CSR_READ(sc, csr_status) & TULIP_STS_RXSTOPPED) == 0)
3858		    ;
3859		TULIP_CSR_WRITE(sc, csr_status, TULIP_STS_RXSTOPPED);
3860		sc->tulip_flags |= TULIP_RXIGNORE;
3861	    }
3862	    tulip_rx_intr(sc);
3863	    if (sc->tulip_flags & TULIP_RXIGNORE) {
3864		/*
3865		 * Restart the receiver.
3866		 */
3867		sc->tulip_flags &= ~TULIP_RXIGNORE;
3868		TULIP_CSR_WRITE(sc, csr_command, sc->tulip_cmdmode);
3869	    }
3870	}
3871	if (csr & TULIP_STS_ABNRMLINTR) {
3872	    u_int32_t tmp = csr & sc->tulip_intrmask
3873		& ~(TULIP_STS_NORMALINTR|TULIP_STS_ABNRMLINTR);
3874	    if (csr & TULIP_STS_TXUNDERFLOW) {
3875		if ((sc->tulip_cmdmode & TULIP_CMD_THRESHOLDCTL) != TULIP_CMD_THRSHLD160) {
3876		    sc->tulip_cmdmode += TULIP_CMD_THRSHLD96;
3877		    sc->tulip_flags |= TULIP_NEWTXTHRESH;
3878		} else if (sc->tulip_features & TULIP_HAVE_STOREFWD) {
3879		    sc->tulip_cmdmode |= TULIP_CMD_STOREFWD;
3880		    sc->tulip_flags |= TULIP_NEWTXTHRESH;
3881		}
3882	    }
3883	    if (sc->tulip_flags & TULIP_NOMESSAGES) {
3884		sc->tulip_statusbits |= tmp;
3885	    } else {
3886		tulip_print_abnormal_interrupt(sc, tmp);
3887		sc->tulip_flags |= TULIP_NOMESSAGES;
3888	    }
3889	    TULIP_CSR_WRITE(sc, csr_command, sc->tulip_cmdmode);
3890	}
3891	if (sc->tulip_flags & (TULIP_WANTTXSTART|TULIP_TXPROBE_ACTIVE|TULIP_DOINGSETUP|TULIP_PROMISC)) {
3892	    tulip_tx_intr(sc);
3893	    if ((sc->tulip_flags & TULIP_TXPROBE_ACTIVE) == 0)
3894		tulip_ifstart(&sc->tulip_if);
3895	}
3896    }
3897    if (sc->tulip_flags & TULIP_NEEDRESET) {
3898	tulip_reset(sc);
3899	tulip_init(sc);
3900    }
3901    TULIP_PERFEND(intr);
3902}
3903
3904#if defined(TULIP_USE_SOFTINTR)
3905/*
3906 * This is an experimental idea to alleviate problems due to interrupt
3907 * livelock.  What is interrupt livelock?  It's when you spend all your
3908 * time servicing device interrupts and never drop below device ipl
3909 * to do "useful" work.
3910 *
3911 * So what we do here is see if the device needs service and if so,
3912 * disable interrupts (dismiss the interrupt), place it in a list of devices
3913 * needing service, and issue a network software interrupt.
3914 *
3915 * When our network software interrupt routine gets called, we simply
3916 * walk done the list of devices that we have created and deal with them
3917 * at splnet/splsoftnet.
3918 *
3919 */
3920static void
3921tulip_hardintr_handler(
3922    tulip_softc_t * const sc,
3923    int *progress_p)
3924{
3925    if (TULIP_CSR_READ(sc, csr_status) & (TULIP_STS_NORMALINTR|TULIP_STS_ABNRMLINTR) == 0)
3926	return;
3927    *progress_p = 1;
3928    /*
3929     * disable interrupts
3930     */
3931    TULIP_CSR_WRITE(sc, csr_intr, 0);
3932    /*
3933     * mark it as needing a software interrupt
3934     */
3935    tulip_softintr_mask |= (1U << sc->tulip_unit);
3936}
3937
3938static void
3939tulip_softintr(
3940    void)
3941{
3942    u_int32_t softintr_mask, mask;
3943    int progress = 0;
3944    int unit;
3945    int s;
3946
3947    /*
3948     * Copy mask to local copy and reset global one to 0.
3949     */
3950    s = splimp();
3951    softintr_mask = tulip_softintr_mask;
3952    tulip_softintr_mask = 0;
3953    splx(s);
3954
3955    /*
3956     * Optimize for the single unit case.
3957     */
3958    if (tulip_softintr_max_unit == 0) {
3959	if (softintr_mask & 1) {
3960	    tulip_softc_t * const sc = tulips[0];
3961	    /*
3962	     * Handle the "interrupt" and then reenable interrupts
3963	     */
3964	    softintr_mask = 0;
3965	    tulip_intr_handler(sc, &progress);
3966	    TULIP_CSR_WRITE(sc, csr_intr, sc->tulip_intrmask);
3967	}
3968	return;
3969    }
3970
3971    /*
3972     * Handle all "queued" interrupts in a round robin fashion.
3973     * This is done so as not to favor a particular interface.
3974     */
3975    unit = tulip_softintr_last_unit;
3976    mask = (1U << unit);
3977    while (softintr_mask != 0) {
3978	if (tulip_softintr_max_unit == unit) {
3979	    unit  = 0; mask   = 1;
3980	} else {
3981	    unit += 1; mask <<= 1;
3982	}
3983	if (softintr_mask & mask) {
3984	    tulip_softc_t * const sc = tulips[unit];
3985	    /*
3986	     * Handle the "interrupt" and then reenable interrupts
3987	     */
3988	    softintr_mask ^= mask;
3989	    tulip_intr_handler(sc, &progress);
3990	    TULIP_CSR_WRITE(sc, csr_intr, sc->tulip_intrmask);
3991	}
3992    }
3993
3994    /*
3995     * Save where we ending up.
3996     */
3997    tulip_softintr_last_unit = unit;
3998}
3999#endif	/* TULIP_USE_SOFTINTR */
4000
4001static void
4002tulip_intr_shared(
4003    void *arg)
4004{
4005    tulip_softc_t * sc = arg;
4006    int progress = 0;
4007
4008    for (; sc != NULL; sc = sc->tulip_slaves) {
4009#if defined(TULIP_DEBUG)
4010	sc->tulip_dbg.dbg_intrs++;
4011#endif
4012#if defined(TULIP_USE_SOFTINTR)
4013	tulip_hardintr_handler(sc, &progress);
4014#else
4015	tulip_intr_handler(sc, &progress);
4016#endif
4017    }
4018#if defined(TULIP_USE_SOFTINTR)
4019    if (progress)
4020	schednetisr(NETISR_DE);
4021#endif
4022}
4023
4024static void
4025tulip_intr_normal(
4026    void *arg)
4027{
4028    tulip_softc_t * sc = (tulip_softc_t *) arg;
4029    int progress = 0;
4030
4031#if defined(TULIP_DEBUG)
4032    sc->tulip_dbg.dbg_intrs++;
4033#endif
4034#if defined(TULIP_USE_SOFTINTR)
4035    tulip_hardintr_handler(sc, &progress);
4036    if (progress)
4037	schednetisr(NETISR_DE);
4038#else
4039    tulip_intr_handler(sc, &progress);
4040#endif
4041}
4042
4043static struct mbuf *
4044tulip_mbuf_compress(
4045    struct mbuf *m)
4046{
4047    struct mbuf *m0;
4048#if MCLBYTES >= ETHERMTU + 18 && !defined(BIG_PACKET)
4049    MGETHDR(m0, M_DONTWAIT, MT_DATA);
4050    if (m0 != NULL) {
4051	if (m->m_pkthdr.len > MHLEN) {
4052	    MCLGET(m0, M_DONTWAIT);
4053	    if ((m0->m_flags & M_EXT) == 0) {
4054		m_freem(m);
4055		m_freem(m0);
4056		return NULL;
4057	    }
4058	}
4059	m_copydata(m, 0, m->m_pkthdr.len, mtod(m0, caddr_t));
4060	m0->m_pkthdr.len = m0->m_len = m->m_pkthdr.len;
4061    }
4062#else
4063    int mlen = MHLEN;
4064    int len = m->m_pkthdr.len;
4065    struct mbuf **mp = &m0;
4066
4067    while (len > 0) {
4068	if (mlen == MHLEN) {
4069	    MGETHDR(*mp, M_DONTWAIT, MT_DATA);
4070	} else {
4071	    MGET(*mp, M_DONTWAIT, MT_DATA);
4072	}
4073	if (*mp == NULL) {
4074	    m_freem(m0);
4075	    m0 = NULL;
4076	    break;
4077	}
4078	if (len > MLEN) {
4079	    MCLGET(*mp, M_DONTWAIT);
4080	    if (((*mp)->m_flags & M_EXT) == 0) {
4081		m_freem(m0);
4082		m0 = NULL;
4083		break;
4084	    }
4085	    (*mp)->m_len = len <= MCLBYTES ? len : MCLBYTES;
4086	} else {
4087	    (*mp)->m_len = len <= mlen ? len : mlen;
4088	}
4089	m_copydata(m, m->m_pkthdr.len - len,
4090		   (*mp)->m_len, mtod((*mp), caddr_t));
4091	len -= (*mp)->m_len;
4092	mp = &(*mp)->m_next;
4093	mlen = MLEN;
4094    }
4095#endif
4096    m_freem(m);
4097    return m0;
4098}
4099
4100static struct mbuf *
4101tulip_txput(
4102    tulip_softc_t * const sc,
4103    struct mbuf *m)
4104{
4105    TULIP_PERFSTART(txput)
4106    tulip_ringinfo_t * const ri = &sc->tulip_txinfo;
4107    tulip_desc_t *eop, *nextout;
4108    int segcnt, free;
4109    u_int32_t d_status;
4110#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NOTX)
4111    bus_dmamap_t map;
4112    int error;
4113#else
4114    struct mbuf *m0;
4115#endif
4116
4117#if defined(TULIP_DEBUG)
4118    if ((sc->tulip_cmdmode & TULIP_CMD_TXRUN) == 0) {
4119	printf("%s: txput%s: tx not running\n",
4120	       sc->tulip_xname,
4121	       (sc->tulip_flags & TULIP_TXPROBE_ACTIVE) ? "(probe)" : "");
4122	sc->tulip_flags |= TULIP_WANTTXSTART;
4123	sc->tulip_dbg.dbg_txput_finishes[0]++;
4124	goto finish;
4125    }
4126#endif
4127
4128    /*
4129     * Now we try to fill in our transmit descriptors.  This is
4130     * a bit reminiscent of going on the Ark two by two
4131     * since each descriptor for the TULIP can describe
4132     * two buffers.  So we advance through packet filling
4133     * each of the two entries at a time to to fill each
4134     * descriptor.  Clear the first and last segment bits
4135     * in each descriptor (actually just clear everything
4136     * but the end-of-ring or chain bits) to make sure
4137     * we don't get messed up by previously sent packets.
4138     *
4139     * We may fail to put the entire packet on the ring if
4140     * there is either not enough ring entries free or if the
4141     * packet has more than MAX_TXSEG segments.  In the former
4142     * case we will just wait for the ring to empty.  In the
4143     * latter case we have to recopy.
4144     */
4145#if !defined(TULIP_BUS_DMA) || defined(TULIP_BUS_DMA_NOTX)
4146  again:
4147    m0 = m;
4148#endif
4149    d_status = 0;
4150    eop = nextout = ri->ri_nextout;
4151    segcnt = 0;
4152    free = ri->ri_free;
4153
4154#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NOTX)
4155    /*
4156     * Reclaim some dma maps from if we are out.
4157     */
4158    if (sc->tulip_txmaps_free == 0) {
4159#if defined(TULIP_DEBUG)
4160	sc->tulip_dbg.dbg_no_txmaps++;
4161#endif
4162	free += tulip_tx_intr(sc);
4163    }
4164    if (sc->tulip_txmaps_free > 0) {
4165	map = sc->tulip_txmaps[sc->tulip_txmaps_free-1];
4166    } else {
4167	sc->tulip_flags |= TULIP_WANTTXSTART;
4168#if defined(TULIP_DEBUG)
4169	sc->tulip_dbg.dbg_txput_finishes[1]++;
4170#endif
4171	goto finish;
4172    }
4173    error = bus_dmamap_load_mbuf(sc->tulip_dmatag, map, m, BUS_DMA_NOWAIT);
4174    if (error != 0) {
4175	if (error == EFBIG) {
4176	    /*
4177	     * The packet exceeds the number of transmit buffer
4178	     * entries that we can use for one packet, so we have
4179	     * to recopy it into one mbuf and then try again.
4180	     */
4181	    m = tulip_mbuf_compress(m);
4182	    if (m == NULL) {
4183#if defined(TULIP_DEBUG)
4184		sc->tulip_dbg.dbg_txput_finishes[2]++;
4185#endif
4186		goto finish;
4187	    }
4188	    error = bus_dmamap_load_mbuf(sc->tulip_dmatag, map, m, BUS_DMA_NOWAIT);
4189	}
4190	if (error != 0) {
4191	    printf("%s: unable to load tx map, "
4192		   "error = %d\n", sc->tulip_xname, error);
4193#if defined(TULIP_DEBUG)
4194	    sc->tulip_dbg.dbg_txput_finishes[3]++;
4195#endif
4196	    goto finish;
4197	}
4198    }
4199    if ((free -= (map->dm_nsegs + 1) / 2) <= 0
4200	    /*
4201	     * See if there's any unclaimed space in the transmit ring.
4202	     */
4203	    && (free += tulip_tx_intr(sc)) <= 0) {
4204	/*
4205	 * There's no more room but since nothing
4206	 * has been committed at this point, just
4207	 * show output is active, put back the
4208	 * mbuf and return.
4209	 */
4210	sc->tulip_flags |= TULIP_WANTTXSTART;
4211#if defined(TULIP_DEBUG)
4212	sc->tulip_dbg.dbg_txput_finishes[4]++;
4213#endif
4214	bus_dmamap_unload(sc->tulip_dmatag, map);
4215	goto finish;
4216    }
4217    for (; map->dm_nsegs - segcnt > 1; segcnt += 2) {
4218	eop = nextout;
4219	eop->d_flag   &= TULIP_DFLAG_ENDRING|TULIP_DFLAG_CHAIN;
4220	eop->d_status  = d_status;
4221	eop->d_addr1   = map->dm_segs[segcnt].ds_addr;
4222	eop->d_length1 = map->dm_segs[segcnt].ds_len;
4223	eop->d_addr2   = map->dm_segs[segcnt+1].ds_addr;
4224	eop->d_length2 = map->dm_segs[segcnt+1].ds_len;
4225	d_status = TULIP_DSTS_OWNER;
4226	if (++nextout == ri->ri_last)
4227	    nextout = ri->ri_first;
4228    }
4229    if (segcnt < map->dm_nsegs) {
4230	eop = nextout;
4231	eop->d_flag   &= TULIP_DFLAG_ENDRING|TULIP_DFLAG_CHAIN;
4232	eop->d_status  = d_status;
4233	eop->d_addr1   = map->dm_segs[segcnt].ds_addr;
4234	eop->d_length1 = map->dm_segs[segcnt].ds_len;
4235	eop->d_addr2   = 0;
4236	eop->d_length2 = 0;
4237	if (++nextout == ri->ri_last)
4238	    nextout = ri->ri_first;
4239    }
4240    TULIP_TXMAP_PRESYNC(sc, map);
4241    M_SETCTX(m, map);
4242    map = NULL;
4243    --sc->tulip_txmaps_free;		/* commit to using the dmamap */
4244
4245#else /* !TULIP_BUS_DMA */
4246
4247    do {
4248	int len = m0->m_len;
4249	caddr_t addr = mtod(m0, caddr_t);
4250	unsigned clsize = PAGE_SIZE - (((uintptr_t) addr) & (PAGE_SIZE-1));
4251
4252	while (len > 0) {
4253	    unsigned slen = min(len, clsize);
4254#ifdef BIG_PACKET
4255	    int partial = 0;
4256	    if (slen >= 2048)
4257		slen = 2040, partial = 1;
4258#endif
4259	    segcnt++;
4260	    if (segcnt > TULIP_MAX_TXSEG) {
4261		/*
4262		 * The packet exceeds the number of transmit buffer
4263		 * entries that we can use for one packet, so we have
4264		 * recopy it into one mbuf and then try again.
4265		 */
4266		m = tulip_mbuf_compress(m);
4267		if (m == NULL)
4268		    goto finish;
4269		goto again;
4270	    }
4271	    if (segcnt & 1) {
4272		if (--free == 0) {
4273		    /*
4274		     * See if there's any unclaimed space in the
4275		     * transmit ring.
4276		     */
4277		    if ((free += tulip_tx_intr(sc)) == 0) {
4278			/*
4279			 * There's no more room but since nothing
4280			 * has been committed at this point, just
4281			 * show output is active, put back the
4282			 * mbuf and return.
4283			 */
4284			sc->tulip_flags |= TULIP_WANTTXSTART;
4285#if defined(TULIP_DEBUG)
4286			sc->tulip_dbg.dbg_txput_finishes[1]++;
4287#endif
4288			goto finish;
4289		    }
4290		}
4291		eop = nextout;
4292		if (++nextout == ri->ri_last)
4293		    nextout = ri->ri_first;
4294		eop->d_flag &= TULIP_DFLAG_ENDRING|TULIP_DFLAG_CHAIN;
4295		eop->d_status = d_status;
4296		eop->d_addr1 = TULIP_KVATOPHYS(sc, addr);
4297		eop->d_length1 = slen;
4298	    } else {
4299		/*
4300		 *  Fill in second half of descriptor
4301		 */
4302		eop->d_addr2 = TULIP_KVATOPHYS(sc, addr);
4303		eop->d_length2 = slen;
4304	    }
4305	    d_status = TULIP_DSTS_OWNER;
4306	    len -= slen;
4307	    addr += slen;
4308#ifdef BIG_PACKET
4309	    if (partial)
4310		continue;
4311#endif
4312	    clsize = PAGE_SIZE;
4313	}
4314    } while ((m0 = m0->m_next) != NULL);
4315#endif /* TULIP_BUS_DMA */
4316
4317    /*
4318     * bounce a copy to the bpf listener, if any.
4319     */
4320    BPF_MTAP(&sc->tulip_if, m);
4321
4322    /*
4323     * The descriptors have been filled in.  Now get ready
4324     * to transmit.
4325     */
4326    _IF_ENQUEUE(&sc->tulip_txq, m);
4327    m = NULL;
4328
4329    /*
4330     * Make sure the next descriptor after this packet is owned
4331     * by us since it may have been set up above if we ran out
4332     * of room in the ring.
4333     */
4334    nextout->d_status = 0;
4335    TULIP_TXDESC_PRESYNC(sc, nextout, sizeof(u_int32_t));
4336
4337#if !defined(TULIP_BUS_DMA) || defined(TULIP_BUS_DMA_NOTX)
4338    /*
4339     * If we only used the first segment of the last descriptor,
4340     * make sure the second segment will not be used.
4341     */
4342    if (segcnt & 1) {
4343	eop->d_addr2 = 0;
4344	eop->d_length2 = 0;
4345    }
4346#endif /* TULIP_BUS_DMA */
4347
4348    /*
4349     * Mark the last and first segments, indicate we want a transmit
4350     * complete interrupt, and tell it to transmit!
4351     */
4352    eop->d_flag |= TULIP_DFLAG_TxLASTSEG|TULIP_DFLAG_TxWANTINTR;
4353
4354    /*
4355     * Note that ri->ri_nextout is still the start of the packet
4356     * and until we set the OWNER bit, we can still back out of
4357     * everything we have done.
4358     */
4359    ri->ri_nextout->d_flag |= TULIP_DFLAG_TxFIRSTSEG;
4360#if defined(TULIP_BUS_MAP) && !defined(TULIP_BUS_DMA_NOTX)
4361    if (eop < ri->ri_nextout) {
4362	TULIP_TXDESC_PRESYNC(sc, ri->ri_nextout,
4363			     (caddr_t) ri->ri_last - (caddr_t) ri->ri_nextout);
4364	TULIP_TXDESC_PRESYNC(sc, ri->ri_first,
4365			     (caddr_t) (eop + 1) - (caddr_t) ri->ri_first);
4366    } else {
4367	TULIP_TXDESC_PRESYNC(sc, ri->ri_nextout,
4368			     (caddr_t) (eop + 1) - (caddr_t) ri->ri_nextout);
4369    }
4370#endif
4371    ri->ri_nextout->d_status = TULIP_DSTS_OWNER;
4372    TULIP_TXDESC_PRESYNC(sc, ri->ri_nextout, sizeof(u_int32_t));
4373
4374    /*
4375     * This advances the ring for us.
4376     */
4377    ri->ri_nextout = nextout;
4378    ri->ri_free = free;
4379
4380    TULIP_PERFEND(txput);
4381
4382    if (sc->tulip_flags & TULIP_TXPROBE_ACTIVE) {
4383	TULIP_CSR_WRITE(sc, csr_txpoll, 1);
4384	sc->tulip_if.if_flags |= IFF_OACTIVE;
4385	sc->tulip_if.if_start = tulip_ifstart;
4386	TULIP_PERFEND(txput);
4387	return NULL;
4388    }
4389
4390    /*
4391     * switch back to the single queueing ifstart.
4392     */
4393    sc->tulip_flags &= ~TULIP_WANTTXSTART;
4394    if (sc->tulip_txtimer == 0)
4395	sc->tulip_txtimer = TULIP_TXTIMER;
4396#if defined(TULIP_DEBUG)
4397    sc->tulip_dbg.dbg_txput_finishes[5]++;
4398#endif
4399
4400    /*
4401     * If we want a txstart, there must be not enough space in the
4402     * transmit ring.  So we want to enable transmit done interrupts
4403     * so we can immediately reclaim some space.  When the transmit
4404     * interrupt is posted, the interrupt handler will call tx_intr
4405     * to reclaim space and then txstart (since WANTTXSTART is set).
4406     * txstart will move the packet into the transmit ring and clear
4407     * WANTTXSTART thereby causing TXINTR to be cleared.
4408     */
4409  finish:
4410#if defined(TULIP_DEBUG)
4411    sc->tulip_dbg.dbg_txput_finishes[6]++;
4412#endif
4413    if (sc->tulip_flags & (TULIP_WANTTXSTART|TULIP_DOINGSETUP)) {
4414	sc->tulip_if.if_flags |= IFF_OACTIVE;
4415	sc->tulip_if.if_start = tulip_ifstart;
4416	if ((sc->tulip_intrmask & TULIP_STS_TXINTR) == 0) {
4417	    sc->tulip_intrmask |= TULIP_STS_TXINTR;
4418	    TULIP_CSR_WRITE(sc, csr_intr, sc->tulip_intrmask);
4419	}
4420    } else if ((sc->tulip_flags & TULIP_PROMISC) == 0) {
4421	if (sc->tulip_intrmask & TULIP_STS_TXINTR) {
4422	    sc->tulip_intrmask &= ~TULIP_STS_TXINTR;
4423	    TULIP_CSR_WRITE(sc, csr_intr, sc->tulip_intrmask);
4424	}
4425    }
4426    TULIP_CSR_WRITE(sc, csr_txpoll, 1);
4427    TULIP_PERFEND(txput);
4428    return m;
4429}
4430
4431static void
4432tulip_txput_setup(
4433    tulip_softc_t * const sc)
4434{
4435    tulip_ringinfo_t * const ri = &sc->tulip_txinfo;
4436    tulip_desc_t *nextout;
4437
4438    /*
4439     * We will transmit, at most, one setup packet per call to ifstart.
4440     */
4441
4442#if defined(TULIP_DEBUG)
4443    if ((sc->tulip_cmdmode & TULIP_CMD_TXRUN) == 0) {
4444	printf("%s: txput_setup: tx not running\n",
4445	       sc->tulip_xname);
4446	sc->tulip_flags |= TULIP_WANTTXSTART;
4447	sc->tulip_if.if_start = tulip_ifstart;
4448	return;
4449    }
4450#endif
4451    /*
4452     * Try to reclaim some free descriptors..
4453     */
4454    if (ri->ri_free < 2)
4455	tulip_tx_intr(sc);
4456    if ((sc->tulip_flags & TULIP_DOINGSETUP) || ri->ri_free == 1) {
4457	sc->tulip_flags |= TULIP_WANTTXSTART;
4458	sc->tulip_if.if_start = tulip_ifstart;
4459	return;
4460    }
4461    bcopy(sc->tulip_setupdata, sc->tulip_setupbuf,
4462	  sizeof(sc->tulip_setupbuf));
4463    /*
4464     * Clear WANTSETUP and set DOINGSETUP.  Set know that WANTSETUP is
4465     * set and DOINGSETUP is clear doing an XOR of the two will DTRT.
4466     */
4467    sc->tulip_flags ^= TULIP_WANTSETUP|TULIP_DOINGSETUP;
4468    ri->ri_free--;
4469    nextout = ri->ri_nextout;
4470    nextout->d_flag &= TULIP_DFLAG_ENDRING|TULIP_DFLAG_CHAIN;
4471    nextout->d_flag |= TULIP_DFLAG_TxFIRSTSEG|TULIP_DFLAG_TxLASTSEG
4472	|TULIP_DFLAG_TxSETUPPKT|TULIP_DFLAG_TxWANTINTR;
4473    if (sc->tulip_flags & TULIP_WANTHASHPERFECT)
4474	nextout->d_flag |= TULIP_DFLAG_TxHASHFILT;
4475    else if (sc->tulip_flags & TULIP_WANTHASHONLY)
4476	nextout->d_flag |= TULIP_DFLAG_TxHASHFILT|TULIP_DFLAG_TxINVRSFILT;
4477
4478    nextout->d_length2 = 0;
4479    nextout->d_addr2 = 0;
4480#if defined(TULIP_BUS_DMA) && !defined(TULIP_BUS_DMA_NOTX)
4481    nextout->d_length1 = sc->tulip_setupmap->dm_segs[0].ds_len;
4482    nextout->d_addr1 = sc->tulip_setupmap->dm_segs[0].ds_addr;
4483    if (sc->tulip_setupmap->dm_nsegs == 2) {
4484	nextout->d_length2 = sc->tulip_setupmap->dm_segs[1].ds_len;
4485	nextout->d_addr2 = sc->tulip_setupmap->dm_segs[1].ds_addr;
4486    }
4487    TULIP_TXMAP_PRESYNC(sc, sc->tulip_setupmap);
4488    TULIP_TXDESC_PRESYNC(sc, nextout, sizeof(*nextout));
4489#else
4490    nextout->d_length1 = sizeof(sc->tulip_setupbuf);
4491    nextout->d_addr1 = TULIP_KVATOPHYS(sc, sc->tulip_setupbuf);
4492#endif
4493
4494    /*
4495     * Advance the ring for the next transmit packet.
4496     */
4497    if (++ri->ri_nextout == ri->ri_last)
4498	ri->ri_nextout = ri->ri_first;
4499
4500    /*
4501     * Make sure the next descriptor is owned by us since it
4502     * may have been set up above if we ran out of room in the
4503     * ring.
4504     */
4505    ri->ri_nextout->d_status = 0;
4506    TULIP_TXDESC_PRESYNC(sc, ri->ri_nextout, sizeof(u_int32_t));
4507    nextout->d_status = TULIP_DSTS_OWNER;
4508    /*
4509     * Flush the ownwership of the current descriptor
4510     */
4511    TULIP_TXDESC_PRESYNC(sc, nextout, sizeof(u_int32_t));
4512    TULIP_CSR_WRITE(sc, csr_txpoll, 1);
4513    if ((sc->tulip_intrmask & TULIP_STS_TXINTR) == 0) {
4514	sc->tulip_intrmask |= TULIP_STS_TXINTR;
4515	TULIP_CSR_WRITE(sc, csr_intr, sc->tulip_intrmask);
4516    }
4517}
4518
4519
4520/*
4521 * This routine is entered at splnet() (splsoftnet() on NetBSD)
4522 * and thereby imposes no problems when TULIP_USE_SOFTINTR is
4523 * defined or not.
4524 */
4525static int
4526tulip_ifioctl(
4527    struct ifnet * ifp,
4528    u_long cmd,
4529    caddr_t data)
4530{
4531    TULIP_PERFSTART(ifioctl)
4532    tulip_softc_t * const sc = (tulip_softc_t *)ifp->if_softc;
4533    struct ifreq *ifr = (struct ifreq *) data;
4534    int s;
4535    int error = 0;
4536
4537#if defined(TULIP_USE_SOFTINTR)
4538    s = splnet();
4539#else
4540    s = splimp();
4541#endif
4542    switch (cmd) {
4543	case SIOCSIFFLAGS: {
4544	    tulip_addr_filter(sc); /* reinit multicast filter */
4545	    tulip_init(sc);
4546	    break;
4547	}
4548
4549	case SIOCSIFMEDIA:
4550	case SIOCGIFMEDIA: {
4551	    error = ifmedia_ioctl(ifp, ifr, &sc->tulip_ifmedia, cmd);
4552	    break;
4553	}
4554
4555	case SIOCADDMULTI:
4556	case SIOCDELMULTI: {
4557	    /*
4558	     * Update multicast listeners
4559	     */
4560	    tulip_addr_filter(sc);		/* reset multicast filtering */
4561	    tulip_init(sc);
4562	    error = 0;
4563	    break;
4564	}
4565
4566	case SIOCSIFMTU:
4567	    /*
4568	     * Set the interface MTU.
4569	     */
4570	    if (ifr->ifr_mtu > ETHERMTU
4571#ifdef BIG_PACKET
4572		    && sc->tulip_chipid != TULIP_21140
4573		    && sc->tulip_chipid != TULIP_21140A
4574		    && sc->tulip_chipid != TULIP_21041
4575#endif
4576		) {
4577		error = EINVAL;
4578		break;
4579	    }
4580	    ifp->if_mtu = ifr->ifr_mtu;
4581#ifdef BIG_PACKET
4582	    tulip_reset(sc);
4583	    tulip_init(sc);
4584#endif
4585	    break;
4586
4587#ifdef SIOCGADDRROM
4588	case SIOCGADDRROM: {
4589	    error = copyout(sc->tulip_rombuf, ifr->ifr_data, sizeof(sc->tulip_rombuf));
4590	    break;
4591	}
4592#endif
4593#ifdef SIOCGCHIPID
4594	case SIOCGCHIPID: {
4595	    ifr->ifr_metric = (int) sc->tulip_chipid;
4596	    break;
4597	}
4598#endif
4599	default: {
4600	    error = ether_ioctl(ifp, cmd, data);
4601	    break;
4602	}
4603    }
4604
4605    splx(s);
4606    TULIP_PERFEND(ifioctl);
4607    return error;
4608}
4609
4610/*
4611 * These routines gets called at device spl (from ether_output).  This might
4612 * pose a problem for TULIP_USE_SOFTINTR if ether_output is called at
4613 * device spl from another driver.
4614 */
4615
4616static void
4617tulip_ifstart(
4618    struct ifnet * const ifp)
4619{
4620    TULIP_PERFSTART(ifstart)
4621    tulip_softc_t * const sc = (tulip_softc_t *)ifp->if_softc;
4622
4623    if (sc->tulip_if.if_flags & IFF_RUNNING) {
4624
4625	if ((sc->tulip_flags & (TULIP_WANTSETUP|TULIP_TXPROBE_ACTIVE)) == TULIP_WANTSETUP)
4626	    tulip_txput_setup(sc);
4627
4628	while (!IFQ_DRV_IS_EMPTY(&sc->tulip_if.if_snd)) {
4629	    struct mbuf *m;
4630	    IFQ_DRV_DEQUEUE(&sc->tulip_if.if_snd, m);
4631	    if(m == NULL)
4632		break;
4633	    if ((m = tulip_txput(sc, m)) != NULL) {
4634		IFQ_DRV_PREPEND(&sc->tulip_if.if_snd, m);
4635		break;
4636	    }
4637	}
4638	if (IFQ_DRV_IS_EMPTY(&sc->tulip_if.if_snd))
4639	    sc->tulip_if.if_start = tulip_ifstart_one;
4640    }
4641
4642    TULIP_PERFEND(ifstart);
4643}
4644
4645static void
4646tulip_ifstart_one(
4647    struct ifnet * const ifp)
4648{
4649    TULIP_PERFSTART(ifstart_one)
4650    tulip_softc_t * const sc = (tulip_softc_t *)ifp->if_softc;
4651
4652    if ((sc->tulip_if.if_flags & IFF_RUNNING)
4653	    && !IFQ_DRV_IS_EMPTY(&sc->tulip_if.if_snd)) {
4654	struct mbuf *m;
4655	IFQ_DRV_DEQUEUE(&sc->tulip_if.if_snd, m);
4656	if(m == NULL);
4657	else if((m = tulip_txput(sc, m)) != NULL)
4658	    IFQ_DRV_PREPEND(&sc->tulip_if.if_snd, m);
4659    }
4660    TULIP_PERFEND(ifstart_one);
4661}
4662
4663/*
4664 * Even though this routine runs at device spl, it does not break
4665 * our use of splnet (splsoftnet under NetBSD) for the majority
4666 * of this driver (if TULIP_USE_SOFTINTR defined) since
4667 * if_watcbog is called from if_watchdog which is called from
4668 * splsoftclock which is below spl[soft]net.
4669 */
4670static void
4671tulip_ifwatchdog(
4672    struct ifnet *ifp)
4673{
4674    TULIP_PERFSTART(ifwatchdog)
4675    tulip_softc_t * const sc = (tulip_softc_t *)ifp->if_softc;
4676
4677#if defined(TULIP_DEBUG)
4678    u_int32_t rxintrs = sc->tulip_dbg.dbg_rxintrs - sc->tulip_dbg.dbg_last_rxintrs;
4679    if (rxintrs > sc->tulip_dbg.dbg_high_rxintrs_hz)
4680	sc->tulip_dbg.dbg_high_rxintrs_hz = rxintrs;
4681    sc->tulip_dbg.dbg_last_rxintrs = sc->tulip_dbg.dbg_rxintrs;
4682#endif /* TULIP_DEBUG */
4683
4684    sc->tulip_if.if_timer = 1;
4685    /*
4686     * These should be rare so do a bulk test up front so we can just skip
4687     * them if needed.
4688     */
4689    if (sc->tulip_flags & (TULIP_SYSTEMERROR|TULIP_RXBUFSLOW|TULIP_NOMESSAGES)) {
4690	/*
4691	 * If the number of receive buffer is low, try to refill
4692	 */
4693	if (sc->tulip_flags & TULIP_RXBUFSLOW)
4694	    tulip_rx_intr(sc);
4695
4696	if (sc->tulip_flags & TULIP_SYSTEMERROR) {
4697	    printf("%s: %d system errors: last was %s\n",
4698		   sc->tulip_xname, sc->tulip_system_errors,
4699		   tulip_system_errors[sc->tulip_last_system_error]);
4700	}
4701	if (sc->tulip_statusbits) {
4702	    tulip_print_abnormal_interrupt(sc, sc->tulip_statusbits);
4703	    sc->tulip_statusbits = 0;
4704	}
4705
4706	sc->tulip_flags &= ~(TULIP_NOMESSAGES|TULIP_SYSTEMERROR);
4707    }
4708
4709    if (sc->tulip_txtimer)
4710	tulip_tx_intr(sc);
4711    if (sc->tulip_txtimer && --sc->tulip_txtimer == 0) {
4712	printf("%s: transmission timeout\n", sc->tulip_xname);
4713	if (TULIP_DO_AUTOSENSE(sc)) {
4714	    sc->tulip_media = TULIP_MEDIA_UNKNOWN;
4715	    sc->tulip_probe_state = TULIP_PROBE_INACTIVE;
4716	    sc->tulip_flags &= ~(TULIP_WANTRXACT|TULIP_LINKUP);
4717	}
4718	tulip_reset(sc);
4719	tulip_init(sc);
4720    }
4721
4722    TULIP_PERFEND(ifwatchdog);
4723    TULIP_PERFMERGE(sc, perf_intr_cycles);
4724    TULIP_PERFMERGE(sc, perf_ifstart_cycles);
4725    TULIP_PERFMERGE(sc, perf_ifioctl_cycles);
4726    TULIP_PERFMERGE(sc, perf_ifwatchdog_cycles);
4727    TULIP_PERFMERGE(sc, perf_timeout_cycles);
4728    TULIP_PERFMERGE(sc, perf_ifstart_one_cycles);
4729    TULIP_PERFMERGE(sc, perf_txput_cycles);
4730    TULIP_PERFMERGE(sc, perf_txintr_cycles);
4731    TULIP_PERFMERGE(sc, perf_rxintr_cycles);
4732    TULIP_PERFMERGE(sc, perf_rxget_cycles);
4733    TULIP_PERFMERGE(sc, perf_intr);
4734    TULIP_PERFMERGE(sc, perf_ifstart);
4735    TULIP_PERFMERGE(sc, perf_ifioctl);
4736    TULIP_PERFMERGE(sc, perf_ifwatchdog);
4737    TULIP_PERFMERGE(sc, perf_timeout);
4738    TULIP_PERFMERGE(sc, perf_ifstart_one);
4739    TULIP_PERFMERGE(sc, perf_txput);
4740    TULIP_PERFMERGE(sc, perf_txintr);
4741    TULIP_PERFMERGE(sc, perf_rxintr);
4742    TULIP_PERFMERGE(sc, perf_rxget);
4743}
4744
4745/*
4746 * All printf's are real as of now!
4747 */
4748#ifdef printf
4749#undef printf
4750#endif
4751
4752static void
4753tulip_attach(
4754    tulip_softc_t * const sc)
4755{
4756    struct ifnet * const ifp = &sc->tulip_if;
4757
4758    /* XXX: driver name/unit should be set some other way */
4759    ifp->if_dname = "de";
4760    ifp->if_dunit = sc->tulip_unit;
4761    ifp->if_flags = IFF_BROADCAST|IFF_SIMPLEX|IFF_MULTICAST;
4762    ifp->if_ioctl = tulip_ifioctl;
4763    ifp->if_start = tulip_ifstart;
4764    ifp->if_watchdog = tulip_ifwatchdog;
4765    ifp->if_timer = 1;
4766    ifp->if_init = tulip_ifinit;
4767
4768    printf("%s: %s%s pass %d.%d%s\n",
4769	   sc->tulip_xname,
4770	   sc->tulip_boardid,
4771	   tulip_chipdescs[sc->tulip_chipid],
4772	   (sc->tulip_revinfo & 0xF0) >> 4,
4773	   sc->tulip_revinfo & 0x0F,
4774	   (sc->tulip_features & (TULIP_HAVE_ISVSROM|TULIP_HAVE_OKSROM))
4775		 == TULIP_HAVE_ISVSROM ? " (invalid EESPROM checksum)" : "");
4776#ifndef __FreeBSD__
4777    printf("%s: address %6D\n",
4778	   sc->tulip_xname, sc->tulip_enaddr, ":");
4779#endif
4780
4781#if defined(__alpha__)
4782    /*
4783     * In case the SRM console told us about a bogus media,
4784     * we need to check to be safe.
4785     */
4786    if (sc->tulip_mediums[sc->tulip_media] == NULL)
4787	sc->tulip_media = TULIP_MEDIA_UNKNOWN;
4788#endif
4789
4790    (*sc->tulip_boardsw->bd_media_probe)(sc);
4791    ifmedia_init(&sc->tulip_ifmedia, 0,
4792		 tulip_ifmedia_change,
4793		 tulip_ifmedia_status);
4794    sc->tulip_flags &= ~TULIP_DEVICEPROBE;
4795    tulip_ifmedia_add(sc);
4796
4797    tulip_reset(sc);
4798
4799    ether_ifattach(&(sc)->tulip_if, sc->tulip_enaddr);
4800    IFQ_SET_MAXLEN(&ifp->if_snd, ifqmaxlen);
4801    ifp->if_snd.ifq_drv_maxlen = ifqmaxlen;
4802    IFQ_SET_READY(&ifp->if_snd);
4803}
4804
4805#if defined(TULIP_BUS_DMA)
4806#if !defined(TULIP_BUS_DMA_NOTX) || !defined(TULIP_BUS_DMA_NORX)
4807static int
4808tulip_busdma_allocmem(
4809    tulip_softc_t * const sc,
4810    size_t size,
4811    bus_dmamap_t *map_p,
4812    tulip_desc_t **desc_p)
4813{
4814    bus_dma_segment_t segs[1];
4815    int nsegs, error;
4816    error = bus_dmamem_alloc(sc->tulip_dmatag, size, 1, PAGE_SIZE,
4817			     segs, sizeof(segs)/sizeof(segs[0]),
4818			     &nsegs, BUS_DMA_NOWAIT);
4819    if (error == 0) {
4820	void *desc;
4821	error = bus_dmamem_map(sc->tulip_dmatag, segs, nsegs, size,
4822			       (void *) &desc, BUS_DMA_NOWAIT|BUS_DMA_COHERENT);
4823	if (error == 0) {
4824	    bus_dmamap_t map;
4825	    error = bus_dmamap_create(sc->tulip_dmatag, size, 1, size, 0,
4826				      BUS_DMA_NOWAIT, &map);
4827	    if (error == 0) {
4828		error = bus_dmamap_load(sc->tulip_dmatag, map, desc,
4829					size, NULL, BUS_DMA_NOWAIT);
4830		if (error)
4831		    bus_dmamap_destroy(sc->tulip_dmatag, map);
4832		else
4833		    *map_p = map;
4834	    }
4835	    if (error)
4836		bus_dmamem_unmap(sc->tulip_dmatag, desc, size);
4837	}
4838	if (error)
4839	    bus_dmamem_free(sc->tulip_dmatag, segs, nsegs);
4840	else
4841	    *desc_p = desc;
4842    }
4843    return error;
4844}
4845#endif
4846
4847static int
4848tulip_busdma_init(
4849    tulip_softc_t * const sc)
4850{
4851    int error = 0;
4852
4853#if !defined(TULIP_BUS_DMA_NOTX)
4854    /*
4855     * Allocate dmamap for setup descriptor
4856     */
4857    error = bus_dmamap_create(sc->tulip_dmatag, sizeof(sc->tulip_setupbuf), 2,
4858			      sizeof(sc->tulip_setupbuf), 0, BUS_DMA_NOWAIT,
4859			      &sc->tulip_setupmap);
4860    if (error == 0) {
4861	error = bus_dmamap_load(sc->tulip_dmatag, sc->tulip_setupmap,
4862				sc->tulip_setupbuf, sizeof(sc->tulip_setupbuf),
4863				NULL, BUS_DMA_NOWAIT);
4864	if (error)
4865	    bus_dmamap_destroy(sc->tulip_dmatag, sc->tulip_setupmap);
4866    }
4867    /*
4868     * Allocate space and dmamap for transmit ring
4869     */
4870    if (error == 0) {
4871	error = tulip_busdma_allocmem(sc, sizeof(tulip_desc_t) * TULIP_TXDESCS,
4872				      &sc->tulip_txdescmap,
4873				      &sc->tulip_txdescs);
4874    }
4875
4876    /*
4877     * Allocate dmamaps for each transmit descriptors
4878     */
4879    if (error == 0) {
4880	while (error == 0 && sc->tulip_txmaps_free < TULIP_TXDESCS) {
4881	    bus_dmamap_t map;
4882	    if ((error = TULIP_TXMAP_CREATE(sc, &map)) == 0)
4883		sc->tulip_txmaps[sc->tulip_txmaps_free++] = map;
4884	}
4885	if (error) {
4886	    while (sc->tulip_txmaps_free > 0)
4887		bus_dmamap_destroy(sc->tulip_dmatag,
4888				   sc->tulip_txmaps[--sc->tulip_txmaps_free]);
4889	}
4890    }
4891#else
4892    if (error == 0) {
4893	sc->tulip_txdescs = (tulip_desc_t *) malloc(TULIP_TXDESCS * sizeof(tulip_desc_t), M_DEVBUF, M_NOWAIT);
4894	if (sc->tulip_txdescs == NULL)
4895	    error = ENOMEM;
4896    }
4897#endif
4898#if !defined(TULIP_BUS_DMA_NORX)
4899    /*
4900     * Allocate space and dmamap for receive ring
4901     */
4902    if (error == 0) {
4903	error = tulip_busdma_allocmem(sc, sizeof(tulip_desc_t) * TULIP_RXDESCS,
4904				      &sc->tulip_rxdescmap,
4905				      &sc->tulip_rxdescs);
4906    }
4907
4908    /*
4909     * Allocate dmamaps for each receive descriptors
4910     */
4911    if (error == 0) {
4912	while (error == 0 && sc->tulip_rxmaps_free < TULIP_RXDESCS) {
4913	    bus_dmamap_t map;
4914	    if ((error = TULIP_RXMAP_CREATE(sc, &map)) == 0)
4915		sc->tulip_rxmaps[sc->tulip_rxmaps_free++] = map;
4916	}
4917	if (error) {
4918	    while (sc->tulip_rxmaps_free > 0)
4919		bus_dmamap_destroy(sc->tulip_dmatag,
4920				   sc->tulip_rxmaps[--sc->tulip_rxmaps_free]);
4921	}
4922    }
4923#else
4924    if (error == 0) {
4925	sc->tulip_rxdescs = (tulip_desc_t *) malloc(TULIP_RXDESCS * sizeof(tulip_desc_t), M_DEVBUF, M_NOWAIT);
4926	if (sc->tulip_rxdescs == NULL)
4927	    error = ENOMEM;
4928    }
4929#endif
4930    return error;
4931}
4932#endif /* TULIP_BUS_DMA */
4933
4934static void
4935tulip_initcsrs(
4936    tulip_softc_t * const sc,
4937    tulip_csrptr_t csr_base,
4938    size_t csr_size)
4939{
4940    sc->tulip_csrs.csr_busmode		= csr_base +  0 * csr_size;
4941    sc->tulip_csrs.csr_txpoll		= csr_base +  1 * csr_size;
4942    sc->tulip_csrs.csr_rxpoll		= csr_base +  2 * csr_size;
4943    sc->tulip_csrs.csr_rxlist		= csr_base +  3 * csr_size;
4944    sc->tulip_csrs.csr_txlist		= csr_base +  4 * csr_size;
4945    sc->tulip_csrs.csr_status		= csr_base +  5 * csr_size;
4946    sc->tulip_csrs.csr_command		= csr_base +  6 * csr_size;
4947    sc->tulip_csrs.csr_intr		= csr_base +  7 * csr_size;
4948    sc->tulip_csrs.csr_missed_frames	= csr_base +  8 * csr_size;
4949    sc->tulip_csrs.csr_9		= csr_base +  9 * csr_size;
4950    sc->tulip_csrs.csr_10		= csr_base + 10 * csr_size;
4951    sc->tulip_csrs.csr_11		= csr_base + 11 * csr_size;
4952    sc->tulip_csrs.csr_12		= csr_base + 12 * csr_size;
4953    sc->tulip_csrs.csr_13		= csr_base + 13 * csr_size;
4954    sc->tulip_csrs.csr_14		= csr_base + 14 * csr_size;
4955    sc->tulip_csrs.csr_15		= csr_base + 15 * csr_size;
4956}
4957
4958static void
4959tulip_initring(
4960    tulip_softc_t * const sc,
4961    tulip_ringinfo_t * const ri,
4962    tulip_desc_t *descs,
4963    int ndescs)
4964{
4965    ri->ri_max = ndescs;
4966    ri->ri_first = descs;
4967    ri->ri_last = ri->ri_first + ri->ri_max;
4968    bzero((caddr_t) ri->ri_first, sizeof(ri->ri_first[0]) * ri->ri_max);
4969    ri->ri_last[-1].d_flag = TULIP_DFLAG_ENDRING;
4970}
4971
4972/*
4973 * This is the PCI configuration support.
4974 */
4975
4976#define	PCI_CBIO	0x10	/* Configuration Base IO Address */
4977#define	PCI_CBMA	0x14	/* Configuration Base Memory Address */
4978#define	PCI_CFDA	0x40	/* Configuration Driver Area */
4979
4980static int
4981tulip_pci_probe(device_t dev)
4982{
4983    const char *name = NULL;
4984
4985    if (pci_get_vendor(dev) != DEC_VENDORID)
4986	return ENXIO;
4987
4988    /*
4989     * Some LanMedia WAN cards use the Tulip chip, but they have
4990     * their own driver, and we should not recognize them
4991     */
4992    if (pci_get_subvendor(dev) == 0x1376)
4993	return ENXIO;
4994
4995    switch (pci_get_device(dev)) {
4996    case CHIPID_21040:
4997	name = "Digital 21040 Ethernet";
4998	break;
4999    case CHIPID_21041:
5000	name = "Digital 21041 Ethernet";
5001	break;
5002    case CHIPID_21140:
5003	if (pci_get_revid(dev) >= 0x20)
5004	    name = "Digital 21140A Fast Ethernet";
5005	else
5006	    name = "Digital 21140 Fast Ethernet";
5007	break;
5008    case CHIPID_21142:
5009	if (pci_get_revid(dev) >= 0x20)
5010	    name = "Digital 21143 Fast Ethernet";
5011	else
5012	    name = "Digital 21142 Fast Ethernet";
5013	break;
5014    }
5015    if (name) {
5016	device_set_desc(dev, name);
5017	return -200;
5018    }
5019    return ENXIO;
5020}
5021
5022static int
5023tulip_shutdown(device_t dev)
5024{
5025    tulip_softc_t * const sc = device_get_softc(dev);
5026    TULIP_CSR_WRITE(sc, csr_busmode, TULIP_BUSMODE_SWRESET);
5027    DELAY(10);	/* Wait 10 microseconds (actually 50 PCI cycles but at
5028		   33MHz that comes to two microseconds but wait a
5029		   bit longer anyways) */
5030    return 0;
5031}
5032
5033static int
5034tulip_pci_attach(device_t dev)
5035{
5036    tulip_softc_t *sc;
5037#if defined(__alpha__)
5038    tulip_media_t media = TULIP_MEDIA_UNKNOWN;
5039#endif
5040    int retval, idx;
5041    u_int32_t revinfo, cfdainfo, cfcsinfo;
5042    unsigned csroffset = TULIP_PCI_CSROFFSET;
5043    unsigned csrsize = TULIP_PCI_CSRSIZE;
5044    tulip_csrptr_t csr_base;
5045    tulip_chipid_t chipid = TULIP_CHIPID_UNKNOWN;
5046    struct resource *res;
5047    int rid, unit;
5048
5049    unit = device_get_unit(dev);
5050
5051    if (unit >= TULIP_MAX_DEVICES) {
5052	printf("de%d", unit);
5053	printf(": not configured; limit of %d reached or exceeded\n",
5054	       TULIP_MAX_DEVICES);
5055	return ENXIO;
5056    }
5057
5058    revinfo  = pci_get_revid(dev);
5059    cfdainfo = pci_read_config(dev, PCI_CFDA, 4);
5060    cfcsinfo = pci_read_config(dev, PCIR_COMMAND, 4);
5061
5062    /* turn busmaster on in case BIOS doesn't set it */
5063    if(!(cfcsinfo & PCIM_CMD_BUSMASTEREN)) {
5064	 cfcsinfo |= PCIM_CMD_BUSMASTEREN;
5065	 pci_write_config(dev, PCIR_COMMAND, cfcsinfo, 4);
5066    }
5067
5068    if (pci_get_vendor(dev) == DEC_VENDORID) {
5069	if (pci_get_device(dev) == CHIPID_21040)
5070		chipid = TULIP_21040;
5071	else if (pci_get_device(dev) == CHIPID_21041)
5072		chipid = TULIP_21041;
5073	else if (pci_get_device(dev) == CHIPID_21140)
5074		chipid = (revinfo >= 0x20) ? TULIP_21140A : TULIP_21140;
5075	else if (pci_get_device(dev) == CHIPID_21142)
5076		chipid = (revinfo >= 0x20) ? TULIP_21143 : TULIP_21142;
5077    }
5078    if (chipid == TULIP_CHIPID_UNKNOWN)
5079	return ENXIO;
5080
5081    if (chipid == TULIP_21040 && revinfo < 0x20) {
5082	printf("de%d", unit);
5083	printf(": not configured; 21040 pass 2.0 required (%d.%d found)\n",
5084	       revinfo >> 4, revinfo & 0x0f);
5085	return ENXIO;
5086    } else if (chipid == TULIP_21140 && revinfo < 0x11) {
5087	printf("de%d: not configured; 21140 pass 1.1 required (%d.%d found)\n",
5088	       unit, revinfo >> 4, revinfo & 0x0f);
5089	return ENXIO;
5090    }
5091
5092    sc = device_get_softc(dev);
5093    sc->tulip_pci_busno = pci_get_bus(dev);
5094    sc->tulip_pci_devno = pci_get_slot(dev);
5095    sc->tulip_chipid = chipid;
5096    sc->tulip_flags |= TULIP_DEVICEPROBE;
5097    if (chipid == TULIP_21140 || chipid == TULIP_21140A)
5098	sc->tulip_features |= TULIP_HAVE_GPR|TULIP_HAVE_STOREFWD;
5099    if (chipid == TULIP_21140A && revinfo <= 0x22)
5100	sc->tulip_features |= TULIP_HAVE_RXBADOVRFLW;
5101    if (chipid == TULIP_21140)
5102	sc->tulip_features |= TULIP_HAVE_BROKEN_HASH;
5103    if (chipid != TULIP_21040 && chipid != TULIP_21140)
5104	sc->tulip_features |= TULIP_HAVE_POWERMGMT;
5105    if (chipid == TULIP_21041 || chipid == TULIP_21142 || chipid == TULIP_21143) {
5106	sc->tulip_features |= TULIP_HAVE_DUALSENSE;
5107	if (chipid != TULIP_21041 || revinfo >= 0x20)
5108	    sc->tulip_features |= TULIP_HAVE_SIANWAY;
5109	if (chipid != TULIP_21041)
5110	    sc->tulip_features |= TULIP_HAVE_SIAGP|TULIP_HAVE_RXBADOVRFLW|TULIP_HAVE_STOREFWD;
5111	if (chipid != TULIP_21041 && revinfo >= 0x20)
5112	    sc->tulip_features |= TULIP_HAVE_SIA100;
5113    }
5114
5115    if (sc->tulip_features & TULIP_HAVE_POWERMGMT
5116	    && (cfdainfo & (TULIP_CFDA_SLEEP|TULIP_CFDA_SNOOZE))) {
5117	cfdainfo &= ~(TULIP_CFDA_SLEEP|TULIP_CFDA_SNOOZE);
5118	pci_write_config(dev, PCI_CFDA, cfdainfo, 4);
5119	DELAY(11*1000);
5120    }
5121#if defined(__alpha__)
5122    /*
5123     * The Alpha SRM console encodes a console set media in the driver
5124     * part of the CFDA register.  Note that the Multia presents a
5125     * problem in that its BNC mode is really EXTSIA.  So in that case
5126     * force a probe.
5127     */
5128    switch ((cfdainfo >> 8) & 0xff) {
5129	case 1: media = chipid > TULIP_21040 ? TULIP_MEDIA_AUI : TULIP_MEDIA_AUIBNC; break;
5130	case 2: media = chipid > TULIP_21040 ? TULIP_MEDIA_BNC : TULIP_MEDIA_UNKNOWN; break;
5131	case 3: media = TULIP_MEDIA_10BASET; break;
5132	case 4: media = TULIP_MEDIA_10BASET_FD; break;
5133	case 5: media = TULIP_MEDIA_100BASETX; break;
5134	case 6: media = TULIP_MEDIA_100BASETX_FD; break;
5135	default: media = TULIP_MEDIA_UNKNOWN; break;
5136    }
5137#endif
5138
5139    sc->tulip_unit = unit;
5140    snprintf(sc->tulip_xname, IFNAMSIZ, "de%d", sc->tulip_unit);
5141    sc->tulip_revinfo = revinfo;
5142    sc->tulip_if.if_softc = sc;
5143#if defined(TULIP_IOMAPPED)
5144    rid = PCI_CBIO;
5145    res = bus_alloc_resource_any(dev, SYS_RES_IOPORT, &rid, RF_ACTIVE);
5146#else
5147    rid = PCI_CBMA;
5148    res = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid, RF_ACTIVE);
5149#endif
5150    if (!res)
5151	return ENXIO;
5152    sc->tulip_csrs_bst = rman_get_bustag(res);
5153    sc->tulip_csrs_bsh = rman_get_bushandle(res);
5154    csr_base = 0;
5155
5156    tulips[unit] = sc;
5157
5158    tulip_initcsrs(sc, csr_base + csroffset, csrsize);
5159
5160#if defined(TULIP_BUS_DMA)
5161    if ((retval = tulip_busdma_init(sc)) != 0) {
5162	printf("error initing bus_dma: %d\n", retval);
5163	return ENXIO;
5164    }
5165#else
5166    sc->tulip_rxdescs = (tulip_desc_t *) malloc(sizeof(tulip_desc_t) * TULIP_RXDESCS, M_DEVBUF, M_NOWAIT);
5167    sc->tulip_txdescs = (tulip_desc_t *) malloc(sizeof(tulip_desc_t) * TULIP_TXDESCS, M_DEVBUF, M_NOWAIT);
5168    if (sc->tulip_rxdescs == NULL || sc->tulip_txdescs == NULL) {
5169	printf("malloc failed\n");
5170	if (sc->tulip_rxdescs)
5171	    free((caddr_t) sc->tulip_rxdescs, M_DEVBUF);
5172	if (sc->tulip_txdescs)
5173	    free((caddr_t) sc->tulip_txdescs, M_DEVBUF);
5174	return ENXIO;
5175    }
5176#endif
5177
5178    tulip_initring(sc, &sc->tulip_rxinfo, sc->tulip_rxdescs, TULIP_RXDESCS);
5179    tulip_initring(sc, &sc->tulip_txinfo, sc->tulip_txdescs, TULIP_TXDESCS);
5180
5181    /*
5182     * Make sure there won't be any interrupts or such...
5183     */
5184    TULIP_CSR_WRITE(sc, csr_busmode, TULIP_BUSMODE_SWRESET);
5185    DELAY(100);	/* Wait 10 microseconds (actually 50 PCI cycles but at
5186		   33MHz that comes to two microseconds but wait a
5187		   bit longer anyways) */
5188
5189    if ((retval = tulip_read_macaddr(sc)) < 0) {
5190	printf("%s", sc->tulip_xname);
5191	printf(": can't read ENET ROM (why=%d) (", retval);
5192	for (idx = 0; idx < 32; idx++)
5193	    printf("%02x", sc->tulip_rombuf[idx]);
5194	printf("\n");
5195	printf("%s: %s%s pass %d.%d\n",
5196	       sc->tulip_xname,
5197	       sc->tulip_boardid, tulip_chipdescs[sc->tulip_chipid],
5198	       (sc->tulip_revinfo & 0xF0) >> 4, sc->tulip_revinfo & 0x0F);
5199	printf("%s: address unknown\n", sc->tulip_xname);
5200    } else {
5201	int s;
5202	void (*intr_rtn)(void *) = tulip_intr_normal;
5203
5204	if (sc->tulip_features & TULIP_HAVE_SHAREDINTR)
5205	    intr_rtn = tulip_intr_shared;
5206
5207	if ((sc->tulip_features & TULIP_HAVE_SLAVEDINTR) == 0) {
5208	    void *ih;
5209
5210	    rid = 0;
5211	    res = bus_alloc_resource_any(dev, SYS_RES_IRQ, &rid,
5212					 RF_SHAREABLE | RF_ACTIVE);
5213	    if (res == 0 || bus_setup_intr(dev, res, INTR_TYPE_NET,
5214					   intr_rtn, sc, &ih)) {
5215		printf("%s: couldn't map interrupt\n",
5216		       sc->tulip_xname);
5217		free((caddr_t) sc->tulip_rxdescs, M_DEVBUF);
5218		free((caddr_t) sc->tulip_txdescs, M_DEVBUF);
5219		return ENXIO;
5220	    }
5221	}
5222#if defined(TULIP_USE_SOFTINTR)
5223	if (sc->tulip_unit > tulip_softintr_max_unit)
5224	    tulip_softintr_max_unit = sc->tulip_unit;
5225#endif
5226
5227	s = splimp();
5228#if defined(__alpha__)
5229	sc->tulip_media = media;
5230#endif
5231	tulip_attach(sc);
5232#if defined(__alpha__)
5233	if (sc->tulip_media != TULIP_MEDIA_UNKNOWN)
5234		tulip_linkup(sc, media);
5235#endif
5236	splx(s);
5237    }
5238    return 0;
5239}
5240
5241static device_method_t tulip_pci_methods[] = {
5242    /* Device interface */
5243    DEVMETHOD(device_probe,	tulip_pci_probe),
5244    DEVMETHOD(device_attach,	tulip_pci_attach),
5245    DEVMETHOD(device_shutdown,	tulip_shutdown),
5246    { 0, 0 }
5247};
5248static driver_t tulip_pci_driver = {
5249    "de",
5250    tulip_pci_methods,
5251    sizeof(tulip_softc_t),
5252};
5253static devclass_t tulip_devclass;
5254DRIVER_MODULE(de, pci, tulip_pci_driver, tulip_devclass, 0, 0);
5255