root/dev/sbus/be.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. bematch
  2. beattach
  3. be_put
  4. be_get
  5. be_read
  6. bestart
  7. bestop
  8. bereset
  9. bewatchdog
  10. beintr
  11. beqint
  12. beeint
  13. betint
  14. berint
  15. beioctl
  16. beinit
  17. be_mcreset
  18. be_mii_sync
  19. be_pal_gate
  20. be_tcvr_read_bit
  21. be_tcvr_write_bit
  22. be_mii_sendbits
  23. be_mii_readreg
  24. be_mii_writereg
  25. be_mii_reset
  26. be_tick
  27. be_mii_statchg
  28. be_ifmedia_sts
  29. be_ifmedia_upd
  30. be_intphy_service
  31. be_intphy_status

    1 /*      $OpenBSD: be.c,v 1.19 2006/06/02 20:00:56 miod Exp $    */
    2 /*      $NetBSD: be.c,v 1.26 2001/03/20 15:39:20 pk Exp $       */
    3 
    4 /*-
    5  * Copyright (c) 1999 The NetBSD Foundation, Inc.
    6  * All rights reserved.
    7  *
    8  * This code is derived from software contributed to The NetBSD Foundation
    9  * by Paul Kranenburg.
   10  *
   11  * Redistribution and use in source and binary forms, with or without
   12  * modification, are permitted provided that the following conditions
   13  * are met:
   14  * 1. Redistributions of source code must retain the above copyright
   15  *    notice, this list of conditions and the following disclaimer.
   16  * 2. Redistributions in binary form must reproduce the above copyright
   17  *    notice, this list of conditions and the following disclaimer in the
   18  *    documentation and/or other materials provided with the distribution.
   19  * 3. All advertising materials mentioning features or use of this software
   20  *    must display the following acknowledgement:
   21  *        This product includes software developed by the NetBSD
   22  *        Foundation, Inc. and its contributors.
   23  * 4. Neither the name of The NetBSD Foundation nor the names of its
   24  *    contributors may be used to endorse or promote products derived
   25  *    from this software without specific prior written permission.
   26  *
   27  * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
   28  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
   29  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
   30  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
   31  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
   32  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
   33  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
   34  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
   35  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
   36  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
   37  * POSSIBILITY OF SUCH DAMAGE.
   38  */
   39 
   40 /*
   41  * Copyright (c) 1998 Theo de Raadt and Jason L. Wright.
   42  * All rights reserved.
   43  *
   44  * Redistribution and use in source and binary forms, with or without
   45  * modification, are permitted provided that the following conditions
   46  * are met:
   47  * 1. Redistributions of source code must retain the above copyright
   48  *    notice, this list of conditions and the following disclaimer.
   49  * 2. Redistributions in binary form must reproduce the above copyright
   50  *    notice, this list of conditions and the following disclaimer in the
   51  *    documentation and/or other materials provided with the distribution.
   52  *
   53  * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR
   54  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
   55  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
   56  * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT,
   57  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
   58  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
   59  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
   60  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
   61  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
   62  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
   63  */
   64 
   65 #include "bpfilter.h"
   66 
   67 #include <sys/param.h>
   68 #include <sys/systm.h>
   69 #include <sys/timeout.h>
   70 #include <sys/kernel.h>
   71 #include <sys/errno.h>
   72 #include <sys/ioctl.h>
   73 #include <sys/mbuf.h>
   74 #include <sys/socket.h>
   75 #include <sys/syslog.h>
   76 #include <sys/device.h>
   77 #include <sys/malloc.h>
   78 
   79 #include <net/if.h>
   80 #include <net/if_dl.h>
   81 #include <net/if_types.h>
   82 #include <net/netisr.h>
   83 #include <net/if_media.h>
   84 
   85 #ifdef INET
   86 #include <netinet/in.h>
   87 #include <netinet/in_systm.h>
   88 #include <netinet/in_var.h>
   89 #include <netinet/ip.h>
   90 #include <netinet/if_ether.h>
   91 #endif
   92 
   93 #if NBPFILTER > 0
   94 #include <net/bpf.h>
   95 #endif
   96 
   97 #include <machine/bus.h>
   98 #include <machine/intr.h>
   99 #include <machine/autoconf.h>
  100 
  101 #include <dev/sbus/sbusvar.h>
  102 
  103 #include <dev/mii/mii.h>
  104 #include <dev/mii/miivar.h>
  105 
  106 #include <dev/sbus/qecreg.h>
  107 #include <dev/sbus/qecvar.h>
  108 #include <dev/sbus/bereg.h>
  109 
  110 struct be_softc {
  111         struct  device  sc_dev;
  112         bus_space_tag_t sc_bustag;      /* bus & dma tags */
  113         bus_dma_tag_t   sc_dmatag;
  114         bus_dmamap_t    sc_dmamap;
  115         struct  arpcom sc_arpcom;
  116         /*struct        ifmedia sc_ifmedia;     -* interface media */
  117         struct mii_data sc_mii;         /* MII media control */
  118 #define sc_media        sc_mii.mii_media/* shorthand */
  119         int             sc_phys[2];     /* MII instance -> phy */
  120 
  121         struct timeout sc_tick_ch;
  122 
  123         /*
  124          * Some `mii_softc' items we need to emulate MII operation
  125          * for our internal transceiver.
  126          */
  127         int             sc_mii_inst;    /* instance of internal phy */
  128         int             sc_mii_active;  /* currently active medium */
  129         int             sc_mii_ticks;   /* tick counter */
  130         int             sc_mii_flags;   /* phy status flags */
  131 #define MIIF_HAVELINK   0x04000000
  132         int             sc_intphy_curspeed;     /* Established link speed */
  133 
  134         struct  qec_softc *sc_qec;      /* QEC parent */
  135 
  136         bus_space_handle_t      sc_qr;  /* QEC registers */
  137         bus_space_handle_t      sc_br;  /* BE registers */
  138         bus_space_handle_t      sc_cr;  /* channel registers */
  139         bus_space_handle_t      sc_tr;  /* transceiver registers */
  140 
  141         u_int   sc_rev;
  142 
  143         int     sc_channel;             /* channel number */
  144         int     sc_burst;
  145 
  146         struct  qec_ring        sc_rb;  /* Packet Ring Buffer */
  147 };
  148 
  149 int     bematch(struct device *, void *, void *);
  150 void    beattach(struct device *, struct device *, void *);
  151 
  152 void    beinit(struct be_softc *);
  153 void    bestart(struct ifnet *);
  154 void    bestop(struct be_softc *);
  155 void    bewatchdog(struct ifnet *);
  156 int     beioctl(struct ifnet *, u_long, caddr_t);
  157 void    bereset(struct be_softc *);
  158 
  159 int     beintr(void *);
  160 int     berint(struct be_softc *);
  161 int     betint(struct be_softc *);
  162 int     beqint(struct be_softc *, u_int32_t);
  163 int     beeint(struct be_softc *, u_int32_t);
  164 
  165 static void     be_read(struct be_softc *, int, int);
  166 static int      be_put(struct be_softc *, int, struct mbuf *);
  167 static struct mbuf *be_get(struct be_softc *, int, int);
  168 
  169 void    be_pal_gate(struct be_softc *, int);
  170 
  171 /* ifmedia callbacks */
  172 void    be_ifmedia_sts(struct ifnet *, struct ifmediareq *);
  173 int     be_ifmedia_upd(struct ifnet *);
  174 
  175 void    be_mcreset(struct be_softc *);
  176 
  177 /* MII methods & callbacks */
  178 static int      be_mii_readreg(struct device *, int, int);
  179 static void     be_mii_writereg(struct device *, int, int, int);
  180 static void     be_mii_statchg(struct device *);
  181 
  182 /* MII helpers */
  183 static void     be_mii_sync(struct be_softc *);
  184 static void     be_mii_sendbits(struct be_softc *, int, u_int32_t, int);
  185 static int      be_mii_reset(struct be_softc *, int);
  186 static int      be_tcvr_read_bit(struct be_softc *, int);
  187 static void     be_tcvr_write_bit(struct be_softc *, int, int);
  188 
  189 void    be_tick(void *);
  190 void    be_intphy_auto(struct be_softc *);
  191 void    be_intphy_status(struct be_softc *);
  192 int     be_intphy_service(struct be_softc *, struct mii_data *, int);
  193 
  194 
  195 struct cfattach be_ca = {
  196         sizeof(struct be_softc), bematch, beattach
  197 };
  198 
  199 struct cfdriver be_cd = {
  200         NULL, "be", DV_IFNET
  201 };
  202 
  203 int
  204 bematch(struct device *parent, void *vcf, void *aux)
  205 {
  206         struct cfdata *cf = vcf;
  207         struct sbus_attach_args *sa = aux;
  208 
  209         return (strcmp(cf->cf_driver->cd_name, sa->sa_name) == 0);
  210 }
  211 
  212 void
  213 beattach(struct device *parent, struct device *self, void *aux)
  214 {
  215         struct sbus_attach_args *sa = aux;
  216         struct qec_softc *qec = (struct qec_softc *)parent;
  217         struct be_softc *sc = (struct be_softc *)self;
  218         struct ifnet *ifp = &sc->sc_arpcom.ac_if;
  219         struct mii_data *mii = &sc->sc_mii;
  220         struct mii_softc *child;
  221         int node = sa->sa_node;
  222         bus_dma_tag_t dmatag = sa->sa_dmatag;
  223         bus_dma_segment_t seg;
  224         bus_size_t size;
  225         int instance;
  226         int rseg, error;
  227         u_int32_t v;
  228         extern void myetheraddr(u_char *);
  229 
  230         /* Pass on the bus tags */
  231         sc->sc_bustag = sa->sa_bustag;
  232         sc->sc_dmatag = sa->sa_dmatag;
  233 
  234         if (sa->sa_nreg < 3) {
  235                 printf("%s: only %d register sets\n",
  236                     self->dv_xname, sa->sa_nreg);
  237                 return;
  238         }
  239 
  240         if (sbus_bus_map(sa->sa_bustag, sa->sa_reg[0].sbr_slot,
  241             (bus_addr_t)sa->sa_reg[0].sbr_offset,
  242             (bus_size_t)sa->sa_reg[0].sbr_size, 0, 0, &sc->sc_cr) != 0) {
  243                 printf("beattach: cannot map registers\n");
  244                 return;
  245         }
  246 
  247         if (sbus_bus_map(sa->sa_bustag, sa->sa_reg[1].sbr_slot,
  248             (bus_addr_t)sa->sa_reg[1].sbr_offset,
  249             (bus_size_t)sa->sa_reg[1].sbr_size, 0, 0, &sc->sc_br) != 0) {
  250                 printf("beattach: cannot map registers\n");
  251                 return;
  252         }
  253 
  254         if (sbus_bus_map(sa->sa_bustag, sa->sa_reg[2].sbr_slot,
  255             (bus_addr_t)sa->sa_reg[2].sbr_offset,
  256             (bus_size_t)sa->sa_reg[2].sbr_size, 0, 0, &sc->sc_tr) != 0) {
  257                 printf("beattach: cannot map registers\n");
  258                 return;
  259         }
  260 
  261         sc->sc_qec = qec;
  262         sc->sc_qr = qec->sc_regs;
  263 
  264         sc->sc_rev = getpropint(node, "board-version", -1);
  265         printf(" rev %x", sc->sc_rev);
  266 
  267         bestop(sc);
  268 
  269         sc->sc_channel = getpropint(node, "channel#", -1);
  270         if (sc->sc_channel == -1)
  271                 sc->sc_channel = 0;
  272 
  273         sc->sc_burst = getpropint(node, "burst-sizes", -1);
  274         if (sc->sc_burst == -1)
  275                 sc->sc_burst = qec->sc_burst;
  276 
  277         /* Clamp at parent's burst sizes */
  278         sc->sc_burst &= qec->sc_burst;
  279 
  280         /* Establish interrupt handler */
  281         if (sa->sa_nintr == 0 || bus_intr_establish(sa->sa_bustag, sa->sa_pri,
  282             IPL_NET, 0, beintr, sc, self->dv_xname) == NULL) {
  283                 printf(": no interrupt established\n");
  284                 return;
  285         }
  286 
  287         myetheraddr(sc->sc_arpcom.ac_enaddr);
  288         printf(" address %s\n", ether_sprintf(sc->sc_arpcom.ac_enaddr));
  289 
  290         /*
  291          * Allocate descriptor ring and buffers.
  292          */
  293 
  294         /* for now, allocate as many bufs as there are ring descriptors */
  295         sc->sc_rb.rb_ntbuf = QEC_XD_RING_MAXSIZE;
  296         sc->sc_rb.rb_nrbuf = QEC_XD_RING_MAXSIZE;
  297 
  298         size =  QEC_XD_RING_MAXSIZE * sizeof(struct qec_xd) +
  299                 QEC_XD_RING_MAXSIZE * sizeof(struct qec_xd) +
  300                 sc->sc_rb.rb_ntbuf * BE_PKT_BUF_SZ +
  301                 sc->sc_rb.rb_nrbuf * BE_PKT_BUF_SZ;
  302 
  303         /* Get a DMA handle */
  304         if ((error = bus_dmamap_create(dmatag, size, 1, size, 0,
  305             BUS_DMA_NOWAIT, &sc->sc_dmamap)) != 0) {
  306                 printf("%s: DMA map create error %d\n", self->dv_xname, error);
  307                 return;
  308         }
  309 
  310         /* Allocate DMA buffer */
  311         if ((error = bus_dmamem_alloc(sa->sa_dmatag, size, 0, 0,
  312             &seg, 1, &rseg, BUS_DMA_NOWAIT)) != 0) {
  313                 printf("%s: DMA buffer alloc error %d\n",
  314                         self->dv_xname, error);
  315                 return;
  316         }
  317 
  318         /* Map DMA memory in CPU addressable space */
  319         if ((error = bus_dmamem_map(sa->sa_dmatag, &seg, rseg, size,
  320             &sc->sc_rb.rb_membase, BUS_DMA_NOWAIT|BUS_DMA_COHERENT)) != 0) {
  321                 printf("%s: DMA buffer map error %d\n",
  322                         self->dv_xname, error);
  323                 bus_dmamem_free(sa->sa_dmatag, &seg, rseg);
  324                 return;
  325         }
  326 
  327         /* Load the buffer */
  328         if ((error = bus_dmamap_load(dmatag, sc->sc_dmamap,
  329             sc->sc_rb.rb_membase, size, NULL, BUS_DMA_NOWAIT)) != 0) {
  330                 printf("%s: DMA buffer map load error %d\n",
  331                     self->dv_xname, error);
  332                 bus_dmamem_unmap(dmatag, sc->sc_rb.rb_membase, size);
  333                 bus_dmamem_free(dmatag, &seg, rseg);
  334                 return;
  335         }
  336         sc->sc_rb.rb_dmabase = sc->sc_dmamap->dm_segs[0].ds_addr;
  337 
  338         /*
  339          * Initialize our media structures and MII info.
  340          */
  341         mii->mii_ifp = ifp;
  342         mii->mii_readreg = be_mii_readreg;
  343         mii->mii_writereg = be_mii_writereg;
  344         mii->mii_statchg = be_mii_statchg;
  345 
  346         ifmedia_init(&mii->mii_media, 0, be_ifmedia_upd, be_ifmedia_sts);
  347 
  348         timeout_set(&sc->sc_tick_ch, be_tick, sc);
  349 
  350         /*
  351          * Initialize transceiver and determine which PHY connection to use.
  352          */
  353         be_mii_sync(sc);
  354         v = bus_space_read_4(sc->sc_bustag, sc->sc_tr, BE_TRI_MGMTPAL);
  355 
  356         instance = 0;
  357 
  358         if ((v & MGMT_PAL_EXT_MDIO) != 0) {
  359 
  360                 mii_attach(&sc->sc_dev, mii, 0xffffffff, BE_PHY_EXTERNAL,
  361                     MII_OFFSET_ANY, 0);
  362 
  363                 child = LIST_FIRST(&mii->mii_phys);
  364                 if (child == NULL) {
  365                         /* No PHY attached */
  366                         ifmedia_add(&sc->sc_media,
  367                             IFM_MAKEWORD(IFM_ETHER,IFM_NONE,0,instance),
  368                             0, NULL);
  369                         ifmedia_set(&sc->sc_media,
  370                             IFM_MAKEWORD(IFM_ETHER,IFM_NONE,0,instance));
  371                 } else {
  372                         /*
  373                          * Note: we support just one PHY on the external
  374                          * MII connector.
  375                          */
  376 #ifdef DIAGNOSTIC
  377                         if (LIST_NEXT(child, mii_list) != NULL) {
  378                                 printf("%s: spurious MII device %s attached\n",
  379                                     sc->sc_dev.dv_xname,
  380                                     child->mii_dev.dv_xname);
  381                         }
  382 #endif
  383                         if (child->mii_phy != BE_PHY_EXTERNAL ||
  384                             child->mii_inst > 0) {
  385                                 printf("%s: cannot accommodate MII device %s"
  386                                     " at phy %d, instance %d\n",
  387                                     sc->sc_dev.dv_xname,
  388                                     child->mii_dev.dv_xname,
  389                                     child->mii_phy, child->mii_inst);
  390                         } else {
  391                                 sc->sc_phys[instance] = child->mii_phy;
  392                         }
  393 
  394                         /*
  395                          * XXX - we can really do the following ONLY if the
  396                          * phy indeed has the auto negotiation capability!!
  397                          */
  398                         ifmedia_set(&sc->sc_media,
  399                             IFM_MAKEWORD(IFM_ETHER,IFM_AUTO,0,instance));
  400 
  401                         /* Mark our current media setting */
  402                         be_pal_gate(sc, BE_PHY_EXTERNAL);
  403                         instance++;
  404                 }
  405 
  406         }
  407 
  408         if ((v & MGMT_PAL_INT_MDIO) != 0) {
  409                 /*
  410                  * The be internal phy looks vaguely like MII hardware,
  411                  * but not enough to be able to use the MII device
  412                  * layer. Hence, we have to take care of media selection
  413                  * ourselves.
  414                  */
  415 
  416                 sc->sc_mii_inst = instance;
  417                 sc->sc_phys[instance] = BE_PHY_INTERNAL;
  418 
  419                 /* Use `ifm_data' to store BMCR bits */
  420                 ifmedia_add(&sc->sc_media,
  421                     IFM_MAKEWORD(IFM_ETHER,IFM_10_T,0,instance), 0, NULL);
  422                 ifmedia_add(&sc->sc_media,
  423                     IFM_MAKEWORD(IFM_ETHER,IFM_100_TX,0,instance),
  424                     BMCR_S100, NULL);
  425                 ifmedia_add(&sc->sc_media,
  426                     IFM_MAKEWORD(IFM_ETHER,IFM_AUTO,0,instance), 0, NULL);
  427 
  428                 printf("on-board transceiver at %s: 10baseT, 100baseTX, auto\n",
  429                     self->dv_xname);
  430 
  431                 be_mii_reset(sc, BE_PHY_INTERNAL);
  432                 /* Only set default medium here if there's no external PHY */
  433                 if (instance == 0) {
  434                         be_pal_gate(sc, BE_PHY_INTERNAL);
  435                         ifmedia_set(&sc->sc_media,
  436                             IFM_MAKEWORD(IFM_ETHER,IFM_AUTO,0,instance));
  437                 } else
  438                         be_mii_writereg((void *)sc,
  439                             BE_PHY_INTERNAL, MII_BMCR, BMCR_ISO);
  440         }
  441 
  442         bcopy(sc->sc_dev.dv_xname, ifp->if_xname, IFNAMSIZ);
  443         ifp->if_softc = sc;
  444         ifp->if_start = bestart;
  445         ifp->if_ioctl = beioctl;
  446         ifp->if_watchdog = bewatchdog;
  447         ifp->if_flags =
  448             IFF_BROADCAST | IFF_SIMPLEX | IFF_NOTRAILERS | IFF_MULTICAST;
  449         IFQ_SET_READY(&ifp->if_snd);
  450 
  451         /* Attach the interface. */
  452         if_attach(ifp);
  453         ether_ifattach(ifp);
  454 }
  455 
  456 
  457 /*
  458  * Routine to copy from mbuf chain to transmit buffer in
  459  * network buffer memory.
  460  */
  461 static __inline__ int
  462 be_put(struct be_softc *sc, int idx, struct mbuf *m)
  463 {
  464         struct mbuf *n;
  465         int len, tlen = 0, boff = 0;
  466         caddr_t bp;
  467 
  468         bp = sc->sc_rb.rb_txbuf + (idx % sc->sc_rb.rb_ntbuf) * BE_PKT_BUF_SZ;
  469 
  470         for (; m; m = n) {
  471                 len = m->m_len;
  472                 if (len == 0) {
  473                         MFREE(m, n);
  474                         continue;
  475                 }
  476                 bcopy(mtod(m, caddr_t), bp+boff, len);
  477                 boff += len;
  478                 tlen += len;
  479                 MFREE(m, n);
  480         }
  481         return (tlen);
  482 }
  483 
  484 /*
  485  * Pull data off an interface.
  486  * Len is the length of data, with local net header stripped.
  487  * We copy the data into mbufs.  When full cluster sized units are present,
  488  * we copy into clusters.
  489  */
  490 static __inline__ struct mbuf *
  491 be_get(struct be_softc *sc, int idx, int totlen)
  492 {
  493         struct ifnet *ifp = &sc->sc_arpcom.ac_if;
  494         struct mbuf *m;
  495         struct mbuf *top, **mp;
  496         int len, pad, boff = 0;
  497         caddr_t bp;
  498 
  499         bp = sc->sc_rb.rb_rxbuf + (idx % sc->sc_rb.rb_nrbuf) * BE_PKT_BUF_SZ;
  500 
  501         MGETHDR(m, M_DONTWAIT, MT_DATA);
  502         if (m == NULL)
  503                 return (NULL);
  504         m->m_pkthdr.rcvif = ifp;
  505         m->m_pkthdr.len = totlen;
  506 
  507         pad = ALIGN(sizeof(struct ether_header)) - sizeof(struct ether_header);
  508         m->m_data += pad;
  509         len = MHLEN - pad;
  510         top = NULL;
  511         mp = &top;
  512 
  513         while (totlen > 0) {
  514                 if (top) {
  515                         MGET(m, M_DONTWAIT, MT_DATA);
  516                         if (m == NULL) {
  517                                 m_freem(top);
  518                                 return (NULL);
  519                         }
  520                         len = MLEN;
  521                 }
  522                 if (top && totlen >= MINCLSIZE) {
  523                         MCLGET(m, M_DONTWAIT);
  524                         if (m->m_flags & M_EXT)
  525                                 len = MCLBYTES;
  526                 }
  527                 m->m_len = len = min(totlen, len);
  528                 bcopy(bp + boff, mtod(m, caddr_t), len);
  529                 boff += len;
  530                 totlen -= len;
  531                 *mp = m;
  532                 mp = &m->m_next;
  533         }
  534 
  535         return (top);
  536 }
  537 
  538 /*
  539  * Pass a packet to the higher levels.
  540  */
  541 static __inline__ void
  542 be_read(struct be_softc *sc, int idx, int len)
  543 {
  544         struct ifnet *ifp = &sc->sc_arpcom.ac_if;
  545         struct mbuf *m;
  546 
  547         if (len <= sizeof(struct ether_header) ||
  548             len > ETHERMTU + sizeof(struct ether_header)) {
  549 
  550                 printf("%s: invalid packet size %d; dropping\n",
  551                     ifp->if_xname, len);
  552 
  553                 ifp->if_ierrors++;
  554                 return;
  555         }
  556 
  557         /*
  558          * Pull packet off interface.
  559          */
  560         m = be_get(sc, idx, len);
  561         if (m == NULL) {
  562                 ifp->if_ierrors++;
  563                 return;
  564         }
  565         ifp->if_ipackets++;
  566 
  567 #if NBPFILTER > 0
  568         /*
  569          * Check if there's a BPF listener on this interface.
  570          * If so, hand off the raw packet to BPF.
  571          */
  572         if (ifp->if_bpf)
  573                 bpf_mtap(ifp->if_bpf, m, BPF_DIRECTION_IN);
  574 #endif
  575         /* Pass the packet up. */
  576         ether_input_mbuf(ifp, m);
  577 }
  578 
  579 /*
  580  * Start output on interface.
  581  * We make two assumptions here:
  582  *  1) that the current priority is set to splnet _before_ this code
  583  *     is called *and* is returned to the appropriate priority after
  584  *     return
  585  *  2) that the IFF_OACTIVE flag is checked before this code is called
  586  *     (i.e. that the output part of the interface is idle)
  587  */
  588 void
  589 bestart(struct ifnet *ifp)
  590 {
  591         struct be_softc *sc = (struct be_softc *)ifp->if_softc;
  592         struct qec_xd *txd = sc->sc_rb.rb_txd;
  593         struct mbuf *m;
  594         unsigned int bix, len;
  595         unsigned int ntbuf = sc->sc_rb.rb_ntbuf;
  596 
  597         if ((ifp->if_flags & (IFF_RUNNING | IFF_OACTIVE)) != IFF_RUNNING)
  598                 return;
  599 
  600         bix = sc->sc_rb.rb_tdhead;
  601 
  602         for (;;) {
  603                 IFQ_DEQUEUE(&ifp->if_snd, m);
  604                 if (m == 0)
  605                         break;
  606 
  607 #if NBPFILTER > 0
  608                 /*
  609                  * If BPF is listening on this interface, let it see the
  610                  * packet before we commit it to the wire.
  611                  */
  612                 if (ifp->if_bpf)
  613                         bpf_mtap(ifp->if_bpf, m, BPF_DIRECTION_OUT);
  614 #endif
  615 
  616                 /*
  617                  * Copy the mbuf chain into the transmit buffer.
  618                  */
  619                 len = be_put(sc, bix, m);
  620 
  621                 /*
  622                  * Initialize transmit registers and start transmission
  623                  */
  624                 txd[bix].xd_flags = QEC_XD_OWN | QEC_XD_SOP | QEC_XD_EOP |
  625                                     (len & QEC_XD_LENGTH);
  626                 bus_space_write_4(sc->sc_bustag, sc->sc_cr, BE_CRI_CTRL,
  627                                   BE_CR_CTRL_TWAKEUP);
  628 
  629                 if (++bix == QEC_XD_RING_MAXSIZE)
  630                         bix = 0;
  631 
  632                 if (++sc->sc_rb.rb_td_nbusy == ntbuf) {
  633                         ifp->if_flags |= IFF_OACTIVE;
  634                         break;
  635                 }
  636         }
  637 
  638         sc->sc_rb.rb_tdhead = bix;
  639 }
  640 
  641 void
  642 bestop(struct be_softc *sc)
  643 {
  644         int n;
  645         bus_space_tag_t t = sc->sc_bustag;
  646         bus_space_handle_t br = sc->sc_br;
  647 
  648         timeout_del(&sc->sc_tick_ch);
  649 
  650         /* Down the MII. */
  651         mii_down(&sc->sc_mii);
  652         (void)be_intphy_service(sc, &sc->sc_mii, MII_DOWN);
  653 
  654         /* Stop the transmitter */
  655         bus_space_write_4(t, br, BE_BRI_TXCFG, 0);
  656         for (n = 32; n > 0; n--) {
  657                 if (bus_space_read_4(t, br, BE_BRI_TXCFG) == 0)
  658                         break;
  659                 DELAY(20);
  660         }
  661 
  662         /* Stop the receiver */
  663         bus_space_write_4(t, br, BE_BRI_RXCFG, 0);
  664         for (n = 32; n > 0; n--) {
  665                 if (bus_space_read_4(t, br, BE_BRI_RXCFG) == 0)
  666                         break;
  667                 DELAY(20);
  668         }
  669 }
  670 
  671 /*
  672  * Reset interface.
  673  */
  674 void
  675 bereset(struct be_softc *sc)
  676 {
  677         int s;
  678 
  679         s = splnet();
  680         bestop(sc);
  681         if ((sc->sc_arpcom.ac_if.if_flags & IFF_UP) != 0)
  682                 beinit(sc);
  683         splx(s);
  684 }
  685 
  686 void
  687 bewatchdog(struct ifnet *ifp)
  688 {
  689         struct be_softc *sc = ifp->if_softc;
  690 
  691         log(LOG_ERR, "%s: device timeout\n", sc->sc_dev.dv_xname);
  692         ++sc->sc_arpcom.ac_if.if_oerrors;
  693         bereset(sc);
  694 }
  695 
  696 int
  697 beintr(void *v)
  698 {
  699         struct be_softc *sc = (struct be_softc *)v;
  700         bus_space_tag_t t = sc->sc_bustag;
  701         u_int32_t whyq, whyb, whyc;
  702         int r = 0;
  703 
  704         /* Read QEC status, channel status and BE status */
  705         whyq = bus_space_read_4(t, sc->sc_qr, QEC_QRI_STAT);
  706         whyc = bus_space_read_4(t, sc->sc_cr, BE_CRI_STAT);
  707         whyb = bus_space_read_4(t, sc->sc_br, BE_BRI_STAT);
  708 
  709         if (whyq & QEC_STAT_BM)
  710                 r |= beeint(sc, whyb);
  711 
  712         if (whyq & QEC_STAT_ER)
  713                 r |= beqint(sc, whyc);
  714 
  715         if (whyq & QEC_STAT_TX && whyc & BE_CR_STAT_TXIRQ)
  716                 r |= betint(sc);
  717 
  718         if (whyq & QEC_STAT_RX && whyc & BE_CR_STAT_RXIRQ)
  719                 r |= berint(sc);
  720 
  721         return (r);
  722 }
  723 
  724 /*
  725  * QEC Interrupt.
  726  */
  727 int
  728 beqint(struct be_softc *sc, u_int32_t why)
  729 {
  730         int r = 0, rst = 0;
  731 
  732         if (why & BE_CR_STAT_TXIRQ)
  733                 r |= 1;
  734         if (why & BE_CR_STAT_RXIRQ)
  735                 r |= 1;
  736 
  737         if (why & BE_CR_STAT_BERROR) {
  738                 r |= 1;
  739                 rst = 1;
  740                 printf("%s: bigmac error\n", sc->sc_dev.dv_xname);
  741         }
  742 
  743         if (why & BE_CR_STAT_TXDERR) {
  744                 r |= 1;
  745                 rst = 1;
  746                 printf("%s: bogus tx descriptor\n", sc->sc_dev.dv_xname);
  747         }
  748 
  749         if (why & (BE_CR_STAT_TXLERR | BE_CR_STAT_TXPERR | BE_CR_STAT_TXSERR)) {
  750                 r |= 1;
  751                 rst = 1;
  752                 printf("%s: tx dma error ( ", sc->sc_dev.dv_xname);
  753                 if (why & BE_CR_STAT_TXLERR)
  754                         printf("Late ");
  755                 if (why & BE_CR_STAT_TXPERR)
  756                         printf("Parity ");
  757                 if (why & BE_CR_STAT_TXSERR)
  758                         printf("Generic ");
  759                 printf(")\n");
  760         }
  761 
  762         if (why & BE_CR_STAT_RXDROP) {
  763                 r |= 1;
  764                 rst = 1;
  765                 printf("%s: out of rx descriptors\n", sc->sc_dev.dv_xname);
  766         }
  767 
  768         if (why & BE_CR_STAT_RXSMALL) {
  769                 r |= 1;
  770                 rst = 1;
  771                 printf("%s: rx descriptor too small\n", sc->sc_dev.dv_xname);
  772         }
  773 
  774         if (why & (BE_CR_STAT_RXLERR | BE_CR_STAT_RXPERR | BE_CR_STAT_RXSERR)) {
  775                 r |= 1;
  776                 rst = 1;
  777                 printf("%s: rx dma error ( ", sc->sc_dev.dv_xname);
  778                 if (why & BE_CR_STAT_RXLERR)
  779                         printf("Late ");
  780                 if (why & BE_CR_STAT_RXPERR)
  781                         printf("Parity ");
  782                 if (why & BE_CR_STAT_RXSERR)
  783                         printf("Generic ");
  784                 printf(")\n");
  785         }
  786 
  787         if (!r) {
  788                 rst = 1;
  789                 printf("%s: unexpected error interrupt %08x\n",
  790                         sc->sc_dev.dv_xname, why);
  791         }
  792 
  793         if (rst) {
  794                 printf("%s: resetting\n", sc->sc_dev.dv_xname);
  795                 bereset(sc);
  796         }
  797 
  798         return (r);
  799 }
  800 
  801 /*
  802  * Error interrupt.
  803  */
  804 int
  805 beeint(struct be_softc *sc, u_int32_t why)
  806 {
  807         int r = 0, rst = 0;
  808 
  809         if (why & BE_BR_STAT_RFIFOVF) {
  810                 r |= 1;
  811                 rst = 1;
  812                 printf("%s: receive fifo overrun\n", sc->sc_dev.dv_xname);
  813         }
  814         if (why & BE_BR_STAT_TFIFO_UND) {
  815                 r |= 1;
  816                 rst = 1;
  817                 printf("%s: transmit fifo underrun\n", sc->sc_dev.dv_xname);
  818         }
  819         if (why & BE_BR_STAT_MAXPKTERR) {
  820                 r |= 1;
  821                 rst = 1;
  822                 printf("%s: max packet size error\n", sc->sc_dev.dv_xname);
  823         }
  824 
  825         if (!r) {
  826                 rst = 1;
  827                 printf("%s: unexpected error interrupt %08x\n",
  828                         sc->sc_dev.dv_xname, why);
  829         }
  830 
  831         if (rst) {
  832                 printf("%s: resetting\n", sc->sc_dev.dv_xname);
  833                 bereset(sc);
  834         }
  835 
  836         return (r);
  837 }
  838 
  839 /*
  840  * Transmit interrupt.
  841  */
  842 int
  843 betint(struct be_softc *sc)
  844 {
  845         struct ifnet *ifp = &sc->sc_arpcom.ac_if;
  846         bus_space_tag_t t = sc->sc_bustag;
  847         bus_space_handle_t br = sc->sc_br;
  848         unsigned int bix, txflags;
  849 
  850         /*
  851          * Unload collision counters
  852          */
  853         ifp->if_collisions +=
  854                 bus_space_read_4(t, br, BE_BRI_NCCNT) +
  855                 bus_space_read_4(t, br, BE_BRI_FCCNT) +
  856                 bus_space_read_4(t, br, BE_BRI_EXCNT) +
  857                 bus_space_read_4(t, br, BE_BRI_LTCNT);
  858 
  859         /*
  860          * the clear the hardware counters
  861          */
  862         bus_space_write_4(t, br, BE_BRI_NCCNT, 0);
  863         bus_space_write_4(t, br, BE_BRI_FCCNT, 0);
  864         bus_space_write_4(t, br, BE_BRI_EXCNT, 0);
  865         bus_space_write_4(t, br, BE_BRI_LTCNT, 0);
  866 
  867         bix = sc->sc_rb.rb_tdtail;
  868 
  869         for (;;) {
  870                 if (sc->sc_rb.rb_td_nbusy <= 0)
  871                         break;
  872 
  873                 txflags = sc->sc_rb.rb_txd[bix].xd_flags;
  874 
  875                 if (txflags & QEC_XD_OWN)
  876                         break;
  877 
  878                 ifp->if_flags &= ~IFF_OACTIVE;
  879                 ifp->if_opackets++;
  880 
  881                 if (++bix == QEC_XD_RING_MAXSIZE)
  882                         bix = 0;
  883 
  884                 --sc->sc_rb.rb_td_nbusy;
  885         }
  886 
  887         sc->sc_rb.rb_tdtail = bix;
  888 
  889         bestart(ifp);
  890 
  891         if (sc->sc_rb.rb_td_nbusy == 0)
  892                 ifp->if_timer = 0;
  893 
  894         return (1);
  895 }
  896 
  897 /*
  898  * Receive interrupt.
  899  */
  900 int
  901 berint(struct be_softc *sc)
  902 {
  903         struct qec_xd *xd = sc->sc_rb.rb_rxd;
  904         unsigned int bix, len;
  905         unsigned int nrbuf = sc->sc_rb.rb_nrbuf;
  906 
  907         bix = sc->sc_rb.rb_rdtail;
  908 
  909         /*
  910          * Process all buffers with valid data.
  911          */
  912         for (;;) {
  913                 len = xd[bix].xd_flags;
  914                 if (len & QEC_XD_OWN)
  915                         break;
  916 
  917                 len &= QEC_XD_LENGTH;
  918                 be_read(sc, bix, len);
  919 
  920                 /* ... */
  921                 xd[(bix+nrbuf) % QEC_XD_RING_MAXSIZE].xd_flags =
  922                         QEC_XD_OWN | (BE_PKT_BUF_SZ & QEC_XD_LENGTH);
  923 
  924                 if (++bix == QEC_XD_RING_MAXSIZE)
  925                         bix = 0;
  926         }
  927 
  928         sc->sc_rb.rb_rdtail = bix;
  929 
  930         return (1);
  931 }
  932 
  933 int
  934 beioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
  935 {
  936         struct be_softc *sc = ifp->if_softc;
  937         struct ifaddr *ifa = (struct ifaddr *)data;
  938         struct ifreq *ifr = (struct ifreq *)data;
  939         int s, error = 0;
  940 
  941         s = splnet();
  942 
  943         if ((error = ether_ioctl(ifp, &sc->sc_arpcom, cmd, data)) > 0) {
  944                 splx(s);
  945                 return (error);
  946         }
  947 
  948         switch (cmd) {
  949         case SIOCSIFADDR:
  950                 ifp->if_flags |= IFF_UP;
  951                 switch (ifa->ifa_addr->sa_family) {
  952 #ifdef INET
  953                 case AF_INET:
  954                         beinit(sc);
  955                         arp_ifinit(&sc->sc_arpcom, ifa);
  956                         break;
  957 #endif /* INET */
  958                 default:
  959                         beinit(sc);
  960                         break;
  961                 }
  962                 break;
  963 
  964         case SIOCSIFFLAGS:
  965                 if ((ifp->if_flags & IFF_UP) == 0 &&
  966                     (ifp->if_flags & IFF_RUNNING) != 0) {
  967                         /*
  968                          * If interface is marked down and it is running, then
  969                          * stop it.
  970                          */
  971                         bestop(sc);
  972                         ifp->if_flags &= ~IFF_RUNNING;
  973                 } else if ((ifp->if_flags & IFF_UP) != 0 &&
  974                     (ifp->if_flags & IFF_RUNNING) == 0) {
  975                         /*
  976                          * If interface is marked up and it is stopped, then
  977                          * start it.
  978                          */
  979                         beinit(sc);
  980                 } else {
  981                         /*
  982                          * Reset the interface to pick up changes in any other
  983                          * flags that affect hardware registers.
  984                          */
  985                         bestop(sc);
  986                         beinit(sc);
  987                 }
  988 #ifdef BEDEBUG
  989                 if (ifp->if_flags & IFF_DEBUG)
  990                         sc->sc_debug = 1;
  991                 else
  992                         sc->sc_debug = 0;
  993 #endif
  994                 break;
  995 
  996         case SIOCADDMULTI:
  997         case SIOCDELMULTI:
  998                 error = (cmd == SIOCADDMULTI) ?
  999                     ether_addmulti(ifr, &sc->sc_arpcom):
 1000                     ether_delmulti(ifr, &sc->sc_arpcom);
 1001 
 1002                 if (error == ENETRESET) {
 1003                         /*
 1004                          * Multicast list has changed; set the hardware filter
 1005                          * accordingly.
 1006                          */
 1007                         if (ifp->if_flags & IFF_RUNNING)
 1008                                 be_mcreset(sc);
 1009                         error = 0;
 1010                 }
 1011                 break;
 1012         case SIOCGIFMEDIA:
 1013         case SIOCSIFMEDIA:
 1014                 error = ifmedia_ioctl(ifp, ifr, &sc->sc_media, cmd);
 1015                 break;
 1016         default:
 1017                 error = EINVAL;
 1018                 break;
 1019         }
 1020         splx(s);
 1021         return (error);
 1022 }
 1023 
 1024 
 1025 void
 1026 beinit(struct be_softc *sc)
 1027 {
 1028         struct ifnet *ifp = &sc->sc_arpcom.ac_if;
 1029         bus_space_tag_t t = sc->sc_bustag;
 1030         bus_space_handle_t br = sc->sc_br;
 1031         bus_space_handle_t cr = sc->sc_cr;
 1032         struct qec_softc *qec = sc->sc_qec;
 1033         u_int32_t v;
 1034         u_int32_t qecaddr;
 1035         u_int8_t *ea;
 1036         int s;
 1037 
 1038         s = splnet();
 1039 
 1040         qec_meminit(&sc->sc_rb, BE_PKT_BUF_SZ);
 1041 
 1042         bestop(sc);
 1043 
 1044         ea = sc->sc_arpcom.ac_enaddr;
 1045         bus_space_write_4(t, br, BE_BRI_MACADDR0, (ea[0] << 8) | ea[1]);
 1046         bus_space_write_4(t, br, BE_BRI_MACADDR1, (ea[2] << 8) | ea[3]);
 1047         bus_space_write_4(t, br, BE_BRI_MACADDR2, (ea[4] << 8) | ea[5]);
 1048 
 1049         /* Clear hash table */
 1050         bus_space_write_4(t, br, BE_BRI_HASHTAB0, 0);
 1051         bus_space_write_4(t, br, BE_BRI_HASHTAB1, 0);
 1052         bus_space_write_4(t, br, BE_BRI_HASHTAB2, 0);
 1053         bus_space_write_4(t, br, BE_BRI_HASHTAB3, 0);
 1054 
 1055         /* Re-initialize RX configuration */
 1056         v = BE_BR_RXCFG_FIFO;
 1057         bus_space_write_4(t, br, BE_BRI_RXCFG, v);
 1058 
 1059         be_mcreset(sc);
 1060 
 1061         bus_space_write_4(t, br, BE_BRI_RANDSEED, 0xbd);
 1062 
 1063         bus_space_write_4(t, br, BE_BRI_XIFCFG,
 1064                           BE_BR_XCFG_ODENABLE | BE_BR_XCFG_RESV);
 1065 
 1066         bus_space_write_4(t, br, BE_BRI_JSIZE, 4);
 1067 
 1068         /*
 1069          * Turn off counter expiration interrupts as well as
 1070          * 'gotframe' and 'sentframe'
 1071          */
 1072         bus_space_write_4(t, br, BE_BRI_IMASK,
 1073                           BE_BR_IMASK_GOTFRAME  |
 1074                           BE_BR_IMASK_RCNTEXP   |
 1075                           BE_BR_IMASK_ACNTEXP   |
 1076                           BE_BR_IMASK_CCNTEXP   |
 1077                           BE_BR_IMASK_LCNTEXP   |
 1078                           BE_BR_IMASK_CVCNTEXP  |
 1079                           BE_BR_IMASK_SENTFRAME |
 1080                           BE_BR_IMASK_NCNTEXP   |
 1081                           BE_BR_IMASK_ECNTEXP   |
 1082                           BE_BR_IMASK_LCCNTEXP  |
 1083                           BE_BR_IMASK_FCNTEXP   |
 1084                           BE_BR_IMASK_DTIMEXP);
 1085 
 1086         /* Channel registers: */
 1087         bus_space_write_4(t, cr, BE_CRI_RXDS, (u_int32_t)sc->sc_rb.rb_rxddma);
 1088         bus_space_write_4(t, cr, BE_CRI_TXDS, (u_int32_t)sc->sc_rb.rb_txddma);
 1089 
 1090         qecaddr = sc->sc_channel * qec->sc_msize;
 1091         bus_space_write_4(t, cr, BE_CRI_RXWBUF, qecaddr);
 1092         bus_space_write_4(t, cr, BE_CRI_RXRBUF, qecaddr);
 1093         bus_space_write_4(t, cr, BE_CRI_TXWBUF, qecaddr + qec->sc_rsize);
 1094         bus_space_write_4(t, cr, BE_CRI_TXRBUF, qecaddr + qec->sc_rsize);
 1095 
 1096         bus_space_write_4(t, cr, BE_CRI_RIMASK, 0);
 1097         bus_space_write_4(t, cr, BE_CRI_TIMASK, 0);
 1098         bus_space_write_4(t, cr, BE_CRI_QMASK, 0);
 1099         bus_space_write_4(t, cr, BE_CRI_BMASK, 0);
 1100         bus_space_write_4(t, cr, BE_CRI_CCNT, 0);
 1101 
 1102         /* Enable transmitter */
 1103         bus_space_write_4(t, br, BE_BRI_TXCFG,
 1104                           BE_BR_TXCFG_FIFO | BE_BR_TXCFG_ENABLE);
 1105 
 1106         /* Enable receiver */
 1107         v = bus_space_read_4(t, br, BE_BRI_RXCFG);
 1108         v |= BE_BR_RXCFG_FIFO | BE_BR_RXCFG_ENABLE;
 1109         bus_space_write_4(t, br, BE_BRI_RXCFG, v);
 1110 
 1111         ifp->if_flags |= IFF_RUNNING;
 1112         ifp->if_flags &= ~IFF_OACTIVE;
 1113 
 1114         be_ifmedia_upd(ifp);
 1115         timeout_add(&sc->sc_tick_ch, hz);
 1116         splx(s);
 1117 }
 1118 
 1119 void
 1120 be_mcreset(struct be_softc *sc)
 1121 {
 1122         struct arpcom *ac = &sc->sc_arpcom;
 1123         struct ifnet *ifp = &sc->sc_arpcom.ac_if;
 1124         bus_space_tag_t t = sc->sc_bustag;
 1125         bus_space_handle_t br = sc->sc_br;
 1126         u_int32_t crc;
 1127         u_int16_t hash[4];
 1128         u_int8_t octet;
 1129         u_int32_t v;
 1130         int i, j;
 1131         struct ether_multi *enm;
 1132         struct ether_multistep step;
 1133 
 1134         if (ifp->if_flags & IFF_PROMISC) {
 1135                 v = bus_space_read_4(t, br, BE_BRI_RXCFG);
 1136                 v |= BE_BR_RXCFG_PMISC;
 1137                 bus_space_write_4(t, br, BE_BRI_RXCFG, v);
 1138                 return;
 1139         }
 1140 
 1141         if (ifp->if_flags & IFF_ALLMULTI) {
 1142                 hash[3] = hash[2] = hash[1] = hash[0] = 0xffff;
 1143                 goto chipit;
 1144         }
 1145 
 1146         hash[3] = hash[2] = hash[1] = hash[0] = 0;
 1147 
 1148         ETHER_FIRST_MULTI(step, ac, enm);
 1149         while (enm != NULL) {
 1150                 if (bcmp(enm->enm_addrlo, enm->enm_addrhi, ETHER_ADDR_LEN)) {
 1151                         /*
 1152                          * We must listen to a range of multicast
 1153                          * addresses.  For now, just accept all
 1154                          * multicasts, rather than trying to set only
 1155                          * those filter bits needed to match the range.
 1156                          * (At this time, the only use of address
 1157                          * ranges is for IP multicast routing, for
 1158                          * which the range is big enough to require
 1159                          * all bits set.)
 1160                          */
 1161                         hash[3] = hash[2] = hash[1] = hash[0] = 0xffff;
 1162                         ifp->if_flags |= IFF_ALLMULTI;
 1163                         goto chipit;
 1164                 }
 1165 
 1166                 crc = 0xffffffff;
 1167 
 1168                 for (i = 0; i < ETHER_ADDR_LEN; i++) {
 1169                         octet = enm->enm_addrlo[i];
 1170 
 1171                         for (j = 0; j < 8; j++) {
 1172                                 if ((crc & 1) ^ (octet & 1)) {
 1173                                         crc >>= 1;
 1174                                         crc ^= MC_POLY_LE;
 1175                                 }
 1176                                 else
 1177                                         crc >>= 1;
 1178                                 octet >>= 1;
 1179                         }
 1180                 }
 1181 
 1182                 crc >>= 26;
 1183                 hash[crc >> 4] |= 1 << (crc & 0xf);
 1184                 ETHER_NEXT_MULTI(step, enm);
 1185         }
 1186 
 1187         ifp->if_flags &= ~IFF_ALLMULTI;
 1188 
 1189 chipit:
 1190         /* Enable the hash filter */
 1191         bus_space_write_4(t, br, BE_BRI_HASHTAB0, hash[0]);
 1192         bus_space_write_4(t, br, BE_BRI_HASHTAB1, hash[1]);
 1193         bus_space_write_4(t, br, BE_BRI_HASHTAB2, hash[2]);
 1194         bus_space_write_4(t, br, BE_BRI_HASHTAB3, hash[3]);
 1195 
 1196         v = bus_space_read_4(t, br, BE_BRI_RXCFG);
 1197         v &= ~BE_BR_RXCFG_PMISC;
 1198         v |= BE_BR_RXCFG_HENABLE;
 1199         bus_space_write_4(t, br, BE_BRI_RXCFG, v);
 1200 }
 1201 
 1202 /*
 1203  * Set the tcvr to an idle state
 1204  */
 1205 void
 1206 be_mii_sync(struct be_softc *sc)
 1207 {
 1208         bus_space_tag_t t = sc->sc_bustag;
 1209         bus_space_handle_t tr = sc->sc_tr;
 1210         int n = 32;
 1211 
 1212         while (n--) {
 1213                 bus_space_write_4(t, tr, BE_TRI_MGMTPAL,
 1214                     MGMT_PAL_INT_MDIO | MGMT_PAL_EXT_MDIO | MGMT_PAL_OENAB);
 1215                 (void)bus_space_read_4(t, tr, BE_TRI_MGMTPAL);
 1216                 bus_space_write_4(t, tr, BE_TRI_MGMTPAL,
 1217                     MGMT_PAL_INT_MDIO | MGMT_PAL_EXT_MDIO |
 1218                     MGMT_PAL_OENAB | MGMT_PAL_DCLOCK);
 1219                 (void)bus_space_read_4(t, tr, BE_TRI_MGMTPAL);
 1220         }
 1221 }
 1222 
 1223 void
 1224 be_pal_gate(struct be_softc *sc, int phy)
 1225 {
 1226         bus_space_tag_t t = sc->sc_bustag;
 1227         bus_space_handle_t tr = sc->sc_tr;
 1228         u_int32_t v;
 1229 
 1230         be_mii_sync(sc);
 1231 
 1232         v = ~(TCVR_PAL_EXTLBACK | TCVR_PAL_MSENSE | TCVR_PAL_LTENABLE);
 1233         if (phy == BE_PHY_INTERNAL)
 1234                 v &= ~TCVR_PAL_SERIAL;
 1235 
 1236         bus_space_write_4(t, tr, BE_TRI_TCVRPAL, v);
 1237         (void)bus_space_read_4(t, tr, BE_TRI_TCVRPAL);
 1238 }
 1239 
 1240 static int
 1241 be_tcvr_read_bit(struct be_softc *sc, int phy)
 1242 {
 1243         bus_space_tag_t t = sc->sc_bustag;
 1244         bus_space_handle_t tr = sc->sc_tr;
 1245         int ret;
 1246 
 1247         if (phy == BE_PHY_INTERNAL) {
 1248                 bus_space_write_4(t, tr, BE_TRI_MGMTPAL, MGMT_PAL_EXT_MDIO);
 1249                 (void)bus_space_read_4(t, tr, BE_TRI_MGMTPAL);
 1250                 bus_space_write_4(t, tr, BE_TRI_MGMTPAL,
 1251                     MGMT_PAL_EXT_MDIO | MGMT_PAL_DCLOCK);
 1252                 (void)bus_space_read_4(t, tr, BE_TRI_MGMTPAL);
 1253                 ret = (bus_space_read_4(t, tr, BE_TRI_MGMTPAL) &
 1254                         MGMT_PAL_INT_MDIO) >> MGMT_PAL_INT_MDIO_SHIFT;
 1255         } else {
 1256                 bus_space_write_4(t, tr, BE_TRI_MGMTPAL, MGMT_PAL_INT_MDIO);
 1257                 (void)bus_space_read_4(t, tr, BE_TRI_MGMTPAL);
 1258                 ret = (bus_space_read_4(t, tr, BE_TRI_MGMTPAL) &
 1259                     MGMT_PAL_EXT_MDIO) >> MGMT_PAL_EXT_MDIO_SHIFT;
 1260                 bus_space_write_4(t, tr, BE_TRI_MGMTPAL,
 1261                     MGMT_PAL_INT_MDIO | MGMT_PAL_DCLOCK);
 1262                 (void)bus_space_read_4(t, tr, BE_TRI_MGMTPAL);
 1263         }
 1264 
 1265         return (ret);
 1266 }
 1267 
 1268 static void
 1269 be_tcvr_write_bit(struct be_softc *sc, int phy, int bit)
 1270 {
 1271         bus_space_tag_t t = sc->sc_bustag;
 1272         bus_space_handle_t tr = sc->sc_tr;
 1273         u_int32_t v;
 1274 
 1275         if (phy == BE_PHY_INTERNAL) {
 1276                 v = ((bit & 1) << MGMT_PAL_INT_MDIO_SHIFT) |
 1277                     MGMT_PAL_OENAB | MGMT_PAL_EXT_MDIO;
 1278         } else {
 1279                 v = ((bit & 1) << MGMT_PAL_EXT_MDIO_SHIFT)
 1280                     | MGMT_PAL_OENAB | MGMT_PAL_INT_MDIO;
 1281         }
 1282         bus_space_write_4(t, tr, BE_TRI_MGMTPAL, v);
 1283         (void)bus_space_read_4(t, tr, BE_TRI_MGMTPAL);
 1284         bus_space_write_4(t, tr, BE_TRI_MGMTPAL, v | MGMT_PAL_DCLOCK);
 1285         (void)bus_space_read_4(t, tr, BE_TRI_MGMTPAL);
 1286 }
 1287 
 1288 static void
 1289 be_mii_sendbits(struct be_softc *sc, int phy, u_int32_t data, int nbits)
 1290 {
 1291         int i;
 1292 
 1293         for (i = 1 << (nbits - 1); i != 0; i >>= 1)
 1294                 be_tcvr_write_bit(sc, phy, (data & i) != 0);
 1295 }
 1296 
 1297 static int
 1298 be_mii_readreg(struct device *self, int phy, int reg)
 1299 {
 1300         struct be_softc *sc = (struct be_softc *)self;
 1301         int val = 0, i;
 1302 
 1303         /*
 1304          * Read the PHY register by manually driving the MII control lines.
 1305          */
 1306         be_mii_sync(sc);
 1307         be_mii_sendbits(sc, phy, MII_COMMAND_START, 2);
 1308         be_mii_sendbits(sc, phy, MII_COMMAND_READ, 2);
 1309         be_mii_sendbits(sc, phy, phy, 5);
 1310         be_mii_sendbits(sc, phy, reg, 5);
 1311 
 1312         (void) be_tcvr_read_bit(sc, phy);
 1313         (void) be_tcvr_read_bit(sc, phy);
 1314 
 1315         for (i = 15; i >= 0; i--)
 1316                 val |= (be_tcvr_read_bit(sc, phy) << i);
 1317 
 1318         (void) be_tcvr_read_bit(sc, phy);
 1319         (void) be_tcvr_read_bit(sc, phy);
 1320         (void) be_tcvr_read_bit(sc, phy);
 1321 
 1322         return (val);
 1323 }
 1324 
 1325 void
 1326 be_mii_writereg(struct device *self, int phy, int reg, int val)
 1327 {
 1328         struct be_softc *sc = (struct be_softc *)self;
 1329         int i;
 1330 
 1331         /*
 1332          * Write the PHY register by manually driving the MII control lines.
 1333          */
 1334         be_mii_sync(sc);
 1335         be_mii_sendbits(sc, phy, MII_COMMAND_START, 2);
 1336         be_mii_sendbits(sc, phy, MII_COMMAND_WRITE, 2);
 1337         be_mii_sendbits(sc, phy, phy, 5);
 1338         be_mii_sendbits(sc, phy, reg, 5);
 1339 
 1340         be_tcvr_write_bit(sc, phy, 1);
 1341         be_tcvr_write_bit(sc, phy, 0);
 1342 
 1343         for (i = 15; i >= 0; i--)
 1344                 be_tcvr_write_bit(sc, phy, (val >> i) & 1);
 1345 }
 1346 
 1347 int
 1348 be_mii_reset(struct be_softc *sc, int phy)
 1349 {
 1350         int n;
 1351 
 1352         be_mii_writereg((struct device *)sc, phy, MII_BMCR,
 1353             BMCR_LOOP | BMCR_PDOWN | BMCR_ISO);
 1354         be_mii_writereg((struct device *)sc, phy, MII_BMCR, BMCR_RESET);
 1355 
 1356         for (n = 16; n >= 0; n--) {
 1357                 int bmcr = be_mii_readreg((struct device *)sc, phy, MII_BMCR);
 1358                 if ((bmcr & BMCR_RESET) == 0)
 1359                         break;
 1360                 DELAY(20);
 1361         }
 1362         if (n == 0) {
 1363                 printf("%s: bmcr reset failed\n", sc->sc_dev.dv_xname);
 1364                 return (EIO);
 1365         }
 1366 
 1367         return (0);
 1368 }
 1369 
 1370 void
 1371 be_tick(void *arg)
 1372 {
 1373         struct be_softc *sc = arg;
 1374         int s = splnet();
 1375 
 1376         mii_tick(&sc->sc_mii);
 1377         (void)be_intphy_service(sc, &sc->sc_mii, MII_TICK);
 1378 
 1379         timeout_add(&sc->sc_tick_ch, hz);
 1380         splx(s);
 1381 }
 1382 
 1383 void
 1384 be_mii_statchg(struct device *self)
 1385 {
 1386         struct be_softc *sc = (struct be_softc *)self;
 1387         bus_space_tag_t t = sc->sc_bustag;
 1388         bus_space_handle_t br = sc->sc_br;
 1389         u_int instance;
 1390         u_int32_t v;
 1391 
 1392         instance = IFM_INST(sc->sc_mii.mii_media.ifm_cur->ifm_media);
 1393 #ifdef DIAGNOSTIC
 1394         if (instance > 1)
 1395                 panic("be_mii_statchg: instance %d out of range", instance);
 1396 #endif
 1397 
 1398         /* Update duplex mode in TX configuration */
 1399         v = bus_space_read_4(t, br, BE_BRI_TXCFG);
 1400         if ((IFM_OPTIONS(sc->sc_mii.mii_media_active) & IFM_FDX) != 0)
 1401                 v |= BE_BR_TXCFG_FULLDPLX;
 1402         else
 1403                 v &= ~BE_BR_TXCFG_FULLDPLX;
 1404         bus_space_write_4(t, br, BE_BRI_TXCFG, v);
 1405 
 1406         /* Change to appropriate gate in transceiver PAL */
 1407         be_pal_gate(sc, sc->sc_phys[instance]);
 1408 }
 1409 
 1410 /*
 1411  * Get current media settings.
 1412  */
 1413 void
 1414 be_ifmedia_sts(struct ifnet *ifp, struct ifmediareq *ifmr)
 1415 {
 1416         struct be_softc *sc = ifp->if_softc;
 1417 
 1418         mii_pollstat(&sc->sc_mii);
 1419         (void)be_intphy_service(sc, &sc->sc_mii, MII_POLLSTAT);
 1420 
 1421         ifmr->ifm_status = sc->sc_mii.mii_media_status;
 1422         ifmr->ifm_active = sc->sc_mii.mii_media_active;
 1423         return;
 1424 }
 1425 
 1426 /*
 1427  * Set media options.
 1428  */
 1429 int
 1430 be_ifmedia_upd(struct ifnet *ifp)
 1431 {
 1432         struct be_softc *sc = ifp->if_softc;
 1433         int error;
 1434 
 1435         if ((error = mii_mediachg(&sc->sc_mii)) != 0)
 1436                 return (error);
 1437 
 1438         return (be_intphy_service(sc, &sc->sc_mii, MII_MEDIACHG));
 1439 }
 1440 
 1441 /*
 1442  * Service routine for our pseudo-MII internal transceiver.
 1443  */
 1444 int
 1445 be_intphy_service(struct be_softc *sc, struct mii_data *mii, int cmd)
 1446 {
 1447         struct ifmedia_entry *ife = mii->mii_media.ifm_cur;
 1448         int bmcr, bmsr;
 1449         int error;
 1450 
 1451         switch (cmd) {
 1452         case MII_POLLSTAT:
 1453                 /*
 1454                  * If we're not polling our PHY instance, just return.
 1455                  */
 1456                 if (IFM_INST(ife->ifm_media) != sc->sc_mii_inst)
 1457                         return (0);
 1458 
 1459                 break;
 1460 
 1461         case MII_MEDIACHG:
 1462 
 1463                 /*
 1464                  * If the media indicates a different PHY instance,
 1465                  * isolate ourselves.
 1466                  */
 1467                 if (IFM_INST(ife->ifm_media) != sc->sc_mii_inst) {
 1468                         bmcr = be_mii_readreg((void *)sc,
 1469                             BE_PHY_INTERNAL, MII_BMCR);
 1470                         be_mii_writereg((void *)sc,
 1471                             BE_PHY_INTERNAL, MII_BMCR, bmcr | BMCR_ISO);
 1472                         sc->sc_mii_flags &= ~MIIF_HAVELINK;
 1473                         sc->sc_intphy_curspeed = 0;
 1474                         return (0);
 1475                 }
 1476 
 1477 
 1478                 if ((error = be_mii_reset(sc, BE_PHY_INTERNAL)) != 0)
 1479                         return (error);
 1480 
 1481                 bmcr = be_mii_readreg((void *)sc, BE_PHY_INTERNAL, MII_BMCR);
 1482 
 1483                 /*
 1484                  * Select the new mode and take out of isolation
 1485                  */
 1486                 if (IFM_SUBTYPE(ife->ifm_media) == IFM_100_TX)
 1487                         bmcr |= BMCR_S100;
 1488                 else if (IFM_SUBTYPE(ife->ifm_media) == IFM_10_T)
 1489                         bmcr &= ~BMCR_S100;
 1490                 else if (IFM_SUBTYPE(ife->ifm_media) == IFM_AUTO) {
 1491                         if ((sc->sc_mii_flags & MIIF_HAVELINK) != 0) {
 1492                                 bmcr &= ~BMCR_S100;
 1493                                 bmcr |= sc->sc_intphy_curspeed;
 1494                         } else {
 1495                                 /* Keep isolated until link is up */
 1496                                 bmcr |= BMCR_ISO;
 1497                                 sc->sc_mii_flags |= MIIF_DOINGAUTO;
 1498                         }
 1499                 }
 1500 
 1501                 if ((IFM_OPTIONS(ife->ifm_media) & IFM_FDX) != 0)
 1502                         bmcr |= BMCR_FDX;
 1503                 else
 1504                         bmcr &= ~BMCR_FDX;
 1505 
 1506                 be_mii_writereg((void *)sc, BE_PHY_INTERNAL, MII_BMCR, bmcr);
 1507                 break;
 1508 
 1509         case MII_TICK:
 1510                 /*
 1511                  * If we're not currently selected, just return.
 1512                  */
 1513                 if (IFM_INST(ife->ifm_media) != sc->sc_mii_inst)
 1514                         return (0);
 1515 
 1516                 /* Only used for automatic media selection */
 1517                 if (IFM_SUBTYPE(ife->ifm_media) != IFM_AUTO)
 1518                         return (0);
 1519 
 1520                 /* Is the interface even up? */
 1521                 if ((mii->mii_ifp->if_flags & IFF_UP) == 0)
 1522                         return (0);
 1523 
 1524                 /*
 1525                  * Check link status; if we don't have a link, try another
 1526                  * speed. We can't detect duplex mode, so half-duplex is
 1527                  * what we have to settle for.
 1528                  */
 1529 
 1530                 /* Read twice in case the register is latched */
 1531                 bmsr = be_mii_readreg((void *)sc, BE_PHY_INTERNAL, MII_BMSR) |
 1532                     be_mii_readreg((void *)sc, BE_PHY_INTERNAL, MII_BMSR);
 1533 
 1534                 if ((bmsr & BMSR_LINK) != 0) {
 1535                         /* We have a carrier */
 1536                         bmcr = be_mii_readreg((void *)sc,
 1537                             BE_PHY_INTERNAL, MII_BMCR);
 1538 
 1539                         if ((sc->sc_mii_flags & MIIF_DOINGAUTO) != 0) {
 1540                                 bmcr = be_mii_readreg((void *)sc,
 1541                                     BE_PHY_INTERNAL, MII_BMCR);
 1542 
 1543                                 sc->sc_mii_flags |= MIIF_HAVELINK;
 1544                                 sc->sc_intphy_curspeed = (bmcr & BMCR_S100);
 1545                                 sc->sc_mii_flags &= ~MIIF_DOINGAUTO;
 1546 
 1547                                 bmcr &= ~BMCR_ISO;
 1548                                 be_mii_writereg((void *)sc,
 1549                                     BE_PHY_INTERNAL, MII_BMCR, bmcr);
 1550 
 1551                                 printf("%s: link up at %s Mbps\n",
 1552                                     sc->sc_dev.dv_xname,
 1553                                     (bmcr & BMCR_S100) ? "100" : "10");
 1554                         }
 1555                         return (0);
 1556                 }
 1557 
 1558                 if ((sc->sc_mii_flags & MIIF_DOINGAUTO) == 0) {
 1559                         sc->sc_mii_flags |= MIIF_DOINGAUTO;
 1560                         sc->sc_mii_flags &= ~MIIF_HAVELINK;
 1561                         sc->sc_intphy_curspeed = 0;
 1562                         printf("%s: link down\n", sc->sc_dev.dv_xname);
 1563                 }
 1564 
 1565                 /* Only retry autonegotiation every 5 seconds. */
 1566                 if (++sc->sc_mii_ticks < 5)
 1567                         return(0);
 1568 
 1569                 sc->sc_mii_ticks = 0;
 1570                 bmcr = be_mii_readreg((void *)sc, BE_PHY_INTERNAL, MII_BMCR);
 1571                 /* Just flip the fast speed bit */
 1572                 bmcr ^= BMCR_S100;
 1573                 be_mii_writereg((void *)sc, BE_PHY_INTERNAL, MII_BMCR, bmcr);
 1574 
 1575                 break;
 1576 
 1577         case MII_DOWN:
 1578                 /* Isolate this phy */
 1579                 bmcr = be_mii_readreg((void *)sc, BE_PHY_INTERNAL, MII_BMCR);
 1580                 be_mii_writereg((void *)sc,
 1581                     BE_PHY_INTERNAL, MII_BMCR, bmcr | BMCR_ISO);
 1582                 return (0);
 1583         }
 1584 
 1585         /* Update the media status. */
 1586         be_intphy_status(sc);
 1587 
 1588         /* Callback if something changed. */
 1589         if (sc->sc_mii_active != mii->mii_media_active || cmd == MII_MEDIACHG) {
 1590                 (*mii->mii_statchg)((struct device *)sc);
 1591                 sc->sc_mii_active = mii->mii_media_active;
 1592         }
 1593         return (0);
 1594 }
 1595 
 1596 /*
 1597  * Determine status of internal transceiver
 1598  */
 1599 void
 1600 be_intphy_status(struct be_softc *sc)
 1601 {
 1602         struct mii_data *mii = &sc->sc_mii;
 1603         int media_active, media_status;
 1604         int bmcr, bmsr;
 1605 
 1606         media_status = IFM_AVALID;
 1607         media_active = 0;
 1608 
 1609         /*
 1610          * Internal transceiver; do the work here.
 1611          */
 1612         bmcr = be_mii_readreg((struct device *)sc, BE_PHY_INTERNAL, MII_BMCR);
 1613 
 1614         switch (bmcr & (BMCR_S100 | BMCR_FDX)) {
 1615         case (BMCR_S100 | BMCR_FDX):
 1616                 media_active = IFM_ETHER | IFM_100_TX | IFM_FDX;
 1617                 break;
 1618         case BMCR_S100:
 1619                 media_active = IFM_ETHER | IFM_100_TX | IFM_HDX;
 1620                 break;
 1621         case BMCR_FDX:
 1622                 media_active = IFM_ETHER | IFM_10_T | IFM_FDX;
 1623                 break;
 1624         case 0:
 1625                 media_active = IFM_ETHER | IFM_10_T | IFM_HDX;
 1626                 break;
 1627         }
 1628 
 1629         /* Read twice in case the register is latched */
 1630         bmsr = be_mii_readreg((struct device *)sc, BE_PHY_INTERNAL, MII_BMSR)|
 1631                be_mii_readreg((struct device *)sc, BE_PHY_INTERNAL, MII_BMSR);
 1632         if (bmsr & BMSR_LINK)
 1633                 media_status |=  IFM_ACTIVE;
 1634 
 1635         mii->mii_media_status = media_status;
 1636         mii->mii_media_active = media_active;
 1637 }

/* [<][>][^][v][top][bottom][index][help] */