Annotation of sys/dev/pci/if_pcn.c, Revision 1.1.1.1
1.1 nbrk 1: /* $OpenBSD: if_pcn.c,v 1.15 2006/11/09 14:25:23 reyk Exp $ */
2: /* $NetBSD: if_pcn.c,v 1.26 2005/05/07 09:15:44 is Exp $ */
3:
4: /*
5: * Copyright (c) 2001 Wasabi Systems, Inc.
6: * All rights reserved.
7: *
8: * Written by Jason R. Thorpe for Wasabi Systems, Inc.
9: *
10: * Redistribution and use in source and binary forms, with or without
11: * modification, are permitted provided that the following conditions
12: * are met:
13: * 1. Redistributions of source code must retain the above copyright
14: * notice, this list of conditions and the following disclaimer.
15: * 2. Redistributions in binary form must reproduce the above copyright
16: * notice, this list of conditions and the following disclaimer in the
17: * documentation and/or other materials provided with the distribution.
18: * 3. All advertising materials mentioning features or use of this software
19: * must display the following acknowledgement:
20: * This product includes software developed for the NetBSD Project by
21: * Wasabi Systems, Inc.
22: * 4. The name of Wasabi Systems, Inc. may not be used to endorse
23: * or promote products derived from this software without specific prior
24: * written permission.
25: *
26: * THIS SOFTWARE IS PROVIDED BY WASABI SYSTEMS, INC. ``AS IS'' AND
27: * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
28: * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
29: * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL WASABI SYSTEMS, INC
30: * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
31: * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
32: * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
33: * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
34: * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
35: * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
36: * POSSIBILITY OF SUCH DAMAGE.
37: */
38:
39: /*
40: * Device driver for the AMD PCnet-PCI series of Ethernet
41: * chips:
42: *
43: * * Am79c970 PCnet-PCI Single-Chip Ethernet Controller for PCI
44: * Local Bus
45: *
46: * * Am79c970A PCnet-PCI II Single-Chip Full-Duplex Ethernet Controller
47: * for PCI Local Bus
48: *
49: * * Am79c971 PCnet-FAST Single-Chip Full-Duplex 10/100Mbps
50: * Ethernet Controller for PCI Local Bus
51: *
52: * * Am79c972 PCnet-FAST+ Enhanced 10/100Mbps PCI Ethernet Controller
53: * with OnNow Support
54: *
55: * * Am79c973/Am79c975 PCnet-FAST III Single-Chip 10/100Mbps PCI
56: * Ethernet Controller with Integrated PHY
57: *
58: * This also supports the virtual PCnet-PCI Ethernet interface found
59: * in VMware.
60: *
61: * TODO:
62: *
63: * * Split this into bus-specific and bus-independent portions.
64: * The core could also be used for the ILACC (Am79900) 32-bit
65: * Ethernet chip (XXX only if we use an ILACC-compatible SWSTYLE).
66: */
67:
68: #if 0
69: #include <sys/cdefs.h>
70: __KERNEL_RCSID(0, "$NetBSD: if_pcn.c,v 1.26 2005/05/07 09:15:44 is Exp $");
71: #endif
72:
73: #include "bpfilter.h"
74:
75: #include <sys/param.h>
76: #include <sys/systm.h>
77: #include <sys/timeout.h>
78: #include <sys/mbuf.h>
79: #include <sys/malloc.h>
80: #include <sys/kernel.h>
81: #include <sys/socket.h>
82: #include <sys/ioctl.h>
83: #include <sys/errno.h>
84: #include <sys/device.h>
85: #include <sys/queue.h>
86:
87: #include <net/if.h>
88: #include <net/if_dl.h>
89:
90: #ifdef INET
91: #include <netinet/in.h>
92: #include <netinet/in_systm.h>
93: #include <netinet/in_var.h>
94: #include <netinet/ip.h>
95: #include <netinet/if_ether.h>
96: #endif
97:
98: #include <net/if_media.h>
99:
100: #if NBPFILTER > 0
101: #include <net/bpf.h>
102: #endif
103:
104: #include <machine/bus.h>
105: #include <machine/intr.h>
106: #include <machine/endian.h>
107:
108: #include <dev/mii/mii.h>
109: #include <dev/mii/miivar.h>
110:
111: #include <dev/ic/am79900reg.h>
112: #include <dev/ic/lancereg.h>
113:
114: #include <dev/pci/pcireg.h>
115: #include <dev/pci/pcivar.h>
116: #include <dev/pci/pcidevs.h>
117:
118: /*
119: * Register definitions for the AMD PCnet-PCI series of Ethernet
120: * chips.
121: *
122: * These are only the registers that we access directly from PCI
123: * space. Everything else (accessed via the RAP + RDP/BDP) is
124: * defined in <dev/ic/lancereg.h>.
125: */
126:
127: /*
128: * PCI configuration space.
129: */
130:
131: #define PCN_PCI_CBIO (PCI_MAPREG_START + 0x00)
132: #define PCN_PCI_CBMEM (PCI_MAPREG_START + 0x04)
133:
134: /*
135: * I/O map in Word I/O mode.
136: */
137:
138: #define PCN16_APROM 0x00
139: #define PCN16_RDP 0x10
140: #define PCN16_RAP 0x12
141: #define PCN16_RESET 0x14
142: #define PCN16_BDP 0x16
143:
144: /*
145: * I/O map in DWord I/O mode.
146: */
147:
148: #define PCN32_APROM 0x00
149: #define PCN32_RDP 0x10
150: #define PCN32_RAP 0x14
151: #define PCN32_RESET 0x18
152: #define PCN32_BDP 0x1c
153:
154: /*
155: * Transmit descriptor list size. This is arbitrary, but allocate
156: * enough descriptors for 128 pending transmissions, and 4 segments
157: * per packet. This MUST work out to a power of 2.
158: *
159: * NOTE: We can't have any more than 512 Tx descriptors, SO BE CAREFUL!
160: *
161: * So we play a little trick here. We give each packet up to 16
162: * DMA segments, but only allocate the max of 512 descriptors. The
163: * transmit logic can deal with this, we just are hoping to sneak by.
164: */
165: #define PCN_NTXSEGS 16
166:
167: #define PCN_TXQUEUELEN 128
168: #define PCN_TXQUEUELEN_MASK (PCN_TXQUEUELEN - 1)
169: #define PCN_NTXDESC 512
170: #define PCN_NTXDESC_MASK (PCN_NTXDESC - 1)
171: #define PCN_NEXTTX(x) (((x) + 1) & PCN_NTXDESC_MASK)
172: #define PCN_NEXTTXS(x) (((x) + 1) & PCN_TXQUEUELEN_MASK)
173:
174: /* Tx interrupt every N + 1 packets. */
175: #define PCN_TXINTR_MASK 7
176:
177: /*
178: * Receive descriptor list size. We have one Rx buffer per incoming
179: * packet, so this logic is a little simpler.
180: */
181: #define PCN_NRXDESC 128
182: #define PCN_NRXDESC_MASK (PCN_NRXDESC - 1)
183: #define PCN_NEXTRX(x) (((x) + 1) & PCN_NRXDESC_MASK)
184:
185: /*
186: * Control structures are DMA'd to the PCnet chip. We allocate them in
187: * a single clump that maps to a single DMA segment to make several things
188: * easier.
189: */
190: struct pcn_control_data {
191: /* The transmit descriptors. */
192: struct letmd pcd_txdescs[PCN_NTXDESC];
193:
194: /* The receive descriptors. */
195: struct lermd pcd_rxdescs[PCN_NRXDESC];
196:
197: /* The init block. */
198: struct leinit pcd_initblock;
199: };
200:
201: #define PCN_CDOFF(x) offsetof(struct pcn_control_data, x)
202: #define PCN_CDTXOFF(x) PCN_CDOFF(pcd_txdescs[(x)])
203: #define PCN_CDRXOFF(x) PCN_CDOFF(pcd_rxdescs[(x)])
204: #define PCN_CDINITOFF PCN_CDOFF(pcd_initblock)
205:
206: /*
207: * Software state for transmit jobs.
208: */
209: struct pcn_txsoft {
210: struct mbuf *txs_mbuf; /* head of our mbuf chain */
211: bus_dmamap_t txs_dmamap; /* our DMA map */
212: int txs_firstdesc; /* first descriptor in packet */
213: int txs_lastdesc; /* last descriptor in packet */
214: };
215:
216: /*
217: * Software state for receive jobs.
218: */
219: struct pcn_rxsoft {
220: struct mbuf *rxs_mbuf; /* head of our mbuf chain */
221: bus_dmamap_t rxs_dmamap; /* our DMA map */
222: };
223:
224: /*
225: * Description of Rx FIFO watermarks for various revisions.
226: */
227: static const char * const pcn_79c970_rcvfw[] = {
228: "16 bytes",
229: "64 bytes",
230: "128 bytes",
231: NULL,
232: };
233:
234: static const char * const pcn_79c971_rcvfw[] = {
235: "16 bytes",
236: "64 bytes",
237: "112 bytes",
238: NULL,
239: };
240:
241: /*
242: * Description of Tx start points for various revisions.
243: */
244: static const char * const pcn_79c970_xmtsp[] = {
245: "8 bytes",
246: "64 bytes",
247: "128 bytes",
248: "248 bytes",
249: };
250:
251: static const char * const pcn_79c971_xmtsp[] = {
252: "20 bytes",
253: "64 bytes",
254: "128 bytes",
255: "248 bytes",
256: };
257:
258: static const char * const pcn_79c971_xmtsp_sram[] = {
259: "44 bytes",
260: "64 bytes",
261: "128 bytes",
262: "store-and-forward",
263: };
264:
265: /*
266: * Description of Tx FIFO watermarks for various revisions.
267: */
268: static const char * const pcn_79c970_xmtfw[] = {
269: "16 bytes",
270: "64 bytes",
271: "128 bytes",
272: NULL,
273: };
274:
275: static const char * const pcn_79c971_xmtfw[] = {
276: "16 bytes",
277: "64 bytes",
278: "108 bytes",
279: NULL,
280: };
281:
282: /*
283: * Software state per device.
284: */
285: struct pcn_softc {
286: struct device sc_dev; /* generic device information */
287: bus_space_tag_t sc_st; /* bus space tag */
288: bus_space_handle_t sc_sh; /* bus space handle */
289: bus_dma_tag_t sc_dmat; /* bus DMA tag */
290: struct arpcom sc_arpcom; /* Ethernet common data */
291: void *sc_sdhook; /* shutdown hook */
292:
293: /* Points to our media routines, etc. */
294: const struct pcn_variant *sc_variant;
295:
296: void *sc_ih; /* interrupt cookie */
297:
298: struct mii_data sc_mii; /* MII/media information */
299:
300: struct timeout sc_tick_timeout; /* tick timeout */
301:
302: bus_dmamap_t sc_cddmamap; /* control data DMA map */
303: #define sc_cddma sc_cddmamap->dm_segs[0].ds_addr
304:
305: /* Software state for transmit and receive descriptors. */
306: struct pcn_txsoft sc_txsoft[PCN_TXQUEUELEN];
307: struct pcn_rxsoft sc_rxsoft[PCN_NRXDESC];
308:
309: /* Control data structures */
310: struct pcn_control_data *sc_control_data;
311: #define sc_txdescs sc_control_data->pcd_txdescs
312: #define sc_rxdescs sc_control_data->pcd_rxdescs
313: #define sc_initblock sc_control_data->pcd_initblock
314:
315: const char * const *sc_rcvfw_desc; /* Rx FIFO watermark info */
316: int sc_rcvfw;
317:
318: const char * const *sc_xmtsp_desc; /* Tx start point info */
319: int sc_xmtsp;
320:
321: const char * const *sc_xmtfw_desc; /* Tx FIFO watermark info */
322: int sc_xmtfw;
323:
324: int sc_flags; /* misc. flags; see below */
325: int sc_swstyle; /* the software style in use */
326:
327: int sc_txfree; /* number of free Tx descriptors */
328: int sc_txnext; /* next ready Tx descriptor */
329:
330: int sc_txsfree; /* number of free Tx jobs */
331: int sc_txsnext; /* next free Tx job */
332: int sc_txsdirty; /* dirty Tx jobs */
333:
334: int sc_rxptr; /* next ready Rx descriptor/job */
335:
336: uint32_t sc_csr5; /* prototype CSR5 register */
337: uint32_t sc_mode; /* prototype MODE register */
338: };
339:
340: /* sc_flags */
341: #define PCN_F_HAS_MII 0x0001 /* has MII */
342:
343: #define PCN_CDTXADDR(sc, x) ((sc)->sc_cddma + PCN_CDTXOFF((x)))
344: #define PCN_CDRXADDR(sc, x) ((sc)->sc_cddma + PCN_CDRXOFF((x)))
345: #define PCN_CDINITADDR(sc) ((sc)->sc_cddma + PCN_CDINITOFF)
346:
347: #define PCN_CDTXSYNC(sc, x, n, ops) \
348: do { \
349: int __x, __n; \
350: \
351: __x = (x); \
352: __n = (n); \
353: \
354: /* If it will wrap around, sync to the end of the ring. */ \
355: if ((__x + __n) > PCN_NTXDESC) { \
356: bus_dmamap_sync((sc)->sc_dmat, (sc)->sc_cddmamap, \
357: PCN_CDTXOFF(__x), sizeof(struct letmd) * \
358: (PCN_NTXDESC - __x), (ops)); \
359: __n -= (PCN_NTXDESC - __x); \
360: __x = 0; \
361: } \
362: \
363: /* Now sync whatever is left. */ \
364: bus_dmamap_sync((sc)->sc_dmat, (sc)->sc_cddmamap, \
365: PCN_CDTXOFF(__x), sizeof(struct letmd) * __n, (ops)); \
366: } while (/*CONSTCOND*/0)
367:
368: #define PCN_CDRXSYNC(sc, x, ops) \
369: bus_dmamap_sync((sc)->sc_dmat, (sc)->sc_cddmamap, \
370: PCN_CDRXOFF((x)), sizeof(struct lermd), (ops))
371:
372: #define PCN_CDINITSYNC(sc, ops) \
373: bus_dmamap_sync((sc)->sc_dmat, (sc)->sc_cddmamap, \
374: PCN_CDINITOFF, sizeof(struct leinit), (ops))
375:
376: #define PCN_INIT_RXDESC(sc, x) \
377: do { \
378: struct pcn_rxsoft *__rxs = &(sc)->sc_rxsoft[(x)]; \
379: struct lermd *__rmd = &(sc)->sc_rxdescs[(x)]; \
380: struct mbuf *__m = __rxs->rxs_mbuf; \
381: \
382: /* \
383: * Note: We scoot the packet forward 2 bytes in the buffer \
384: * so that the payload after the Ethernet header is aligned \
385: * to a 4-byte boundary. \
386: */ \
387: __m->m_data = __m->m_ext.ext_buf + 2; \
388: \
389: if ((sc)->sc_swstyle == LE_B20_SSTYLE_PCNETPCI3) { \
390: __rmd->rmd2 = \
391: htole32(__rxs->rxs_dmamap->dm_segs[0].ds_addr + 2); \
392: __rmd->rmd0 = 0; \
393: } else { \
394: __rmd->rmd2 = 0; \
395: __rmd->rmd0 = \
396: htole32(__rxs->rxs_dmamap->dm_segs[0].ds_addr + 2); \
397: } \
398: __rmd->rmd1 = htole32(LE_R1_OWN|LE_R1_ONES| \
399: (LE_BCNT(MCLBYTES - 2) & LE_R1_BCNT_MASK)); \
400: PCN_CDRXSYNC((sc), (x), BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE);\
401: } while(/*CONSTCOND*/0)
402:
403: void pcn_start(struct ifnet *);
404: void pcn_watchdog(struct ifnet *);
405: int pcn_ioctl(struct ifnet *, u_long, caddr_t);
406: int pcn_init(struct ifnet *);
407: void pcn_stop(struct ifnet *, int);
408:
409: void pcn_shutdown(void *);
410:
411: void pcn_reset(struct pcn_softc *);
412: void pcn_rxdrain(struct pcn_softc *);
413: int pcn_add_rxbuf(struct pcn_softc *, int);
414: void pcn_tick(void *);
415:
416: void pcn_spnd(struct pcn_softc *);
417:
418: void pcn_set_filter(struct pcn_softc *);
419:
420: int pcn_intr(void *);
421: void pcn_txintr(struct pcn_softc *);
422: int pcn_rxintr(struct pcn_softc *);
423:
424: int pcn_mii_readreg(struct device *, int, int);
425: void pcn_mii_writereg(struct device *, int, int, int);
426: void pcn_mii_statchg(struct device *);
427:
428: void pcn_79c970_mediainit(struct pcn_softc *);
429: int pcn_79c970_mediachange(struct ifnet *);
430: void pcn_79c970_mediastatus(struct ifnet *, struct ifmediareq *);
431:
432: void pcn_79c971_mediainit(struct pcn_softc *);
433: int pcn_79c971_mediachange(struct ifnet *);
434: void pcn_79c971_mediastatus(struct ifnet *, struct ifmediareq *);
435:
436: /*
437: * Description of a PCnet-PCI variant. Used to select media access
438: * method, mostly, and to print a nice description of the chip.
439: */
440: static const struct pcn_variant {
441: const char *pcv_desc;
442: void (*pcv_mediainit)(struct pcn_softc *);
443: uint16_t pcv_chipid;
444: } pcn_variants[] = {
445: { "Am79c970",
446: pcn_79c970_mediainit,
447: PARTID_Am79c970 },
448:
449: { "Am79c970A",
450: pcn_79c970_mediainit,
451: PARTID_Am79c970A },
452:
453: { "Am79c971",
454: pcn_79c971_mediainit,
455: PARTID_Am79c971 },
456:
457: { "Am79c972",
458: pcn_79c971_mediainit,
459: PARTID_Am79c972 },
460:
461: { "Am79c973",
462: pcn_79c971_mediainit,
463: PARTID_Am79c973 },
464:
465: { "Am79c975",
466: pcn_79c971_mediainit,
467: PARTID_Am79c975 },
468:
469: { "Am79c976",
470: pcn_79c971_mediainit,
471: PARTID_Am79c976 },
472:
473: { "Am79c978",
474: pcn_79c971_mediainit,
475: PARTID_Am79c978 },
476:
477: { "Unknown",
478: pcn_79c971_mediainit,
479: 0 },
480: };
481:
482: int pcn_copy_small = 0;
483:
484: int pcn_match(struct device *, void *, void *);
485: void pcn_attach(struct device *, struct device *, void *);
486:
487: struct cfattach pcn_ca = {
488: sizeof(struct pcn_softc), pcn_match, pcn_attach,
489: };
490:
491: const struct pci_matchid pcn_devices[] = {
492: { PCI_VENDOR_AMD, PCI_PRODUCT_AMD_PCNET_PCI },
493: { PCI_VENDOR_AMD, PCI_PRODUCT_AMD_PCHOME_PCI }
494: };
495:
496: struct cfdriver pcn_cd = {
497: 0, "pcn", DV_IFNET
498: };
499:
500: /*
501: * Routines to read and write the PCnet-PCI CSR/BCR space.
502: */
503:
504: static __inline uint32_t
505: pcn_csr_read(struct pcn_softc *sc, int reg)
506: {
507:
508: bus_space_write_4(sc->sc_st, sc->sc_sh, PCN32_RAP, reg);
509: return (bus_space_read_4(sc->sc_st, sc->sc_sh, PCN32_RDP));
510: }
511:
512: static __inline void
513: pcn_csr_write(struct pcn_softc *sc, int reg, uint32_t val)
514: {
515:
516: bus_space_write_4(sc->sc_st, sc->sc_sh, PCN32_RAP, reg);
517: bus_space_write_4(sc->sc_st, sc->sc_sh, PCN32_RDP, val);
518: }
519:
520: static __inline uint32_t
521: pcn_bcr_read(struct pcn_softc *sc, int reg)
522: {
523:
524: bus_space_write_4(sc->sc_st, sc->sc_sh, PCN32_RAP, reg);
525: return (bus_space_read_4(sc->sc_st, sc->sc_sh, PCN32_BDP));
526: }
527:
528: static __inline void
529: pcn_bcr_write(struct pcn_softc *sc, int reg, uint32_t val)
530: {
531:
532: bus_space_write_4(sc->sc_st, sc->sc_sh, PCN32_RAP, reg);
533: bus_space_write_4(sc->sc_st, sc->sc_sh, PCN32_BDP, val);
534: }
535:
536: static const struct pcn_variant *
537: pcn_lookup_variant(uint16_t chipid)
538: {
539: const struct pcn_variant *pcv;
540:
541: for (pcv = pcn_variants; pcv->pcv_chipid != 0; pcv++) {
542: if (chipid == pcv->pcv_chipid)
543: return (pcv);
544: }
545:
546: /*
547: * This covers unknown chips, which we simply treat like
548: * a generic PCnet-FAST.
549: */
550: return (pcv);
551: }
552:
553: int
554: pcn_match(struct device *parent, void *match, void *aux)
555: {
556: struct pci_attach_args *pa = aux;
557:
558: /*
559: * IBM makes a PCI variant of this card which shows up as a
560: * Trident Microsystems 4DWAVE DX (ethernet network, revision 0x25)
561: * this card is truly a pcn card, so we have a special case match for
562: * it.
563: */
564: if (PCI_VENDOR(pa->pa_id) == PCI_VENDOR_TRIDENT &&
565: PCI_PRODUCT(pa->pa_id) == PCI_PRODUCT_TRIDENT_4DWAVE_DX &&
566: PCI_CLASS(pa->pa_class) == PCI_CLASS_NETWORK)
567: return(1);
568:
569: return (pci_matchbyid((struct pci_attach_args *)aux, pcn_devices,
570: sizeof(pcn_devices)/sizeof(pcn_devices[0])));
571: }
572:
573: void
574: pcn_attach(struct device *parent, struct device *self, void *aux)
575: {
576: struct pcn_softc *sc = (struct pcn_softc *) self;
577: struct pci_attach_args *pa = aux;
578: struct ifnet *ifp = &sc->sc_arpcom.ac_if;
579: pci_chipset_tag_t pc = pa->pa_pc;
580: pci_intr_handle_t ih;
581: const char *intrstr = NULL;
582: bus_space_tag_t iot, memt;
583: bus_space_handle_t ioh, memh;
584: bus_dma_segment_t seg;
585: int ioh_valid, memh_valid;
586: int i, rseg, error;
587: pcireg_t pmode;
588: uint32_t chipid, reg;
589: uint8_t enaddr[ETHER_ADDR_LEN];
590: int pmreg;
591:
592: timeout_set(&sc->sc_tick_timeout, pcn_tick, sc);
593:
594: /*
595: * Map the device.
596: */
597: ioh_valid = (pci_mapreg_map(pa, PCN_PCI_CBIO, PCI_MAPREG_TYPE_IO, 0,
598: &iot, &ioh, NULL, NULL, 0) == 0);
599: memh_valid = (pci_mapreg_map(pa, PCN_PCI_CBMEM,
600: PCI_MAPREG_TYPE_MEM|PCI_MAPREG_MEM_TYPE_32BIT, 0,
601: &memt, &memh, NULL, NULL, 0) == 0);
602:
603: if (memh_valid) {
604: sc->sc_st = memt;
605: sc->sc_sh = memh;
606: } else if (ioh_valid) {
607: sc->sc_st = iot;
608: sc->sc_sh = ioh;
609: } else {
610: printf(": unable to map device registers\n");
611: return;
612: }
613:
614: sc->sc_dmat = pa->pa_dmat;
615:
616: /* Get it out of power save mode, if needed. */
617: if (pci_get_capability(pc, pa->pa_tag, PCI_CAP_PWRMGMT, &pmreg, 0)) {
618: pmode = pci_conf_read(pc, pa->pa_tag, pmreg + PCI_PMCSR) &
619: PCI_PMCSR_STATE_MASK;
620: if (pmode == PCI_PMCSR_STATE_D3) {
621: /*
622: * The card has lost all configuration data in
623: * this state, so punt.
624: */
625: printf(": unable to wake from power state D3\n");
626: return;
627: }
628: if (pmode != PCI_PMCSR_STATE_D0) {
629: printf(": waking up from power date D%d",
630: pmode);
631: pci_conf_write(pc, pa->pa_tag, pmreg + PCI_PMCSR,
632: PCI_PMCSR_STATE_D0);
633: }
634: }
635:
636: /*
637: * Reset the chip to a known state. This also puts the
638: * chip into 32-bit mode.
639: */
640: pcn_reset(sc);
641:
642: #if !defined(PCN_NO_PROM)
643:
644: /*
645: * Read the Ethernet address from the EEPROM.
646: */
647: for (i = 0; i < ETHER_ADDR_LEN; i++)
648: enaddr[i] = bus_space_read_1(sc->sc_st, sc->sc_sh,
649: PCN32_APROM + i);
650: #else
651: /*
652: * The PROM is not used; instead we assume that the MAC address
653: * has been programmed into the device's physical address
654: * registers by the boot firmware
655: */
656:
657: for (i=0; i < 3; i++) {
658: uint32_t val;
659: val = pcn_csr_read(sc, LE_CSR12 + i);
660: enaddr[2*i] = val & 0x0ff;
661: enaddr[2*i+1] = (val >> 8) & 0x0ff;
662: }
663: #endif
664:
665: /*
666: * Now that the device is mapped, attempt to figure out what
667: * kind of chip we have. Note that IDL has all 32 bits of
668: * the chip ID when we're in 32-bit mode.
669: */
670: chipid = pcn_csr_read(sc, LE_CSR88);
671: sc->sc_variant = pcn_lookup_variant(CHIPID_PARTID(chipid));
672:
673: /*
674: * Map and establish our interrupt.
675: */
676: if (pci_intr_map(pa, &ih)) {
677: printf(": unable to map interrupt\n");
678: return;
679: }
680: intrstr = pci_intr_string(pc, ih);
681: sc->sc_ih = pci_intr_establish(pc, ih, IPL_NET, pcn_intr, sc,
682: self->dv_xname);
683: if (sc->sc_ih == NULL) {
684: printf(": unable to establish interrupt");
685: if (intrstr != NULL)
686: printf(" at %s", intrstr);
687: printf("\n");
688: return;
689: }
690:
691: /*
692: * Allocate the control data structures, and create and load the
693: * DMA map for it.
694: */
695: if ((error = bus_dmamem_alloc(sc->sc_dmat,
696: sizeof(struct pcn_control_data), PAGE_SIZE, 0, &seg, 1, &rseg,
697: 0)) != 0) {
698: printf(": unable to allocate control data, error = %d\n",
699: error);
700: return;
701: }
702:
703: if ((error = bus_dmamem_map(sc->sc_dmat, &seg, rseg,
704: sizeof(struct pcn_control_data), (caddr_t *)&sc->sc_control_data,
705: BUS_DMA_COHERENT)) != 0) {
706: printf(": unable to map control data, error = %d\n",
707: error);
708: goto fail_1;
709: }
710:
711: if ((error = bus_dmamap_create(sc->sc_dmat,
712: sizeof(struct pcn_control_data), 1,
713: sizeof(struct pcn_control_data), 0, 0, &sc->sc_cddmamap)) != 0) {
714: printf(": unable to create control data DMA map, "
715: "error = %d\n", error);
716: goto fail_2;
717: }
718:
719: if ((error = bus_dmamap_load(sc->sc_dmat, sc->sc_cddmamap,
720: sc->sc_control_data, sizeof(struct pcn_control_data), NULL,
721: 0)) != 0) {
722: printf(": unable to load control data DMA map, error = %d\n",
723: error);
724: goto fail_3;
725: }
726:
727: /* Create the transmit buffer DMA maps. */
728: for (i = 0; i < PCN_TXQUEUELEN; i++) {
729: if ((error = bus_dmamap_create(sc->sc_dmat, MCLBYTES,
730: PCN_NTXSEGS, MCLBYTES, 0, 0,
731: &sc->sc_txsoft[i].txs_dmamap)) != 0) {
732: printf(": unable to create tx DMA map %d, "
733: "error = %d\n", i, error);
734: goto fail_4;
735: }
736: }
737:
738: /* Create the receive buffer DMA maps. */
739: for (i = 0; i < PCN_NRXDESC; i++) {
740: if ((error = bus_dmamap_create(sc->sc_dmat, MCLBYTES, 1,
741: MCLBYTES, 0, 0, &sc->sc_rxsoft[i].rxs_dmamap)) != 0) {
742: printf(": unable to create rx DMA map %d, "
743: "error = %d\n", i, error);
744: goto fail_5;
745: }
746: sc->sc_rxsoft[i].rxs_mbuf = NULL;
747: }
748:
749: printf(", %s, rev %d: %s, address %s\n", sc->sc_variant->pcv_desc,
750: CHIPID_VER(chipid), intrstr, ether_sprintf(enaddr));
751:
752: /* Initialize our media structures. */
753: (*sc->sc_variant->pcv_mediainit)(sc);
754:
755: /*
756: * Initialize FIFO watermark info.
757: */
758: switch (sc->sc_variant->pcv_chipid) {
759: case PARTID_Am79c970:
760: case PARTID_Am79c970A:
761: sc->sc_rcvfw_desc = pcn_79c970_rcvfw;
762: sc->sc_xmtsp_desc = pcn_79c970_xmtsp;
763: sc->sc_xmtfw_desc = pcn_79c970_xmtfw;
764: break;
765:
766: default:
767: sc->sc_rcvfw_desc = pcn_79c971_rcvfw;
768: /*
769: * Read BCR25 to determine how much SRAM is
770: * on the board. If > 0, then we the chip
771: * uses different Start Point thresholds.
772: *
773: * Note BCR25 and BCR26 are loaded from the
774: * EEPROM on RST, and unaffected by S_RESET,
775: * so we don't really have to worry about
776: * them except for this.
777: */
778: reg = pcn_bcr_read(sc, LE_BCR25) & 0x00ff;
779: if (reg != 0)
780: sc->sc_xmtsp_desc = pcn_79c971_xmtsp_sram;
781: else
782: sc->sc_xmtsp_desc = pcn_79c971_xmtsp;
783: sc->sc_xmtfw_desc = pcn_79c971_xmtfw;
784: break;
785: }
786:
787: /*
788: * Set up defaults -- see the tables above for what these
789: * values mean.
790: *
791: * XXX How should we tune RCVFW and XMTFW?
792: */
793: sc->sc_rcvfw = 1; /* minimum for full-duplex */
794: sc->sc_xmtsp = 1;
795: sc->sc_xmtfw = 0;
796:
797: ifp = &sc->sc_arpcom.ac_if;
798: bcopy(enaddr, sc->sc_arpcom.ac_enaddr, ETHER_ADDR_LEN);
799: bcopy(sc->sc_dev.dv_xname, ifp->if_xname, IFNAMSIZ);
800: ifp->if_softc = sc;
801: ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST;
802: ifp->if_ioctl = pcn_ioctl;
803: ifp->if_start = pcn_start;
804: ifp->if_watchdog = pcn_watchdog;
805: IFQ_SET_MAXLEN(&ifp->if_snd, PCN_NTXDESC -1);
806: IFQ_SET_READY(&ifp->if_snd);
807:
808: /* Attach the interface. */
809: if_attach(ifp);
810: ether_ifattach(ifp);
811:
812: /* Make sure the interface is shutdown during reboot. */
813: sc->sc_sdhook = shutdownhook_establish(pcn_shutdown, sc);
814: if (sc->sc_sdhook == NULL)
815: printf("%s: WARNING: unable to establish shutdown hook\n",
816: sc->sc_dev.dv_xname);
817: return;
818:
819: /*
820: * Free any resources we've allocated during the failed attach
821: * attempt. Do this in reverse order and fall through.
822: */
823: fail_5:
824: for (i = 0; i < PCN_NRXDESC; i++) {
825: if (sc->sc_rxsoft[i].rxs_dmamap != NULL)
826: bus_dmamap_destroy(sc->sc_dmat,
827: sc->sc_rxsoft[i].rxs_dmamap);
828: }
829: fail_4:
830: for (i = 0; i < PCN_TXQUEUELEN; i++) {
831: if (sc->sc_txsoft[i].txs_dmamap != NULL)
832: bus_dmamap_destroy(sc->sc_dmat,
833: sc->sc_txsoft[i].txs_dmamap);
834: }
835: bus_dmamap_unload(sc->sc_dmat, sc->sc_cddmamap);
836: fail_3:
837: bus_dmamap_destroy(sc->sc_dmat, sc->sc_cddmamap);
838: fail_2:
839: bus_dmamem_unmap(sc->sc_dmat, (caddr_t)sc->sc_control_data,
840: sizeof(struct pcn_control_data));
841: fail_1:
842: bus_dmamem_free(sc->sc_dmat, &seg, rseg);
843: }
844:
845: /*
846: * pcn_shutdown:
847: *
848: * Make sure the interface is stopped at reboot time.
849: */
850: void
851: pcn_shutdown(void *arg)
852: {
853: struct pcn_softc *sc = arg;
854:
855: pcn_stop(&sc->sc_arpcom.ac_if, 1);
856: pcn_reset(sc);
857: }
858:
859: /*
860: * pcn_start: [ifnet interface function]
861: *
862: * Start packet transmission on the interface.
863: */
864: void
865: pcn_start(struct ifnet *ifp)
866: {
867: struct pcn_softc *sc = ifp->if_softc;
868: struct mbuf *m0, *m;
869: struct pcn_txsoft *txs;
870: bus_dmamap_t dmamap;
871: int error, nexttx, lasttx = -1, ofree, seg;
872:
873: if ((ifp->if_flags & (IFF_RUNNING|IFF_OACTIVE)) != IFF_RUNNING)
874: return;
875:
876: /*
877: * Remember the previous number of free descriptors and
878: * the first descriptor we'll use.
879: */
880: ofree = sc->sc_txfree;
881:
882: /*
883: * Loop through the send queue, setting up transmit descriptors
884: * until we drain the queue, or use up all available transmit
885: * descriptors.
886: */
887: for (;;) {
888: /* Grab a packet off the queue. */
889: IFQ_POLL(&ifp->if_snd, m0);
890: if (m0 == NULL)
891: break;
892: m = NULL;
893:
894: /* Get a work queue entry. */
895: if (sc->sc_txsfree == 0)
896: break;
897:
898: txs = &sc->sc_txsoft[sc->sc_txsnext];
899: dmamap = txs->txs_dmamap;
900:
901: /*
902: * Load the DMA map. If this fails, the packet either
903: * didn't fit in the alloted number of segments, or we
904: * were short on resources. In this case, we'll copy
905: * and try again.
906: */
907: if (bus_dmamap_load_mbuf(sc->sc_dmat, dmamap, m0,
908: BUS_DMA_WRITE|BUS_DMA_NOWAIT) != 0) {
909: MGETHDR(m, M_DONTWAIT, MT_DATA);
910: if (m == NULL)
911: break;
912: if (m0->m_pkthdr.len > MHLEN) {
913: MCLGET(m, M_DONTWAIT);
914: if ((m->m_flags & M_EXT) == 0) {
915: m_freem(m);
916: break;
917: }
918: }
919: m_copydata(m0, 0, m0->m_pkthdr.len, mtod(m, caddr_t));
920: m->m_pkthdr.len = m->m_len = m0->m_pkthdr.len;
921: error = bus_dmamap_load_mbuf(sc->sc_dmat, dmamap,
922: m, BUS_DMA_WRITE|BUS_DMA_NOWAIT);
923: if (error)
924: break;
925: }
926:
927: /*
928: * Ensure we have enough descriptors free to describe
929: * the packet. Note, we always reserve one descriptor
930: * at the end of the ring as a termination point, to
931: * prevent wrap-around.
932: */
933: if (dmamap->dm_nsegs > (sc->sc_txfree - 1)) {
934: /*
935: * Not enough free descriptors to transmit this
936: * packet. We haven't committed anything yet,
937: * so just unload the DMA map, put the packet
938: * back on the queue, and punt. Notify the upper
939: * layer that there are not more slots left.
940: *
941: * XXX We could allocate an mbuf and copy, but
942: * XXX is it worth it?
943: */
944: ifp->if_flags |= IFF_OACTIVE;
945: bus_dmamap_unload(sc->sc_dmat, dmamap);
946: if (m != NULL)
947: m_freem(m);
948: break;
949: }
950:
951: IFQ_DEQUEUE(&ifp->if_snd, m0);
952: if (m != NULL) {
953: m_freem(m0);
954: m0 = m;
955: }
956:
957: /*
958: * WE ARE NOW COMMITTED TO TRANSMITTING THE PACKET.
959: */
960:
961: /* Sync the DMA map. */
962: bus_dmamap_sync(sc->sc_dmat, dmamap, 0, dmamap->dm_mapsize,
963: BUS_DMASYNC_PREWRITE);
964:
965: /*
966: * Initialize the transmit descriptors.
967: */
968: if (sc->sc_swstyle == LE_B20_SSTYLE_PCNETPCI3) {
969: for (nexttx = sc->sc_txnext, seg = 0;
970: seg < dmamap->dm_nsegs;
971: seg++, nexttx = PCN_NEXTTX(nexttx)) {
972: /*
973: * If this is the first descriptor we're
974: * enqueueing, don't set the OWN bit just
975: * yet. That could cause a race condition.
976: * We'll do it below.
977: */
978: sc->sc_txdescs[nexttx].tmd0 = 0;
979: sc->sc_txdescs[nexttx].tmd2 =
980: htole32(dmamap->dm_segs[seg].ds_addr);
981: sc->sc_txdescs[nexttx].tmd1 =
982: htole32(LE_T1_ONES |
983: (nexttx == sc->sc_txnext ? 0 : LE_T1_OWN) |
984: (LE_BCNT(dmamap->dm_segs[seg].ds_len) &
985: LE_T1_BCNT_MASK));
986: lasttx = nexttx;
987: }
988: } else {
989: for (nexttx = sc->sc_txnext, seg = 0;
990: seg < dmamap->dm_nsegs;
991: seg++, nexttx = PCN_NEXTTX(nexttx)) {
992: /*
993: * If this is the first descriptor we're
994: * enqueueing, don't set the OWN bit just
995: * yet. That could cause a race condition.
996: * We'll do it below.
997: */
998: sc->sc_txdescs[nexttx].tmd0 =
999: htole32(dmamap->dm_segs[seg].ds_addr);
1000: sc->sc_txdescs[nexttx].tmd2 = 0;
1001: sc->sc_txdescs[nexttx].tmd1 =
1002: htole32(LE_T1_ONES |
1003: (nexttx == sc->sc_txnext ? 0 : LE_T1_OWN) |
1004: (LE_BCNT(dmamap->dm_segs[seg].ds_len) &
1005: LE_T1_BCNT_MASK));
1006: lasttx = nexttx;
1007: }
1008: }
1009:
1010: KASSERT(lasttx != -1);
1011: /* Interrupt on the packet, if appropriate. */
1012: if ((sc->sc_txsnext & PCN_TXINTR_MASK) == 0)
1013: sc->sc_txdescs[lasttx].tmd1 |= htole32(LE_T1_LTINT);
1014:
1015: /* Set `start of packet' and `end of packet' appropriately. */
1016: sc->sc_txdescs[lasttx].tmd1 |= htole32(LE_T1_ENP);
1017: sc->sc_txdescs[sc->sc_txnext].tmd1 |=
1018: htole32(LE_T1_OWN|LE_T1_STP);
1019:
1020: /* Sync the descriptors we're using. */
1021: PCN_CDTXSYNC(sc, sc->sc_txnext, dmamap->dm_nsegs,
1022: BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE);
1023:
1024: /* Kick the transmitter. */
1025: pcn_csr_write(sc, LE_CSR0, LE_C0_INEA|LE_C0_TDMD);
1026:
1027: /*
1028: * Store a pointer to the packet so we can free it later,
1029: * and remember what txdirty will be once the packet is
1030: * done.
1031: */
1032: txs->txs_mbuf = m0;
1033: txs->txs_firstdesc = sc->sc_txnext;
1034: txs->txs_lastdesc = lasttx;
1035:
1036: /* Advance the tx pointer. */
1037: sc->sc_txfree -= dmamap->dm_nsegs;
1038: sc->sc_txnext = nexttx;
1039:
1040: sc->sc_txsfree--;
1041: sc->sc_txsnext = PCN_NEXTTXS(sc->sc_txsnext);
1042:
1043: #if NBPFILTER > 0
1044: /* Pass the packet to any BPF listeners. */
1045: if (ifp->if_bpf)
1046: bpf_mtap(ifp->if_bpf, m0, BPF_DIRECTION_OUT);
1047: #endif /* NBPFILTER > 0 */
1048: }
1049:
1050: if (sc->sc_txsfree == 0 || sc->sc_txfree == 0) {
1051: /* No more slots left; notify upper layer. */
1052: ifp->if_flags |= IFF_OACTIVE;
1053: }
1054:
1055: if (sc->sc_txfree != ofree) {
1056: /* Set a watchdog timer in case the chip flakes out. */
1057: ifp->if_timer = 5;
1058: }
1059: }
1060:
1061: /*
1062: * pcn_watchdog: [ifnet interface function]
1063: *
1064: * Watchdog timer handler.
1065: */
1066: void
1067: pcn_watchdog(struct ifnet *ifp)
1068: {
1069: struct pcn_softc *sc = ifp->if_softc;
1070:
1071: /*
1072: * Since we're not interrupting every packet, sweep
1073: * up before we report an error.
1074: */
1075: pcn_txintr(sc);
1076:
1077: if (sc->sc_txfree != PCN_NTXDESC) {
1078: printf("%s: device timeout (txfree %d txsfree %d)\n",
1079: sc->sc_dev.dv_xname, sc->sc_txfree, sc->sc_txsfree);
1080: ifp->if_oerrors++;
1081:
1082: /* Reset the interface. */
1083: (void) pcn_init(ifp);
1084: }
1085:
1086: /* Try to get more packets going. */
1087: pcn_start(ifp);
1088: }
1089:
1090: /*
1091: * pcn_ioctl: [ifnet interface function]
1092: *
1093: * Handle control requests from the operator.
1094: */
1095: int
1096: pcn_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
1097: {
1098: struct pcn_softc *sc = ifp->if_softc;
1099: struct ifreq *ifr = (struct ifreq *) data;
1100: struct ifaddr *ifa = (struct ifaddr *)data;
1101: int s, error = 0;
1102:
1103: s = splnet();
1104:
1105: if ((error = ether_ioctl(ifp, &sc->sc_arpcom, cmd, data)) > 0) {
1106: /* Try to get more packets going. */
1107: pcn_start(ifp);
1108:
1109: splx(s);
1110: return (error);
1111: }
1112:
1113: switch (cmd) {
1114: case SIOCSIFADDR:
1115: ifp->if_flags |= IFF_UP;
1116:
1117: switch (ifa->ifa_addr->sa_family) {
1118: #ifdef INET
1119: case AF_INET:
1120: pcn_init(ifp);
1121: arp_ifinit(&sc->sc_arpcom, ifa);
1122: break;
1123: #endif
1124: default:
1125: pcn_init(ifp);
1126: break;
1127: }
1128: break;
1129:
1130: case SIOCSIFMTU:
1131: if (ifr->ifr_mtu > ETHERMTU || ifr->ifr_mtu < ETHERMIN)
1132: error = EINVAL;
1133: else if (ifp->if_mtu != ifr->ifr_mtu)
1134: ifp->if_mtu = ifr->ifr_mtu;
1135: break;
1136:
1137: case SIOCSIFFLAGS:
1138: /*
1139: * If interface is marked up and not running, then start it.
1140: * If it is marked down and running, stop it.
1141: * XXX If it's up then re-initialize it. This is so flags
1142: * such as IFF_PROMISC are handled.
1143: */
1144: if (ifp->if_flags & IFF_UP)
1145: pcn_init(ifp);
1146: else if (ifp->if_flags & IFF_RUNNING)
1147: pcn_stop(ifp, 1);
1148: break;
1149:
1150: case SIOCADDMULTI:
1151: case SIOCDELMULTI:
1152: error = (cmd == SIOCADDMULTI) ?
1153: ether_addmulti(ifr, &sc->sc_arpcom) :
1154: ether_delmulti(ifr, &sc->sc_arpcom);
1155:
1156: if (error == ENETRESET) {
1157: /*
1158: * Multicast list has changed; set the hardware
1159: * filter accordingly.
1160: */
1161: if (ifp->if_flags & IFF_RUNNING)
1162: error = pcn_init(ifp);
1163: else
1164: error = 0;
1165: }
1166: break;
1167:
1168: case SIOCSIFMEDIA:
1169: case SIOCGIFMEDIA:
1170: error = ifmedia_ioctl(ifp, ifr, &sc->sc_mii.mii_media, cmd);
1171: break;
1172:
1173: default:
1174: error = ENOTTY;
1175: }
1176:
1177: /* Try to get more packets going. */
1178: pcn_start(ifp);
1179:
1180: splx(s);
1181: return (error);
1182: }
1183:
1184: /*
1185: * pcn_intr:
1186: *
1187: * Interrupt service routine.
1188: */
1189: int
1190: pcn_intr(void *arg)
1191: {
1192: struct pcn_softc *sc = arg;
1193: struct ifnet *ifp = &sc->sc_arpcom.ac_if;
1194: uint32_t csr0;
1195: int wantinit, handled = 0;
1196:
1197: for (wantinit = 0; wantinit == 0;) {
1198: csr0 = pcn_csr_read(sc, LE_CSR0);
1199: if ((csr0 & LE_C0_INTR) == 0)
1200: break;
1201:
1202: /* ACK the bits and re-enable interrupts. */
1203: pcn_csr_write(sc, LE_CSR0, csr0 &
1204: (LE_C0_INEA|LE_C0_BABL|LE_C0_MISS|LE_C0_MERR|LE_C0_RINT|
1205: LE_C0_TINT|LE_C0_IDON));
1206:
1207: handled = 1;
1208:
1209: if (csr0 & LE_C0_RINT)
1210: wantinit = pcn_rxintr(sc);
1211:
1212: if (csr0 & LE_C0_TINT)
1213: pcn_txintr(sc);
1214:
1215: if (csr0 & LE_C0_ERR) {
1216: if (csr0 & LE_C0_BABL)
1217: ifp->if_oerrors++;
1218: if (csr0 & LE_C0_MISS)
1219: ifp->if_ierrors++;
1220: if (csr0 & LE_C0_MERR) {
1221: printf("%s: memory error\n",
1222: sc->sc_dev.dv_xname);
1223: wantinit = 1;
1224: break;
1225: }
1226: }
1227:
1228: if ((csr0 & LE_C0_RXON) == 0) {
1229: printf("%s: receiver disabled\n",
1230: sc->sc_dev.dv_xname);
1231: ifp->if_ierrors++;
1232: wantinit = 1;
1233: }
1234:
1235: if ((csr0 & LE_C0_TXON) == 0) {
1236: printf("%s: transmitter disabled\n",
1237: sc->sc_dev.dv_xname);
1238: ifp->if_oerrors++;
1239: wantinit = 1;
1240: }
1241: }
1242:
1243: if (handled) {
1244: if (wantinit)
1245: pcn_init(ifp);
1246:
1247: /* Try to get more packets going. */
1248: pcn_start(ifp);
1249: }
1250:
1251: return (handled);
1252: }
1253:
1254: /*
1255: * pcn_spnd:
1256: *
1257: * Suspend the chip.
1258: */
1259: void
1260: pcn_spnd(struct pcn_softc *sc)
1261: {
1262: int i;
1263:
1264: pcn_csr_write(sc, LE_CSR5, sc->sc_csr5 | LE_C5_SPND);
1265:
1266: for (i = 0; i < 10000; i++) {
1267: if (pcn_csr_read(sc, LE_CSR5) & LE_C5_SPND)
1268: return;
1269: delay(5);
1270: }
1271:
1272: printf("%s: WARNING: chip failed to enter suspended state\n",
1273: sc->sc_dev.dv_xname);
1274: }
1275:
1276: /*
1277: * pcn_txintr:
1278: *
1279: * Helper; handle transmit interrupts.
1280: */
1281: void
1282: pcn_txintr(struct pcn_softc *sc)
1283: {
1284: struct ifnet *ifp = &sc->sc_arpcom.ac_if;
1285: struct pcn_txsoft *txs;
1286: uint32_t tmd1, tmd2, tmd;
1287: int i, j;
1288:
1289: ifp->if_flags &= ~IFF_OACTIVE;
1290:
1291: /*
1292: * Go through our Tx list and free mbufs for those
1293: * frames which have been transmitted.
1294: */
1295: for (i = sc->sc_txsdirty; sc->sc_txsfree != PCN_TXQUEUELEN;
1296: i = PCN_NEXTTXS(i), sc->sc_txsfree++) {
1297: txs = &sc->sc_txsoft[i];
1298:
1299: PCN_CDTXSYNC(sc, txs->txs_firstdesc, txs->txs_dmamap->dm_nsegs,
1300: BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE);
1301:
1302: tmd1 = letoh32(sc->sc_txdescs[txs->txs_lastdesc].tmd1);
1303: if (tmd1 & LE_T1_OWN)
1304: break;
1305:
1306: /*
1307: * Slightly annoying -- we have to loop through the
1308: * descriptors we've used looking for ERR, since it
1309: * can appear on any descriptor in the chain.
1310: */
1311: for (j = txs->txs_firstdesc;; j = PCN_NEXTTX(j)) {
1312: tmd = letoh32(sc->sc_txdescs[j].tmd1);
1313: if (tmd & LE_T1_ERR) {
1314: ifp->if_oerrors++;
1315: if (sc->sc_swstyle == LE_B20_SSTYLE_PCNETPCI3)
1316: tmd2 = letoh32(sc->sc_txdescs[j].tmd0);
1317: else
1318: tmd2 = letoh32(sc->sc_txdescs[j].tmd2);
1319: if (tmd2 & LE_T2_UFLO) {
1320: if (sc->sc_xmtsp < LE_C80_XMTSP_MAX) {
1321: sc->sc_xmtsp++;
1322: printf("%s: transmit "
1323: "underrun; new threshold: "
1324: "%s\n",
1325: sc->sc_dev.dv_xname,
1326: sc->sc_xmtsp_desc[
1327: sc->sc_xmtsp]);
1328: pcn_spnd(sc);
1329: pcn_csr_write(sc, LE_CSR80,
1330: LE_C80_RCVFW(sc->sc_rcvfw) |
1331: LE_C80_XMTSP(sc->sc_xmtsp) |
1332: LE_C80_XMTFW(sc->sc_xmtfw));
1333: pcn_csr_write(sc, LE_CSR5,
1334: sc->sc_csr5);
1335: } else {
1336: printf("%s: transmit "
1337: "underrun\n",
1338: sc->sc_dev.dv_xname);
1339: }
1340: } else if (tmd2 & LE_T2_BUFF) {
1341: printf("%s: transmit buffer error\n",
1342: sc->sc_dev.dv_xname);
1343: }
1344: if (tmd2 & LE_T2_LCOL)
1345: ifp->if_collisions++;
1346: if (tmd2 & LE_T2_RTRY)
1347: ifp->if_collisions += 16;
1348: goto next_packet;
1349: }
1350: if (j == txs->txs_lastdesc)
1351: break;
1352: }
1353: if (tmd1 & LE_T1_ONE)
1354: ifp->if_collisions++;
1355: else if (tmd & LE_T1_MORE) {
1356: /* Real number is unknown. */
1357: ifp->if_collisions += 2;
1358: }
1359: ifp->if_opackets++;
1360: next_packet:
1361: sc->sc_txfree += txs->txs_dmamap->dm_nsegs;
1362: bus_dmamap_sync(sc->sc_dmat, txs->txs_dmamap,
1363: 0, txs->txs_dmamap->dm_mapsize, BUS_DMASYNC_POSTWRITE);
1364: bus_dmamap_unload(sc->sc_dmat, txs->txs_dmamap);
1365: m_freem(txs->txs_mbuf);
1366: txs->txs_mbuf = NULL;
1367: }
1368:
1369: /* Update the dirty transmit buffer pointer. */
1370: sc->sc_txsdirty = i;
1371:
1372: /*
1373: * If there are no more pending transmissions, cancel the watchdog
1374: * timer.
1375: */
1376: if (sc->sc_txsfree == PCN_TXQUEUELEN)
1377: ifp->if_timer = 0;
1378: }
1379:
1380: /*
1381: * pcn_rxintr:
1382: *
1383: * Helper; handle receive interrupts.
1384: */
1385: int
1386: pcn_rxintr(struct pcn_softc *sc)
1387: {
1388: struct ifnet *ifp = &sc->sc_arpcom.ac_if;
1389: struct pcn_rxsoft *rxs;
1390: struct mbuf *m;
1391: uint32_t rmd1;
1392: int i, len;
1393:
1394: for (i = sc->sc_rxptr;; i = PCN_NEXTRX(i)) {
1395: rxs = &sc->sc_rxsoft[i];
1396:
1397: PCN_CDRXSYNC(sc, i, BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE);
1398:
1399: rmd1 = letoh32(sc->sc_rxdescs[i].rmd1);
1400:
1401: if (rmd1 & LE_R1_OWN)
1402: break;
1403:
1404: /*
1405: * Check for errors and make sure the packet fit into
1406: * a single buffer. We have structured this block of
1407: * code the way it is in order to compress it into
1408: * one test in the common case (no error).
1409: */
1410: if (__predict_false((rmd1 & (LE_R1_STP|LE_R1_ENP|LE_R1_ERR)) !=
1411: (LE_R1_STP|LE_R1_ENP))) {
1412: /* Make sure the packet is in a single buffer. */
1413: if ((rmd1 & (LE_R1_STP|LE_R1_ENP)) !=
1414: (LE_R1_STP|LE_R1_ENP)) {
1415: printf("%s: packet spilled into next buffer\n",
1416: sc->sc_dev.dv_xname);
1417: return (1); /* pcn_intr() will re-init */
1418: }
1419:
1420: /*
1421: * If the packet had an error, simple recycle the
1422: * buffer.
1423: */
1424: if (rmd1 & LE_R1_ERR) {
1425: ifp->if_ierrors++;
1426: /*
1427: * If we got an overflow error, chances
1428: * are there will be a CRC error. In
1429: * this case, just print the overflow
1430: * error, and skip the others.
1431: */
1432: if (rmd1 & LE_R1_OFLO)
1433: printf("%s: overflow error\n",
1434: sc->sc_dev.dv_xname);
1435: else {
1436: #define PRINTIT(x, str) \
1437: if (rmd1 & (x)) \
1438: printf("%s: %s\n", \
1439: sc->sc_dev.dv_xname, str);
1440: PRINTIT(LE_R1_FRAM, "framing error");
1441: PRINTIT(LE_R1_CRC, "CRC error");
1442: PRINTIT(LE_R1_BUFF, "buffer error");
1443: }
1444: #undef PRINTIT
1445: PCN_INIT_RXDESC(sc, i);
1446: continue;
1447: }
1448: }
1449:
1450: bus_dmamap_sync(sc->sc_dmat, rxs->rxs_dmamap, 0,
1451: rxs->rxs_dmamap->dm_mapsize, BUS_DMASYNC_POSTREAD);
1452:
1453: /*
1454: * No errors; receive the packet.
1455: */
1456: if (sc->sc_swstyle == LE_B20_SSTYLE_PCNETPCI3)
1457: len = letoh32(sc->sc_rxdescs[i].rmd0) & LE_R1_BCNT_MASK;
1458: else
1459: len = letoh32(sc->sc_rxdescs[i].rmd2) & LE_R1_BCNT_MASK;
1460:
1461: /*
1462: * The LANCE family includes the CRC with every packet;
1463: * trim it off here.
1464: */
1465: len -= ETHER_CRC_LEN;
1466:
1467: /*
1468: * If the packet is small enough to fit in a
1469: * single header mbuf, allocate one and copy
1470: * the data into it. This greatly reduces
1471: * memory consumption when we receive lots
1472: * of small packets.
1473: *
1474: * Otherwise, we add a new buffer to the receive
1475: * chain. If this fails, we drop the packet and
1476: * recycle the old buffer.
1477: */
1478: if (pcn_copy_small != 0 && len <= (MHLEN - 2)) {
1479: MGETHDR(m, M_DONTWAIT, MT_DATA);
1480: if (m == NULL)
1481: goto dropit;
1482: m->m_data += 2;
1483: memcpy(mtod(m, caddr_t),
1484: mtod(rxs->rxs_mbuf, caddr_t), len);
1485: PCN_INIT_RXDESC(sc, i);
1486: bus_dmamap_sync(sc->sc_dmat, rxs->rxs_dmamap, 0,
1487: rxs->rxs_dmamap->dm_mapsize,
1488: BUS_DMASYNC_PREREAD);
1489: } else {
1490: m = rxs->rxs_mbuf;
1491: if (pcn_add_rxbuf(sc, i) != 0) {
1492: dropit:
1493: ifp->if_ierrors++;
1494: PCN_INIT_RXDESC(sc, i);
1495: bus_dmamap_sync(sc->sc_dmat,
1496: rxs->rxs_dmamap, 0,
1497: rxs->rxs_dmamap->dm_mapsize,
1498: BUS_DMASYNC_PREREAD);
1499: continue;
1500: }
1501: }
1502:
1503: m->m_pkthdr.rcvif = ifp;
1504: m->m_pkthdr.len = m->m_len = len;
1505:
1506: #if NBPFILTER > 0
1507: /* Pass this up to any BPF listeners. */
1508: if (ifp->if_bpf)
1509: bpf_mtap(ifp->if_bpf, m, BPF_DIRECTION_IN);
1510: #endif /* NBPFILTER > 0 */
1511:
1512: /* Pass it on. */
1513: ether_input_mbuf(ifp, m);
1514: ifp->if_ipackets++;
1515: }
1516:
1517: /* Update the receive pointer. */
1518: sc->sc_rxptr = i;
1519: return (0);
1520: }
1521:
1522: /*
1523: * pcn_tick:
1524: *
1525: * One second timer, used to tick the MII.
1526: */
1527: void
1528: pcn_tick(void *arg)
1529: {
1530: struct pcn_softc *sc = arg;
1531: int s;
1532:
1533: s = splnet();
1534: mii_tick(&sc->sc_mii);
1535: splx(s);
1536:
1537: timeout_add(&sc->sc_tick_timeout, hz);
1538: }
1539:
1540: /*
1541: * pcn_reset:
1542: *
1543: * Perform a soft reset on the PCnet-PCI.
1544: */
1545: void
1546: pcn_reset(struct pcn_softc *sc)
1547: {
1548:
1549: /*
1550: * The PCnet-PCI chip is reset by reading from the
1551: * RESET register. Note that while the NE2100 LANCE
1552: * boards require a write after the read, the PCnet-PCI
1553: * chips do not require this.
1554: *
1555: * Since we don't know if we're in 16-bit or 32-bit
1556: * mode right now, issue both (it's safe) in the
1557: * hopes that one will succeed.
1558: */
1559: (void) bus_space_read_2(sc->sc_st, sc->sc_sh, PCN16_RESET);
1560: (void) bus_space_read_4(sc->sc_st, sc->sc_sh, PCN32_RESET);
1561:
1562: /* Wait 1ms for it to finish. */
1563: delay(1000);
1564:
1565: /*
1566: * Select 32-bit I/O mode by issuing a 32-bit write to the
1567: * RDP. Since the RAP is 0 after a reset, writing a 0
1568: * to RDP is safe (since it simply clears CSR0).
1569: */
1570: bus_space_write_4(sc->sc_st, sc->sc_sh, PCN32_RDP, 0);
1571: }
1572:
1573: /*
1574: * pcn_init: [ifnet interface function]
1575: *
1576: * Initialize the interface. Must be called at splnet().
1577: */
1578: int
1579: pcn_init(struct ifnet *ifp)
1580: {
1581: struct pcn_softc *sc = ifp->if_softc;
1582: struct pcn_rxsoft *rxs;
1583: uint8_t *enaddr = LLADDR(ifp->if_sadl);
1584: int i, error = 0;
1585: uint32_t reg;
1586:
1587: /* Cancel any pending I/O. */
1588: pcn_stop(ifp, 0);
1589:
1590: /* Reset the chip to a known state. */
1591: pcn_reset(sc);
1592:
1593: /*
1594: * On the Am79c970, select SSTYLE 2, and SSTYLE 3 on everything
1595: * else.
1596: *
1597: * XXX It'd be really nice to use SSTYLE 2 on all the chips,
1598: * because the structure layout is compatible with ILACC,
1599: * but the burst mode is only available in SSTYLE 3, and
1600: * burst mode should provide some performance enhancement.
1601: */
1602: if (sc->sc_variant->pcv_chipid == PARTID_Am79c970)
1603: sc->sc_swstyle = LE_B20_SSTYLE_PCNETPCI2;
1604: else
1605: sc->sc_swstyle = LE_B20_SSTYLE_PCNETPCI3;
1606: pcn_bcr_write(sc, LE_BCR20, sc->sc_swstyle);
1607:
1608: /* Initialize the transmit descriptor ring. */
1609: memset(sc->sc_txdescs, 0, sizeof(sc->sc_txdescs));
1610: PCN_CDTXSYNC(sc, 0, PCN_NTXDESC,
1611: BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE);
1612: sc->sc_txfree = PCN_NTXDESC;
1613: sc->sc_txnext = 0;
1614:
1615: /* Initialize the transmit job descriptors. */
1616: for (i = 0; i < PCN_TXQUEUELEN; i++)
1617: sc->sc_txsoft[i].txs_mbuf = NULL;
1618: sc->sc_txsfree = PCN_TXQUEUELEN;
1619: sc->sc_txsnext = 0;
1620: sc->sc_txsdirty = 0;
1621:
1622: /*
1623: * Initialize the receive descriptor and receive job
1624: * descriptor rings.
1625: */
1626: for (i = 0; i < PCN_NRXDESC; i++) {
1627: rxs = &sc->sc_rxsoft[i];
1628: if (rxs->rxs_mbuf == NULL) {
1629: if ((error = pcn_add_rxbuf(sc, i)) != 0) {
1630: printf("%s: unable to allocate or map rx "
1631: "buffer %d, error = %d\n",
1632: sc->sc_dev.dv_xname, i, error);
1633: /*
1634: * XXX Should attempt to run with fewer receive
1635: * XXX buffers instead of just failing.
1636: */
1637: pcn_rxdrain(sc);
1638: goto out;
1639: }
1640: } else
1641: PCN_INIT_RXDESC(sc, i);
1642: }
1643: sc->sc_rxptr = 0;
1644:
1645: /* Initialize MODE for the initialization block. */
1646: sc->sc_mode = 0;
1647: if (ifp->if_flags & IFF_PROMISC)
1648: sc->sc_mode |= LE_C15_PROM;
1649: if ((ifp->if_flags & IFF_BROADCAST) == 0)
1650: sc->sc_mode |= LE_C15_DRCVBC;
1651:
1652: /*
1653: * If we have MII, simply select MII in the MODE register,
1654: * and clear ASEL. Otherwise, let ASEL stand (for now),
1655: * and leave PORTSEL alone (it is ignored with ASEL is set).
1656: */
1657: if (sc->sc_flags & PCN_F_HAS_MII) {
1658: pcn_bcr_write(sc, LE_BCR2,
1659: pcn_bcr_read(sc, LE_BCR2) & ~LE_B2_ASEL);
1660: sc->sc_mode |= LE_C15_PORTSEL(PORTSEL_MII);
1661:
1662: /*
1663: * Disable MII auto-negotiation. We handle that in
1664: * our own MII layer.
1665: */
1666: pcn_bcr_write(sc, LE_BCR32,
1667: pcn_bcr_read(sc, LE_BCR32) | LE_B32_DANAS);
1668: }
1669:
1670: /*
1671: * Set the Tx and Rx descriptor ring addresses in the init
1672: * block, the TLEN and RLEN other fields of the init block
1673: * MODE register.
1674: */
1675: sc->sc_initblock.init_rdra = htole32(PCN_CDRXADDR(sc, 0));
1676: sc->sc_initblock.init_tdra = htole32(PCN_CDTXADDR(sc, 0));
1677: sc->sc_initblock.init_mode = htole32(sc->sc_mode |
1678: ((ffs(PCN_NTXDESC) - 1) << 28) |
1679: ((ffs(PCN_NRXDESC) - 1) << 20));
1680:
1681: /* Set the station address in the init block. */
1682: sc->sc_initblock.init_padr[0] = htole32(enaddr[0] |
1683: (enaddr[1] << 8) | (enaddr[2] << 16) | (enaddr[3] << 24));
1684: sc->sc_initblock.init_padr[1] = htole32(enaddr[4] |
1685: (enaddr[5] << 8));
1686:
1687: /* Set the multicast filter in the init block. */
1688: pcn_set_filter(sc);
1689:
1690: /* Initialize CSR3. */
1691: pcn_csr_write(sc, LE_CSR3, LE_C3_MISSM|LE_C3_IDONM|LE_C3_DXSUFLO);
1692:
1693: /* Initialize CSR4. */
1694: pcn_csr_write(sc, LE_CSR4, LE_C4_DMAPLUS|LE_C4_APAD_XMT|
1695: LE_C4_MFCOM|LE_C4_RCVCCOM|LE_C4_TXSTRTM);
1696:
1697: /* Initialize CSR5. */
1698: sc->sc_csr5 = LE_C5_LTINTEN|LE_C5_SINTE;
1699: pcn_csr_write(sc, LE_CSR5, sc->sc_csr5);
1700:
1701: /*
1702: * If we have an Am79c971 or greater, initialize CSR7.
1703: *
1704: * XXX Might be nice to use the MII auto-poll interrupt someday.
1705: */
1706: switch (sc->sc_variant->pcv_chipid) {
1707: case PARTID_Am79c970:
1708: case PARTID_Am79c970A:
1709: /* Not available on these chips. */
1710: break;
1711:
1712: default:
1713: pcn_csr_write(sc, LE_CSR7, LE_C7_FASTSPNDE);
1714: break;
1715: }
1716:
1717: /*
1718: * On the Am79c970A and greater, initialize BCR18 to
1719: * enable burst mode.
1720: *
1721: * Also enable the "no underflow" option on the Am79c971 and
1722: * higher, which prevents the chip from generating transmit
1723: * underflows, yet sill provides decent performance. Note if
1724: * chip is not connected to external SRAM, then we still have
1725: * to handle underflow errors (the NOUFLO bit is ignored in
1726: * that case).
1727: */
1728: reg = pcn_bcr_read(sc, LE_BCR18);
1729: switch (sc->sc_variant->pcv_chipid) {
1730: case PARTID_Am79c970:
1731: break;
1732:
1733: case PARTID_Am79c970A:
1734: reg |= LE_B18_BREADE|LE_B18_BWRITE;
1735: break;
1736:
1737: default:
1738: reg |= LE_B18_BREADE|LE_B18_BWRITE|LE_B18_NOUFLO;
1739: break;
1740: }
1741: pcn_bcr_write(sc, LE_BCR18, reg);
1742:
1743: /*
1744: * Initialize CSR80 (FIFO thresholds for Tx and Rx).
1745: */
1746: pcn_csr_write(sc, LE_CSR80, LE_C80_RCVFW(sc->sc_rcvfw) |
1747: LE_C80_XMTSP(sc->sc_xmtsp) | LE_C80_XMTFW(sc->sc_xmtfw));
1748:
1749: /*
1750: * Send the init block to the chip, and wait for it
1751: * to be processed.
1752: */
1753: PCN_CDINITSYNC(sc, BUS_DMASYNC_PREWRITE);
1754: pcn_csr_write(sc, LE_CSR1, PCN_CDINITADDR(sc) & 0xffff);
1755: pcn_csr_write(sc, LE_CSR2, (PCN_CDINITADDR(sc) >> 16) & 0xffff);
1756: pcn_csr_write(sc, LE_CSR0, LE_C0_INIT);
1757: delay(100);
1758: for (i = 0; i < 10000; i++) {
1759: if (pcn_csr_read(sc, LE_CSR0) & LE_C0_IDON)
1760: break;
1761: delay(10);
1762: }
1763: PCN_CDINITSYNC(sc, BUS_DMASYNC_POSTWRITE);
1764: if (i == 10000) {
1765: printf("%s: timeout processing init block\n",
1766: sc->sc_dev.dv_xname);
1767: error = EIO;
1768: goto out;
1769: }
1770:
1771: /* Set the media. */
1772: (void) (*sc->sc_mii.mii_media.ifm_change)(ifp);
1773:
1774: /* Enable interrupts and external activity (and ACK IDON). */
1775: pcn_csr_write(sc, LE_CSR0, LE_C0_INEA|LE_C0_STRT|LE_C0_IDON);
1776:
1777: if (sc->sc_flags & PCN_F_HAS_MII) {
1778: /* Start the one second MII clock. */
1779: timeout_add(&sc->sc_tick_timeout, hz);
1780: }
1781:
1782: /* ...all done! */
1783: ifp->if_flags |= IFF_RUNNING;
1784: ifp->if_flags &= ~IFF_OACTIVE;
1785:
1786: out:
1787: if (error)
1788: printf("%s: interface not running\n", sc->sc_dev.dv_xname);
1789: return (error);
1790: }
1791:
1792: /*
1793: * pcn_rxdrain:
1794: *
1795: * Drain the receive queue.
1796: */
1797: void
1798: pcn_rxdrain(struct pcn_softc *sc)
1799: {
1800: struct pcn_rxsoft *rxs;
1801: int i;
1802:
1803: for (i = 0; i < PCN_NRXDESC; i++) {
1804: rxs = &sc->sc_rxsoft[i];
1805: if (rxs->rxs_mbuf != NULL) {
1806: bus_dmamap_unload(sc->sc_dmat, rxs->rxs_dmamap);
1807: m_freem(rxs->rxs_mbuf);
1808: rxs->rxs_mbuf = NULL;
1809: }
1810: }
1811: }
1812:
1813: /*
1814: * pcn_stop: [ifnet interface function]
1815: *
1816: * Stop transmission on the interface.
1817: */
1818: void
1819: pcn_stop(struct ifnet *ifp, int disable)
1820: {
1821: struct pcn_softc *sc = ifp->if_softc;
1822: struct pcn_txsoft *txs;
1823: int i;
1824:
1825: if (sc->sc_flags & PCN_F_HAS_MII) {
1826: /* Stop the one second clock. */
1827: timeout_del(&sc->sc_tick_timeout);
1828:
1829: /* Down the MII. */
1830: mii_down(&sc->sc_mii);
1831: }
1832:
1833: /* Mark the interface as down and cancel the watchdog timer. */
1834: ifp->if_flags &= ~(IFF_RUNNING | IFF_OACTIVE);
1835: ifp->if_timer = 0;
1836:
1837: /* Stop the chip. */
1838: pcn_csr_write(sc, LE_CSR0, LE_C0_STOP);
1839:
1840: /* Release any queued transmit buffers. */
1841: for (i = 0; i < PCN_TXQUEUELEN; i++) {
1842: txs = &sc->sc_txsoft[i];
1843: if (txs->txs_mbuf != NULL) {
1844: bus_dmamap_unload(sc->sc_dmat, txs->txs_dmamap);
1845: m_freem(txs->txs_mbuf);
1846: txs->txs_mbuf = NULL;
1847: }
1848: }
1849:
1850: if (disable)
1851: pcn_rxdrain(sc);
1852: }
1853:
1854: /*
1855: * pcn_add_rxbuf:
1856: *
1857: * Add a receive buffer to the indicated descriptor.
1858: */
1859: int
1860: pcn_add_rxbuf(struct pcn_softc *sc, int idx)
1861: {
1862: struct pcn_rxsoft *rxs = &sc->sc_rxsoft[idx];
1863: struct mbuf *m;
1864: int error;
1865:
1866: MGETHDR(m, M_DONTWAIT, MT_DATA);
1867: if (m == NULL)
1868: return (ENOBUFS);
1869:
1870: MCLGET(m, M_DONTWAIT);
1871: if ((m->m_flags & M_EXT) == 0) {
1872: m_freem(m);
1873: return (ENOBUFS);
1874: }
1875:
1876: if (rxs->rxs_mbuf != NULL)
1877: bus_dmamap_unload(sc->sc_dmat, rxs->rxs_dmamap);
1878:
1879: rxs->rxs_mbuf = m;
1880:
1881: error = bus_dmamap_load(sc->sc_dmat, rxs->rxs_dmamap,
1882: m->m_ext.ext_buf, m->m_ext.ext_size, NULL,
1883: BUS_DMA_READ|BUS_DMA_NOWAIT);
1884: if (error) {
1885: printf("%s: can't load rx DMA map %d, error = %d\n",
1886: sc->sc_dev.dv_xname, idx, error);
1887: panic("pcn_add_rxbuf");
1888: }
1889:
1890: bus_dmamap_sync(sc->sc_dmat, rxs->rxs_dmamap, 0,
1891: rxs->rxs_dmamap->dm_mapsize, BUS_DMASYNC_PREREAD);
1892:
1893: PCN_INIT_RXDESC(sc, idx);
1894:
1895: return (0);
1896: }
1897:
1898: /*
1899: * pcn_set_filter:
1900: *
1901: * Set up the receive filter.
1902: */
1903: void
1904: pcn_set_filter(struct pcn_softc *sc)
1905: {
1906: struct arpcom *ac = &sc->sc_arpcom;
1907: struct ifnet *ifp = &sc->sc_arpcom.ac_if;
1908: struct ether_multi *enm;
1909: struct ether_multistep step;
1910: uint32_t crc;
1911:
1912: /*
1913: * Set up the multicast address filter by passing all multicast
1914: * addresses through a CRC generator, and then using the high
1915: * order 6 bits as an index into the 64-bit logical address
1916: * filter. The high order bits select the word, while the rest
1917: * of the bits select the bit within the word.
1918: */
1919:
1920: if (ifp->if_flags & IFF_ALLMULTI || ifp->if_flags & IFF_PROMISC)
1921: goto allmulti;
1922:
1923: sc->sc_initblock.init_ladrf[0] =
1924: sc->sc_initblock.init_ladrf[1] =
1925: sc->sc_initblock.init_ladrf[2] =
1926: sc->sc_initblock.init_ladrf[3] = 0;
1927:
1928: ETHER_FIRST_MULTI(step, ac, enm);
1929: while (enm != NULL) {
1930: if (memcmp(enm->enm_addrlo, enm->enm_addrhi, ETHER_ADDR_LEN)) {
1931: /*
1932: * We must listen to a range of multicast addresses.
1933: * For now, just accept all multicasts, rather than
1934: * trying to set only those filter bits needed to match
1935: * the range. (At this time, the only use of address
1936: * ranges is for IP multicast routing, for which the
1937: * range is big enough to require all bits set.)
1938: */
1939: goto allmulti;
1940: }
1941:
1942: crc = ether_crc32_le(enm->enm_addrlo, ETHER_ADDR_LEN);
1943:
1944: /* Just want the 6 most significant bits. */
1945: crc >>= 26;
1946:
1947: /* Set the corresponding bit in the filter. */
1948: sc->sc_initblock.init_ladrf[crc >> 4] |=
1949: htole16(1 << (crc & 0xf));
1950:
1951: ETHER_NEXT_MULTI(step, enm);
1952: }
1953:
1954: ifp->if_flags &= ~IFF_ALLMULTI;
1955: return;
1956:
1957: allmulti:
1958: ifp->if_flags |= IFF_ALLMULTI;
1959: sc->sc_initblock.init_ladrf[0] =
1960: sc->sc_initblock.init_ladrf[1] =
1961: sc->sc_initblock.init_ladrf[2] =
1962: sc->sc_initblock.init_ladrf[3] = 0xffff;
1963: }
1964:
1965: /*
1966: * pcn_79c970_mediainit:
1967: *
1968: * Initialize media for the Am79c970.
1969: */
1970: void
1971: pcn_79c970_mediainit(struct pcn_softc *sc)
1972: {
1973: ifmedia_init(&sc->sc_mii.mii_media, IFM_IMASK, pcn_79c970_mediachange,
1974: pcn_79c970_mediastatus);
1975:
1976: ifmedia_add(&sc->sc_mii.mii_media, IFM_ETHER|IFM_10_5,
1977: PORTSEL_AUI, NULL);
1978: if (sc->sc_variant->pcv_chipid == PARTID_Am79c970A)
1979: ifmedia_add(&sc->sc_mii.mii_media, IFM_ETHER|IFM_10_5|IFM_FDX,
1980: PORTSEL_AUI, NULL);
1981:
1982: ifmedia_add(&sc->sc_mii.mii_media, IFM_ETHER|IFM_10_T,
1983: PORTSEL_10T, NULL);
1984: if (sc->sc_variant->pcv_chipid == PARTID_Am79c970A)
1985: ifmedia_add(&sc->sc_mii.mii_media, IFM_ETHER|IFM_10_T|IFM_FDX,
1986: PORTSEL_10T, NULL);
1987:
1988: ifmedia_add(&sc->sc_mii.mii_media, IFM_ETHER|IFM_AUTO,
1989: 0, NULL);
1990: if (sc->sc_variant->pcv_chipid == PARTID_Am79c970A)
1991: ifmedia_add(&sc->sc_mii.mii_media, IFM_ETHER|IFM_AUTO|IFM_FDX,
1992: 0, NULL);
1993:
1994: ifmedia_set(&sc->sc_mii.mii_media, IFM_ETHER|IFM_AUTO);
1995: }
1996:
1997: /*
1998: * pcn_79c970_mediastatus: [ifmedia interface function]
1999: *
2000: * Get the current interface media status (Am79c970 version).
2001: */
2002: void
2003: pcn_79c970_mediastatus(struct ifnet *ifp, struct ifmediareq *ifmr)
2004: {
2005: struct pcn_softc *sc = ifp->if_softc;
2006:
2007: /*
2008: * The currently selected media is always the active media.
2009: * Note: We have no way to determine what media the AUTO
2010: * process picked.
2011: */
2012: ifmr->ifm_active = sc->sc_mii.mii_media.ifm_media;
2013: }
2014:
2015: /*
2016: * pcn_79c970_mediachange: [ifmedia interface function]
2017: *
2018: * Set hardware to newly-selected media (Am79c970 version).
2019: */
2020: int
2021: pcn_79c970_mediachange(struct ifnet *ifp)
2022: {
2023: struct pcn_softc *sc = ifp->if_softc;
2024: uint32_t reg;
2025:
2026: if (IFM_SUBTYPE(sc->sc_mii.mii_media.ifm_media) == IFM_AUTO) {
2027: /*
2028: * CSR15:PORTSEL doesn't matter. Just set BCR2:ASEL.
2029: */
2030: reg = pcn_bcr_read(sc, LE_BCR2);
2031: reg |= LE_B2_ASEL;
2032: pcn_bcr_write(sc, LE_BCR2, reg);
2033: } else {
2034: /*
2035: * Clear BCR2:ASEL and set the new CSR15:PORTSEL value.
2036: */
2037: reg = pcn_bcr_read(sc, LE_BCR2);
2038: reg &= ~LE_B2_ASEL;
2039: pcn_bcr_write(sc, LE_BCR2, reg);
2040:
2041: reg = pcn_csr_read(sc, LE_CSR15);
2042: reg = (reg & ~LE_C15_PORTSEL(PORTSEL_MASK)) |
2043: LE_C15_PORTSEL(sc->sc_mii.mii_media.ifm_cur->ifm_data);
2044: pcn_csr_write(sc, LE_CSR15, reg);
2045: }
2046:
2047: if ((sc->sc_mii.mii_media.ifm_media & IFM_FDX) != 0) {
2048: reg = LE_B9_FDEN;
2049: if (IFM_SUBTYPE(sc->sc_mii.mii_media.ifm_media) == IFM_10_5)
2050: reg |= LE_B9_AUIFD;
2051: pcn_bcr_write(sc, LE_BCR9, reg);
2052: } else
2053: pcn_bcr_write(sc, LE_BCR9, 0);
2054:
2055: return (0);
2056: }
2057:
2058: /*
2059: * pcn_79c971_mediainit:
2060: *
2061: * Initialize media for the Am79c971.
2062: */
2063: void
2064: pcn_79c971_mediainit(struct pcn_softc *sc)
2065: {
2066: struct ifnet *ifp = &sc->sc_arpcom.ac_if;
2067:
2068: /* We have MII. */
2069: sc->sc_flags |= PCN_F_HAS_MII;
2070:
2071: /*
2072: * The built-in 10BASE-T interface is mapped to the MII
2073: * on the PCNet-FAST. Unfortunately, there's no EEPROM
2074: * word that tells us which PHY to use.
2075: * This driver used to ignore all but the first PHY to
2076: * answer, but this code was removed to support multiple
2077: * external PHYs. As the default instance will be the first
2078: * one to answer, no harm is done by letting the possibly
2079: * non-connected internal PHY show up.
2080: */
2081:
2082: /* Initialize our media structures and probe the MII. */
2083: sc->sc_mii.mii_ifp = ifp;
2084: sc->sc_mii.mii_readreg = pcn_mii_readreg;
2085: sc->sc_mii.mii_writereg = pcn_mii_writereg;
2086: sc->sc_mii.mii_statchg = pcn_mii_statchg;
2087: ifmedia_init(&sc->sc_mii.mii_media, 0, pcn_79c971_mediachange,
2088: pcn_79c971_mediastatus);
2089:
2090: mii_attach(&sc->sc_dev, &sc->sc_mii, 0xffffffff, MII_PHY_ANY,
2091: MII_OFFSET_ANY, 0);
2092: if (LIST_FIRST(&sc->sc_mii.mii_phys) == NULL) {
2093: ifmedia_add(&sc->sc_mii.mii_media, IFM_ETHER|IFM_NONE, 0, NULL);
2094: ifmedia_set(&sc->sc_mii.mii_media, IFM_ETHER|IFM_NONE);
2095: } else
2096: ifmedia_set(&sc->sc_mii.mii_media, IFM_ETHER|IFM_AUTO);
2097: }
2098:
2099: /*
2100: * pcn_79c971_mediastatus: [ifmedia interface function]
2101: *
2102: * Get the current interface media status (Am79c971 version).
2103: */
2104: void
2105: pcn_79c971_mediastatus(struct ifnet *ifp, struct ifmediareq *ifmr)
2106: {
2107: struct pcn_softc *sc = ifp->if_softc;
2108:
2109: mii_pollstat(&sc->sc_mii);
2110: ifmr->ifm_status = sc->sc_mii.mii_media_status;
2111: ifmr->ifm_active = sc->sc_mii.mii_media_active;
2112: }
2113:
2114: /*
2115: * pcn_79c971_mediachange: [ifmedia interface function]
2116: *
2117: * Set hardware to newly-selected media (Am79c971 version).
2118: */
2119: int
2120: pcn_79c971_mediachange(struct ifnet *ifp)
2121: {
2122: struct pcn_softc *sc = ifp->if_softc;
2123:
2124: if (ifp->if_flags & IFF_UP)
2125: mii_mediachg(&sc->sc_mii);
2126: return (0);
2127: }
2128:
2129: /*
2130: * pcn_mii_readreg: [mii interface function]
2131: *
2132: * Read a PHY register on the MII.
2133: */
2134: int
2135: pcn_mii_readreg(struct device *self, int phy, int reg)
2136: {
2137: struct pcn_softc *sc = (void *) self;
2138: uint32_t rv;
2139:
2140: pcn_bcr_write(sc, LE_BCR33, reg | (phy << PHYAD_SHIFT));
2141: rv = pcn_bcr_read(sc, LE_BCR34) & LE_B34_MIIMD;
2142: if (rv == 0xffff)
2143: return (0);
2144:
2145: return (rv);
2146: }
2147:
2148: /*
2149: * pcn_mii_writereg: [mii interface function]
2150: *
2151: * Write a PHY register on the MII.
2152: */
2153: void
2154: pcn_mii_writereg(struct device *self, int phy, int reg, int val)
2155: {
2156: struct pcn_softc *sc = (void *) self;
2157:
2158: pcn_bcr_write(sc, LE_BCR33, reg | (phy << PHYAD_SHIFT));
2159: pcn_bcr_write(sc, LE_BCR34, val);
2160: }
2161:
2162: /*
2163: * pcn_mii_statchg: [mii interface function]
2164: *
2165: * Callback from MII layer when media changes.
2166: */
2167: void
2168: pcn_mii_statchg(struct device *self)
2169: {
2170: struct pcn_softc *sc = (void *) self;
2171:
2172: if ((sc->sc_mii.mii_media_active & IFM_FDX) != 0)
2173: pcn_bcr_write(sc, LE_BCR9, LE_B9_FDEN);
2174: else
2175: pcn_bcr_write(sc, LE_BCR9, 0);
2176: }
CVSweb