dp83932.c revision 1.28
1/* $NetBSD: dp83932.c,v 1.28 2009/09/01 15:20:53 tsutsui Exp $ */ 2 3/*- 4 * Copyright (c) 2001 The NetBSD Foundation, Inc. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to The NetBSD Foundation 8 * by Jason R. Thorpe. 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 * 19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 22 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 29 * POSSIBILITY OF SUCH DAMAGE. 30 */ 31 32/* 33 * Device driver for the National Semiconductor DP83932 34 * Systems-Oriented Network Interface Controller (SONIC). 35 */ 36 37#include <sys/cdefs.h> 38__KERNEL_RCSID(0, "$NetBSD: dp83932.c,v 1.28 2009/09/01 15:20:53 tsutsui Exp $"); 39 40#include "bpfilter.h" 41 42#include <sys/param.h> 43#include <sys/systm.h> 44#include <sys/mbuf.h> 45#include <sys/malloc.h> 46#include <sys/kernel.h> 47#include <sys/socket.h> 48#include <sys/ioctl.h> 49#include <sys/errno.h> 50#include <sys/device.h> 51 52#include <uvm/uvm_extern.h> 53 54#include <net/if.h> 55#include <net/if_dl.h> 56#include <net/if_ether.h> 57 58#if NBPFILTER > 0 59#include <net/bpf.h> 60#endif 61 62#include <sys/bus.h> 63#include <sys/intr.h> 64 65#include <dev/ic/dp83932reg.h> 66#include <dev/ic/dp83932var.h> 67 68void sonic_start(struct ifnet *); 69void sonic_watchdog(struct ifnet *); 70int sonic_ioctl(struct ifnet *, u_long, void *); 71int sonic_init(struct ifnet *); 72void sonic_stop(struct ifnet *, int); 73 74bool sonic_shutdown(device_t, int); 75 76void sonic_reset(struct sonic_softc *); 77void sonic_rxdrain(struct sonic_softc *); 78int sonic_add_rxbuf(struct sonic_softc *, int); 79void sonic_set_filter(struct sonic_softc *); 80 81uint16_t sonic_txintr(struct sonic_softc *); 82void sonic_rxintr(struct sonic_softc *); 83 84int sonic_copy_small = 0; 85 86#define ETHER_PAD_LEN (ETHER_MIN_LEN - ETHER_CRC_LEN) 87 88/* 89 * sonic_attach: 90 * 91 * Attach a SONIC interface to the system. 92 */ 93void 94sonic_attach(struct sonic_softc *sc, const uint8_t *enaddr) 95{ 96 struct ifnet *ifp = &sc->sc_ethercom.ec_if; 97 int i, rseg, error; 98 bus_dma_segment_t seg; 99 size_t cdatasize; 100 uint8_t *nullbuf; 101 102 /* 103 * Allocate the control data structures, and create and load the 104 * DMA map for it. 105 */ 106 if (sc->sc_32bit) 107 cdatasize = sizeof(struct sonic_control_data32); 108 else 109 cdatasize = sizeof(struct sonic_control_data16); 110 111 if ((error = bus_dmamem_alloc(sc->sc_dmat, cdatasize + ETHER_PAD_LEN, 112 PAGE_SIZE, (64 * 1024), &seg, 1, &rseg, 113 BUS_DMA_NOWAIT)) != 0) { 114 aprint_error_dev(sc->sc_dev, 115 "unable to allocate control data, error = %d\n", error); 116 goto fail_0; 117 } 118 119 if ((error = bus_dmamem_map(sc->sc_dmat, &seg, rseg, 120 cdatasize + ETHER_PAD_LEN, (void **) &sc->sc_cdata16, 121 BUS_DMA_NOWAIT|BUS_DMA_COHERENT)) != 0) { 122 aprint_error_dev(sc->sc_dev, 123 "unable to map control data, error = %d\n", error); 124 goto fail_1; 125 } 126 nullbuf = (uint8_t *)sc->sc_cdata16 + cdatasize; 127 memset(nullbuf, 0, ETHER_PAD_LEN); 128 129 if ((error = bus_dmamap_create(sc->sc_dmat, 130 cdatasize, 1, cdatasize, 0, BUS_DMA_NOWAIT, 131 &sc->sc_cddmamap)) != 0) { 132 aprint_error_dev(sc->sc_dev, 133 "unable to create control data DMA map, error = %d\n", 134 error); 135 goto fail_2; 136 } 137 138 if ((error = bus_dmamap_load(sc->sc_dmat, sc->sc_cddmamap, 139 sc->sc_cdata16, cdatasize, NULL, BUS_DMA_NOWAIT)) != 0) { 140 aprint_error_dev(sc->sc_dev, 141 "unable to load control data DMA map, error = %d\n", error); 142 goto fail_3; 143 } 144 145 /* 146 * Create the transmit buffer DMA maps. 147 */ 148 for (i = 0; i < SONIC_NTXDESC; i++) { 149 if ((error = bus_dmamap_create(sc->sc_dmat, MCLBYTES, 150 SONIC_NTXFRAGS, MCLBYTES, 0, BUS_DMA_NOWAIT, 151 &sc->sc_txsoft[i].ds_dmamap)) != 0) { 152 aprint_error_dev(sc->sc_dev, 153 "unable to create tx DMA map %d, error = %d\n", 154 i, error); 155 goto fail_4; 156 } 157 } 158 159 /* 160 * Create the receive buffer DMA maps. 161 */ 162 for (i = 0; i < SONIC_NRXDESC; i++) { 163 if ((error = bus_dmamap_create(sc->sc_dmat, MCLBYTES, 1, 164 MCLBYTES, 0, BUS_DMA_NOWAIT, 165 &sc->sc_rxsoft[i].ds_dmamap)) != 0) { 166 aprint_error_dev(sc->sc_dev, 167 "unable to create rx DMA map %d, error = %d\n", 168 i, error); 169 goto fail_5; 170 } 171 sc->sc_rxsoft[i].ds_mbuf = NULL; 172 } 173 174 /* 175 * create and map the pad buffer 176 */ 177 if ((error = bus_dmamap_create(sc->sc_dmat, ETHER_PAD_LEN, 1, 178 ETHER_PAD_LEN, 0, BUS_DMA_NOWAIT, &sc->sc_nulldmamap)) != 0) { 179 aprint_error_dev(sc->sc_dev, 180 "unable to create pad buffer DMA map, error = %d\n", error); 181 goto fail_5; 182 } 183 184 if ((error = bus_dmamap_load(sc->sc_dmat, sc->sc_nulldmamap, 185 nullbuf, ETHER_PAD_LEN, NULL, BUS_DMA_NOWAIT)) != 0) { 186 aprint_error_dev(sc->sc_dev, 187 "unable to load pad buffer DMA map, error = %d\n", error); 188 goto fail_6; 189 } 190 bus_dmamap_sync(sc->sc_dmat, sc->sc_nulldmamap, 0, ETHER_PAD_LEN, 191 BUS_DMASYNC_PREWRITE); 192 193 /* 194 * Reset the chip to a known state. 195 */ 196 sonic_reset(sc); 197 198 aprint_normal_dev(sc->sc_dev, "Ethernet address %s\n", 199 ether_sprintf(enaddr)); 200 201 strlcpy(ifp->if_xname, device_xname(sc->sc_dev), IFNAMSIZ); 202 ifp->if_softc = sc; 203 ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST; 204 ifp->if_ioctl = sonic_ioctl; 205 ifp->if_start = sonic_start; 206 ifp->if_watchdog = sonic_watchdog; 207 ifp->if_init = sonic_init; 208 ifp->if_stop = sonic_stop; 209 IFQ_SET_READY(&ifp->if_snd); 210 211 /* 212 * We can support 802.1Q VLAN-sized frames. 213 */ 214 sc->sc_ethercom.ec_capabilities |= ETHERCAP_VLAN_MTU; 215 216 /* 217 * Attach the interface. 218 */ 219 if_attach(ifp); 220 ether_ifattach(ifp, enaddr); 221 222 /* 223 * Make sure the interface is shutdown during reboot. 224 */ 225 if (!pmf_device_register1(sc->sc_dev, NULL, NULL, sonic_shutdown)) 226 aprint_error_dev(sc->sc_dev, 227 "WARNING: unable to establish shutdown hook\n"); 228 return; 229 230 /* 231 * Free any resources we've allocated during the failed attach 232 * attempt. Do this in reverse order and fall through. 233 */ 234 fail_6: 235 bus_dmamap_destroy(sc->sc_dmat, sc->sc_nulldmamap); 236 fail_5: 237 for (i = 0; i < SONIC_NRXDESC; i++) { 238 if (sc->sc_rxsoft[i].ds_dmamap != NULL) 239 bus_dmamap_destroy(sc->sc_dmat, 240 sc->sc_rxsoft[i].ds_dmamap); 241 } 242 fail_4: 243 for (i = 0; i < SONIC_NTXDESC; i++) { 244 if (sc->sc_txsoft[i].ds_dmamap != NULL) 245 bus_dmamap_destroy(sc->sc_dmat, 246 sc->sc_txsoft[i].ds_dmamap); 247 } 248 bus_dmamap_unload(sc->sc_dmat, sc->sc_cddmamap); 249 fail_3: 250 bus_dmamap_destroy(sc->sc_dmat, sc->sc_cddmamap); 251 fail_2: 252 bus_dmamem_unmap(sc->sc_dmat, (void *)sc->sc_cdata16, cdatasize); 253 fail_1: 254 bus_dmamem_free(sc->sc_dmat, &seg, rseg); 255 fail_0: 256 return; 257} 258 259/* 260 * sonic_shutdown: 261 * 262 * Make sure the interface is stopped at reboot. 263 */ 264bool 265sonic_shutdown(device_t self, int howto) 266{ 267 struct sonic_softc *sc = device_private(self); 268 269 sonic_stop(&sc->sc_ethercom.ec_if, 1); 270 271 return true; 272} 273 274/* 275 * sonic_start: [ifnet interface function] 276 * 277 * Start packet transmission on the interface. 278 */ 279void 280sonic_start(struct ifnet *ifp) 281{ 282 struct sonic_softc *sc = ifp->if_softc; 283 struct mbuf *m0, *m; 284 struct sonic_tda16 *tda16; 285 struct sonic_tda32 *tda32; 286 struct sonic_descsoft *ds; 287 bus_dmamap_t dmamap; 288 int error, olasttx, nexttx, opending, totlen, olseg; 289 int seg = 0; /* XXX: gcc */ 290 291 if ((ifp->if_flags & (IFF_RUNNING|IFF_OACTIVE)) != IFF_RUNNING) 292 return; 293 294 /* 295 * Remember the previous txpending and the current "last txdesc 296 * used" index. 297 */ 298 opending = sc->sc_txpending; 299 olasttx = sc->sc_txlast; 300 301 /* 302 * Loop through the send queue, setting up transmit descriptors 303 * until we drain the queue, or use up all available transmit 304 * descriptors. Leave one at the end for sanity's sake. 305 */ 306 while (sc->sc_txpending < (SONIC_NTXDESC - 1)) { 307 /* 308 * Grab a packet off the queue. 309 */ 310 IFQ_POLL(&ifp->if_snd, m0); 311 if (m0 == NULL) 312 break; 313 m = NULL; 314 315 /* 316 * Get the next available transmit descriptor. 317 */ 318 nexttx = SONIC_NEXTTX(sc->sc_txlast); 319 ds = &sc->sc_txsoft[nexttx]; 320 dmamap = ds->ds_dmamap; 321 322 /* 323 * Load the DMA map. If this fails, the packet either 324 * didn't fit in the allotted number of frags, or we were 325 * short on resources. In this case, we'll copy and try 326 * again. 327 */ 328 if ((error = bus_dmamap_load_mbuf(sc->sc_dmat, dmamap, m0, 329 BUS_DMA_WRITE|BUS_DMA_NOWAIT)) != 0 || 330 (m0->m_pkthdr.len < ETHER_PAD_LEN && 331 dmamap->dm_nsegs == SONIC_NTXFRAGS)) { 332 if (error == 0) 333 bus_dmamap_unload(sc->sc_dmat, dmamap); 334 MGETHDR(m, M_DONTWAIT, MT_DATA); 335 if (m == NULL) { 336 printf("%s: unable to allocate Tx mbuf\n", 337 device_xname(sc->sc_dev)); 338 break; 339 } 340 if (m0->m_pkthdr.len > MHLEN) { 341 MCLGET(m, M_DONTWAIT); 342 if ((m->m_flags & M_EXT) == 0) { 343 printf("%s: unable to allocate Tx " 344 "cluster\n", 345 device_xname(sc->sc_dev)); 346 m_freem(m); 347 break; 348 } 349 } 350 m_copydata(m0, 0, m0->m_pkthdr.len, mtod(m, void *)); 351 m->m_pkthdr.len = m->m_len = m0->m_pkthdr.len; 352 error = bus_dmamap_load_mbuf(sc->sc_dmat, dmamap, 353 m, BUS_DMA_WRITE|BUS_DMA_NOWAIT); 354 if (error) { 355 printf("%s: unable to load Tx buffer, " 356 "error = %d\n", device_xname(sc->sc_dev), 357 error); 358 m_freem(m); 359 break; 360 } 361 } 362 IFQ_DEQUEUE(&ifp->if_snd, m0); 363 if (m != NULL) { 364 m_freem(m0); 365 m0 = m; 366 } 367 368 /* 369 * WE ARE NOW COMMITTED TO TRANSMITTING THE PACKET. 370 */ 371 372 /* Sync the DMA map. */ 373 bus_dmamap_sync(sc->sc_dmat, dmamap, 0, dmamap->dm_mapsize, 374 BUS_DMASYNC_PREWRITE); 375 376 /* 377 * Store a pointer to the packet so we can free it later. 378 */ 379 ds->ds_mbuf = m0; 380 381 /* 382 * Initialize the transmit descriptor. 383 */ 384 totlen = 0; 385 if (sc->sc_32bit) { 386 tda32 = &sc->sc_tda32[nexttx]; 387 for (seg = 0; seg < dmamap->dm_nsegs; seg++) { 388 tda32->tda_frags[seg].frag_ptr1 = 389 htosonic32(sc, 390 (dmamap->dm_segs[seg].ds_addr >> 16) & 391 0xffff); 392 tda32->tda_frags[seg].frag_ptr0 = 393 htosonic32(sc, 394 dmamap->dm_segs[seg].ds_addr & 0xffff); 395 tda32->tda_frags[seg].frag_size = 396 htosonic32(sc, dmamap->dm_segs[seg].ds_len); 397 totlen += dmamap->dm_segs[seg].ds_len; 398 } 399 if (totlen < ETHER_PAD_LEN) { 400 tda32->tda_frags[seg].frag_ptr1 = 401 htosonic32(sc, 402 (sc->sc_nulldma >> 16) & 0xffff); 403 tda32->tda_frags[seg].frag_ptr0 = 404 htosonic32(sc, sc->sc_nulldma & 0xffff); 405 tda32->tda_frags[seg].frag_size = 406 htosonic32(sc, ETHER_PAD_LEN - totlen); 407 totlen = ETHER_PAD_LEN; 408 seg++; 409 } 410 411 tda32->tda_status = 0; 412 tda32->tda_pktconfig = 0; 413 tda32->tda_pktsize = htosonic32(sc, totlen); 414 tda32->tda_fragcnt = htosonic32(sc, seg); 415 416 /* Link it up. */ 417 tda32->tda_frags[seg].frag_ptr0 = 418 htosonic32(sc, SONIC_CDTXADDR32(sc, 419 SONIC_NEXTTX(nexttx)) & 0xffff); 420 421 /* Sync the Tx descriptor. */ 422 SONIC_CDTXSYNC32(sc, nexttx, 423 BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE); 424 } else { 425 tda16 = &sc->sc_tda16[nexttx]; 426 for (seg = 0; seg < dmamap->dm_nsegs; seg++) { 427 tda16->tda_frags[seg].frag_ptr1 = 428 htosonic16(sc, 429 (dmamap->dm_segs[seg].ds_addr >> 16) & 430 0xffff); 431 tda16->tda_frags[seg].frag_ptr0 = 432 htosonic16(sc, 433 dmamap->dm_segs[seg].ds_addr & 0xffff); 434 tda16->tda_frags[seg].frag_size = 435 htosonic16(sc, dmamap->dm_segs[seg].ds_len); 436 totlen += dmamap->dm_segs[seg].ds_len; 437 } 438 if (totlen < ETHER_PAD_LEN) { 439 tda16->tda_frags[seg].frag_ptr1 = 440 htosonic16(sc, 441 (sc->sc_nulldma >> 16) & 0xffff); 442 tda16->tda_frags[seg].frag_ptr0 = 443 htosonic16(sc, sc->sc_nulldma & 0xffff); 444 tda16->tda_frags[seg].frag_size = 445 htosonic16(sc, ETHER_PAD_LEN - totlen); 446 totlen = ETHER_PAD_LEN; 447 seg++; 448 } 449 450 tda16->tda_status = 0; 451 tda16->tda_pktconfig = 0; 452 tda16->tda_pktsize = htosonic16(sc, totlen); 453 tda16->tda_fragcnt = htosonic16(sc, seg); 454 455 /* Link it up. */ 456 tda16->tda_frags[seg].frag_ptr0 = 457 htosonic16(sc, SONIC_CDTXADDR16(sc, 458 SONIC_NEXTTX(nexttx)) & 0xffff); 459 460 /* Sync the Tx descriptor. */ 461 SONIC_CDTXSYNC16(sc, nexttx, 462 BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE); 463 } 464 465 /* Advance the Tx pointer. */ 466 sc->sc_txpending++; 467 sc->sc_txlast = nexttx; 468 469#if NBPFILTER > 0 470 /* 471 * Pass the packet to any BPF listeners. 472 */ 473 if (ifp->if_bpf) 474 bpf_mtap(ifp->if_bpf, m0); 475#endif 476 } 477 478 if (sc->sc_txpending == (SONIC_NTXDESC - 1)) { 479 /* No more slots left; notify upper layer. */ 480 ifp->if_flags |= IFF_OACTIVE; 481 } 482 483 if (sc->sc_txpending != opending) { 484 /* 485 * We enqueued packets. If the transmitter was idle, 486 * reset the txdirty pointer. 487 */ 488 if (opending == 0) 489 sc->sc_txdirty = SONIC_NEXTTX(olasttx); 490 491 /* 492 * Stop the SONIC on the last packet we've set up, 493 * and clear end-of-list on the descriptor previous 494 * to our new chain. 495 * 496 * NOTE: our `seg' variable should still be valid! 497 */ 498 if (sc->sc_32bit) { 499 olseg = 500 sonic32toh(sc, sc->sc_tda32[olasttx].tda_fragcnt); 501 sc->sc_tda32[sc->sc_txlast].tda_frags[seg].frag_ptr0 |= 502 htosonic32(sc, TDA_LINK_EOL); 503 SONIC_CDTXSYNC32(sc, sc->sc_txlast, 504 BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE); 505 sc->sc_tda32[olasttx].tda_frags[olseg].frag_ptr0 &= 506 htosonic32(sc, ~TDA_LINK_EOL); 507 SONIC_CDTXSYNC32(sc, olasttx, 508 BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE); 509 } else { 510 olseg = 511 sonic16toh(sc, sc->sc_tda16[olasttx].tda_fragcnt); 512 sc->sc_tda16[sc->sc_txlast].tda_frags[seg].frag_ptr0 |= 513 htosonic16(sc, TDA_LINK_EOL); 514 SONIC_CDTXSYNC16(sc, sc->sc_txlast, 515 BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE); 516 sc->sc_tda16[olasttx].tda_frags[olseg].frag_ptr0 &= 517 htosonic16(sc, ~TDA_LINK_EOL); 518 SONIC_CDTXSYNC16(sc, olasttx, 519 BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE); 520 } 521 522 /* Start the transmitter. */ 523 CSR_WRITE(sc, SONIC_CR, CR_TXP); 524 525 /* Set a watchdog timer in case the chip flakes out. */ 526 ifp->if_timer = 5; 527 } 528} 529 530/* 531 * sonic_watchdog: [ifnet interface function] 532 * 533 * Watchdog timer handler. 534 */ 535void 536sonic_watchdog(struct ifnet *ifp) 537{ 538 struct sonic_softc *sc = ifp->if_softc; 539 540 printf("%s: device timeout\n", device_xname(sc->sc_dev)); 541 ifp->if_oerrors++; 542 543 (void)sonic_init(ifp); 544} 545 546/* 547 * sonic_ioctl: [ifnet interface function] 548 * 549 * Handle control requests from the operator. 550 */ 551int 552sonic_ioctl(struct ifnet *ifp, u_long cmd, void *data) 553{ 554 int s, error; 555 556 s = splnet(); 557 558 error = ether_ioctl(ifp, cmd, data); 559 if (error == ENETRESET) { 560 /* 561 * Multicast list has changed; set the hardware 562 * filter accordingly. 563 */ 564 if (ifp->if_flags & IFF_RUNNING) 565 (void)sonic_init(ifp); 566 error = 0; 567 } 568 569 splx(s); 570 return error; 571} 572 573/* 574 * sonic_intr: 575 * 576 * Interrupt service routine. 577 */ 578int 579sonic_intr(void *arg) 580{ 581 struct sonic_softc *sc = arg; 582 struct ifnet *ifp = &sc->sc_ethercom.ec_if; 583 uint16_t isr; 584 int handled = 0, wantinit; 585 586 for (wantinit = 0; wantinit == 0;) { 587 isr = CSR_READ(sc, SONIC_ISR) & sc->sc_imr; 588 if (isr == 0) 589 break; 590 CSR_WRITE(sc, SONIC_ISR, isr); /* ACK */ 591 592 handled = 1; 593 594 if (isr & IMR_PRX) 595 sonic_rxintr(sc); 596 597 if (isr & (IMR_PTX|IMR_TXER)) { 598 if (sonic_txintr(sc) & TCR_FU) { 599 printf("%s: transmit FIFO underrun\n", 600 device_xname(sc->sc_dev)); 601 wantinit = 1; 602 } 603 } 604 605 if (isr & (IMR_RFO|IMR_RBA|IMR_RBE|IMR_RDE)) { 606#define PRINTERR(bit, str) \ 607 if (isr & (bit)) \ 608 printf("%s: %s\n",device_xname(sc->sc_dev), str) 609 PRINTERR(IMR_RFO, "receive FIFO overrun"); 610 PRINTERR(IMR_RBA, "receive buffer exceeded"); 611 PRINTERR(IMR_RBE, "receive buffers exhausted"); 612 PRINTERR(IMR_RDE, "receive descriptors exhausted"); 613 wantinit = 1; 614 } 615 } 616 617 if (handled) { 618 if (wantinit) 619 (void)sonic_init(ifp); 620 sonic_start(ifp); 621 } 622 623 return handled; 624} 625 626/* 627 * sonic_txintr: 628 * 629 * Helper; handle transmit complete interrupts. 630 */ 631uint16_t 632sonic_txintr(struct sonic_softc *sc) 633{ 634 struct ifnet *ifp = &sc->sc_ethercom.ec_if; 635 struct sonic_descsoft *ds; 636 struct sonic_tda32 *tda32; 637 struct sonic_tda16 *tda16; 638 uint16_t status, totstat = 0; 639 int i; 640 641 ifp->if_flags &= ~IFF_OACTIVE; 642 643 for (i = sc->sc_txdirty; sc->sc_txpending != 0; 644 i = SONIC_NEXTTX(i), sc->sc_txpending--) { 645 ds = &sc->sc_txsoft[i]; 646 647 if (sc->sc_32bit) { 648 SONIC_CDTXSYNC32(sc, i, 649 BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE); 650 tda32 = &sc->sc_tda32[i]; 651 status = sonic32toh(sc, tda32->tda_status); 652 SONIC_CDTXSYNC32(sc, i, BUS_DMASYNC_PREREAD); 653 } else { 654 SONIC_CDTXSYNC16(sc, i, 655 BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE); 656 tda16 = &sc->sc_tda16[i]; 657 status = sonic16toh(sc, tda16->tda_status); 658 SONIC_CDTXSYNC16(sc, i, BUS_DMASYNC_PREREAD); 659 } 660 661 if ((status & ~(TCR_EXDIS|TCR_CRCI|TCR_POWC|TCR_PINT)) == 0) 662 break; 663 664 totstat |= status; 665 666 bus_dmamap_sync(sc->sc_dmat, ds->ds_dmamap, 0, 667 ds->ds_dmamap->dm_mapsize, BUS_DMASYNC_POSTWRITE); 668 bus_dmamap_unload(sc->sc_dmat, ds->ds_dmamap); 669 m_freem(ds->ds_mbuf); 670 ds->ds_mbuf = NULL; 671 672 /* 673 * Check for errors and collisions. 674 */ 675 if (status & TCR_PTX) 676 ifp->if_opackets++; 677 else 678 ifp->if_oerrors++; 679 ifp->if_collisions += TDA_STATUS_NCOL(status); 680 } 681 682 /* Update the dirty transmit buffer pointer. */ 683 sc->sc_txdirty = i; 684 685 /* 686 * Cancel the watchdog timer if there are no pending 687 * transmissions. 688 */ 689 if (sc->sc_txpending == 0) 690 ifp->if_timer = 0; 691 692 return totstat; 693} 694 695/* 696 * sonic_rxintr: 697 * 698 * Helper; handle receive interrupts. 699 */ 700void 701sonic_rxintr(struct sonic_softc *sc) 702{ 703 struct ifnet *ifp = &sc->sc_ethercom.ec_if; 704 struct sonic_descsoft *ds; 705 struct sonic_rda32 *rda32; 706 struct sonic_rda16 *rda16; 707 struct mbuf *m; 708 int i, len; 709 uint16_t status, bytecount, ptr0, ptr1, seqno; 710 711 for (i = sc->sc_rxptr;; i = SONIC_NEXTRX(i)) { 712 ds = &sc->sc_rxsoft[i]; 713 714 if (sc->sc_32bit) { 715 SONIC_CDRXSYNC32(sc, i, 716 BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE); 717 rda32 = &sc->sc_rda32[i]; 718 SONIC_CDRXSYNC32(sc, i, BUS_DMASYNC_PREREAD); 719 if (rda32->rda_inuse != 0) 720 break; 721 status = sonic32toh(sc, rda32->rda_status); 722 bytecount = sonic32toh(sc, rda32->rda_bytecount); 723 ptr0 = sonic32toh(sc, rda32->rda_pkt_ptr0); 724 ptr1 = sonic32toh(sc, rda32->rda_pkt_ptr1); 725 seqno = sonic32toh(sc, rda32->rda_seqno); 726 } else { 727 SONIC_CDRXSYNC16(sc, i, 728 BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE); 729 rda16 = &sc->sc_rda16[i]; 730 SONIC_CDRXSYNC16(sc, i, BUS_DMASYNC_PREREAD); 731 if (rda16->rda_inuse != 0) 732 break; 733 status = sonic16toh(sc, rda16->rda_status); 734 bytecount = sonic16toh(sc, rda16->rda_bytecount); 735 ptr0 = sonic16toh(sc, rda16->rda_pkt_ptr0); 736 ptr1 = sonic16toh(sc, rda16->rda_pkt_ptr1); 737 seqno = sonic16toh(sc, rda16->rda_seqno); 738 } 739 740 /* 741 * Make absolutely sure this is the only packet 742 * in this receive buffer. Our entire Rx buffer 743 * management scheme depends on this, and if the 744 * SONIC didn't follow our rule, it means we've 745 * misconfigured it. 746 */ 747 KASSERT(status & RCR_LPKT); 748 749 /* 750 * Make sure the packet arrived OK. If an error occurred, 751 * update stats and reset the descriptor. The buffer will 752 * be reused the next time the descriptor comes up in the 753 * ring. 754 */ 755 if ((status & RCR_PRX) == 0) { 756 if (status & RCR_FAER) 757 printf("%s: Rx frame alignment error\n", 758 device_xname(sc->sc_dev)); 759 else if (status & RCR_CRCR) 760 printf("%s: Rx CRC error\n", 761 device_xname(sc->sc_dev)); 762 ifp->if_ierrors++; 763 SONIC_INIT_RXDESC(sc, i); 764 continue; 765 } 766 767 bus_dmamap_sync(sc->sc_dmat, ds->ds_dmamap, 0, 768 ds->ds_dmamap->dm_mapsize, BUS_DMASYNC_POSTREAD); 769 770 /* 771 * The SONIC includes the CRC with every packet. 772 */ 773 len = bytecount - ETHER_CRC_LEN; 774 775 /* 776 * Ok, if the chip is in 32-bit mode, then receive 777 * buffers must be aligned to 32-bit boundaries, 778 * which means the payload is misaligned. In this 779 * case, we must allocate a new mbuf, and copy the 780 * packet into it, scooted forward 2 bytes to ensure 781 * proper alignment. 782 * 783 * Note, in 16-bit mode, we can configure the SONIC 784 * to do what we want, and we have. 785 */ 786#ifndef __NO_STRICT_ALIGNMENT 787 if (sc->sc_32bit) { 788 MGETHDR(m, M_DONTWAIT, MT_DATA); 789 if (m == NULL) 790 goto dropit; 791 if (len > (MHLEN - 2)) { 792 MCLGET(m, M_DONTWAIT); 793 if ((m->m_flags & M_EXT) == 0) 794 goto dropit; 795 } 796 m->m_data += 2; 797 /* 798 * Note that we use a cluster for incoming frames, 799 * so the buffer is virtually contiguous. 800 */ 801 memcpy(mtod(m, void *), mtod(ds->ds_mbuf, void *), 802 len); 803 SONIC_INIT_RXDESC(sc, i); 804 bus_dmamap_sync(sc->sc_dmat, ds->ds_dmamap, 0, 805 ds->ds_dmamap->dm_mapsize, BUS_DMASYNC_PREREAD); 806 } else 807#endif /* ! __NO_STRICT_ALIGNMENT */ 808 /* 809 * If the packet is small enough to fit in a single 810 * header mbuf, allocate one and copy the data into 811 * it. This greatly reduces memory consumption when 812 * we receive lots of small packets. 813 */ 814 if (sonic_copy_small != 0 && len <= (MHLEN - 2)) { 815 MGETHDR(m, M_DONTWAIT, MT_DATA); 816 if (m == NULL) 817 goto dropit; 818 m->m_data += 2; 819 /* 820 * Note that we use a cluster for incoming frames, 821 * so the buffer is virtually contiguous. 822 */ 823 memcpy(mtod(m, void *), mtod(ds->ds_mbuf, void *), 824 len); 825 SONIC_INIT_RXDESC(sc, i); 826 bus_dmamap_sync(sc->sc_dmat, ds->ds_dmamap, 0, 827 ds->ds_dmamap->dm_mapsize, BUS_DMASYNC_PREREAD); 828 } else { 829 m = ds->ds_mbuf; 830 if (sonic_add_rxbuf(sc, i) != 0) { 831 dropit: 832 ifp->if_ierrors++; 833 SONIC_INIT_RXDESC(sc, i); 834 bus_dmamap_sync(sc->sc_dmat, ds->ds_dmamap, 0, 835 ds->ds_dmamap->dm_mapsize, 836 BUS_DMASYNC_PREREAD); 837 continue; 838 } 839 } 840 841 ifp->if_ipackets++; 842 m->m_pkthdr.rcvif = ifp; 843 m->m_pkthdr.len = m->m_len = len; 844 845#if NBPFILTER > 0 846 /* 847 * Pass this up to any BPF listeners. 848 */ 849 if (ifp->if_bpf) 850 bpf_mtap(ifp->if_bpf, m); 851#endif /* NBPFILTER > 0 */ 852 853 /* Pass it on. */ 854 (*ifp->if_input)(ifp, m); 855 } 856 857 /* Update the receive pointer. */ 858 sc->sc_rxptr = i; 859 CSR_WRITE(sc, SONIC_RWR, SONIC_CDRRADDR(sc, SONIC_PREVRX(i))); 860} 861 862/* 863 * sonic_reset: 864 * 865 * Perform a soft reset on the SONIC. 866 */ 867void 868sonic_reset(struct sonic_softc *sc) 869{ 870 871 /* stop TX, RX and timer, and ensure RST is clear */ 872 CSR_WRITE(sc, SONIC_CR, CR_STP | CR_RXDIS | CR_HTX); 873 delay(1000); 874 875 CSR_WRITE(sc, SONIC_CR, CR_RST); 876 delay(1000); 877 878 /* clear all interrupts */ 879 CSR_WRITE(sc, SONIC_IMR, 0); 880 CSR_WRITE(sc, SONIC_ISR, IMR_ALL); 881 882 CSR_WRITE(sc, SONIC_CR, 0); 883 delay(1000); 884} 885 886/* 887 * sonic_init: [ifnet interface function] 888 * 889 * Initialize the interface. Must be called at splnet(). 890 */ 891int 892sonic_init(struct ifnet *ifp) 893{ 894 struct sonic_softc *sc = ifp->if_softc; 895 struct sonic_descsoft *ds; 896 int i, error = 0; 897 uint16_t reg; 898 899 /* 900 * Cancel any pending I/O. 901 */ 902 sonic_stop(ifp, 0); 903 904 /* 905 * Reset the SONIC to a known state. 906 */ 907 sonic_reset(sc); 908 909 /* 910 * Bring the SONIC into reset state, and program the DCR. 911 * 912 * Note: We don't bother optimizing the transmit and receive 913 * thresholds, here. TFT/RFT values should be set in MD attachments. 914 */ 915 reg = sc->sc_dcr; 916 if (sc->sc_32bit) 917 reg |= DCR_DW; 918 CSR_WRITE(sc, SONIC_CR, CR_RST); 919 CSR_WRITE(sc, SONIC_DCR, reg); 920 CSR_WRITE(sc, SONIC_DCR2, sc->sc_dcr2); 921 CSR_WRITE(sc, SONIC_CR, 0); 922 923 /* 924 * Initialize the transmit descriptors. 925 */ 926 if (sc->sc_32bit) { 927 for (i = 0; i < SONIC_NTXDESC; i++) { 928 memset(&sc->sc_tda32[i], 0, sizeof(struct sonic_tda32)); 929 SONIC_CDTXSYNC32(sc, i, 930 BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE); 931 } 932 } else { 933 for (i = 0; i < SONIC_NTXDESC; i++) { 934 memset(&sc->sc_tda16[i], 0, sizeof(struct sonic_tda16)); 935 SONIC_CDTXSYNC16(sc, i, 936 BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE); 937 } 938 } 939 sc->sc_txpending = 0; 940 sc->sc_txdirty = 0; 941 sc->sc_txlast = SONIC_NTXDESC - 1; 942 943 /* 944 * Initialize the receive descriptor ring. 945 */ 946 for (i = 0; i < SONIC_NRXDESC; i++) { 947 ds = &sc->sc_rxsoft[i]; 948 if (ds->ds_mbuf == NULL) { 949 if ((error = sonic_add_rxbuf(sc, i)) != 0) { 950 printf("%s: unable to allocate or map Rx " 951 "buffer %d, error = %d\n", 952 device_xname(sc->sc_dev), i, error); 953 /* 954 * XXX Should attempt to run with fewer receive 955 * XXX buffers instead of just failing. 956 */ 957 sonic_rxdrain(sc); 958 goto out; 959 } 960 } else 961 SONIC_INIT_RXDESC(sc, i); 962 } 963 sc->sc_rxptr = 0; 964 965 /* Give the transmit ring to the SONIC. */ 966 CSR_WRITE(sc, SONIC_UTDAR, (SONIC_CDTXADDR(sc, 0) >> 16) & 0xffff); 967 CSR_WRITE(sc, SONIC_CTDAR, SONIC_CDTXADDR(sc, 0) & 0xffff); 968 969 /* Give the receive descriptor ring to the SONIC. */ 970 CSR_WRITE(sc, SONIC_URDAR, (SONIC_CDRXADDR(sc, 0) >> 16) & 0xffff); 971 CSR_WRITE(sc, SONIC_CRDAR, SONIC_CDRXADDR(sc, 0) & 0xffff); 972 973 /* Give the receive buffer ring to the SONIC. */ 974 CSR_WRITE(sc, SONIC_URRAR, (SONIC_CDRRADDR(sc, 0) >> 16) & 0xffff); 975 CSR_WRITE(sc, SONIC_RSAR, SONIC_CDRRADDR(sc, 0) & 0xffff); 976 if (sc->sc_32bit) 977 CSR_WRITE(sc, SONIC_REAR, 978 (SONIC_CDRRADDR(sc, SONIC_NRXDESC - 1) + 979 sizeof(struct sonic_rra32)) & 0xffff); 980 else 981 CSR_WRITE(sc, SONIC_REAR, 982 (SONIC_CDRRADDR(sc, SONIC_NRXDESC - 1) + 983 sizeof(struct sonic_rra16)) & 0xffff); 984 CSR_WRITE(sc, SONIC_RRR, SONIC_CDRRADDR(sc, 0) & 0xffff); 985 CSR_WRITE(sc, SONIC_RWR, SONIC_CDRRADDR(sc, SONIC_NRXDESC - 1)); 986 987 /* 988 * Set the End-Of-Buffer counter such that only one packet 989 * will be placed into each buffer we provide. Note we are 990 * following the recommendation of section 3.4.4 of the manual 991 * here, and have "lengthened" the receive buffers accordingly. 992 */ 993 if (sc->sc_32bit) 994 CSR_WRITE(sc, SONIC_EOBC, (ETHER_MAX_LEN + 2) / 2); 995 else 996 CSR_WRITE(sc, SONIC_EOBC, (ETHER_MAX_LEN / 2)); 997 998 /* Reset the receive sequence counter. */ 999 CSR_WRITE(sc, SONIC_RSC, 0); 1000 1001 /* Clear the tally registers. */ 1002 CSR_WRITE(sc, SONIC_CRCETC, 0xffff); 1003 CSR_WRITE(sc, SONIC_FAET, 0xffff); 1004 CSR_WRITE(sc, SONIC_MPT, 0xffff); 1005 1006 /* Set the receive filter. */ 1007 sonic_set_filter(sc); 1008 1009 /* 1010 * Set the interrupt mask register. 1011 */ 1012 sc->sc_imr = IMR_RFO | IMR_RBA | IMR_RBE | IMR_RDE | 1013 IMR_TXER | IMR_PTX | IMR_PRX; 1014 CSR_WRITE(sc, SONIC_IMR, sc->sc_imr); 1015 1016 /* 1017 * Start the receive process in motion. Note, we don't 1018 * start the transmit process until we actually try to 1019 * transmit packets. 1020 */ 1021 CSR_WRITE(sc, SONIC_CR, CR_RXEN | CR_RRRA); 1022 1023 /* 1024 * ...all done! 1025 */ 1026 ifp->if_flags |= IFF_RUNNING; 1027 ifp->if_flags &= ~IFF_OACTIVE; 1028 1029 out: 1030 if (error) 1031 printf("%s: interface not running\n", device_xname(sc->sc_dev)); 1032 return error; 1033} 1034 1035/* 1036 * sonic_rxdrain: 1037 * 1038 * Drain the receive queue. 1039 */ 1040void 1041sonic_rxdrain(struct sonic_softc *sc) 1042{ 1043 struct sonic_descsoft *ds; 1044 int i; 1045 1046 for (i = 0; i < SONIC_NRXDESC; i++) { 1047 ds = &sc->sc_rxsoft[i]; 1048 if (ds->ds_mbuf != NULL) { 1049 bus_dmamap_unload(sc->sc_dmat, ds->ds_dmamap); 1050 m_freem(ds->ds_mbuf); 1051 ds->ds_mbuf = NULL; 1052 } 1053 } 1054} 1055 1056/* 1057 * sonic_stop: [ifnet interface function] 1058 * 1059 * Stop transmission on the interface. 1060 */ 1061void 1062sonic_stop(struct ifnet *ifp, int disable) 1063{ 1064 struct sonic_softc *sc = ifp->if_softc; 1065 struct sonic_descsoft *ds; 1066 int i; 1067 1068 /* 1069 * Disable interrupts. 1070 */ 1071 CSR_WRITE(sc, SONIC_IMR, 0); 1072 1073 /* 1074 * Stop the transmitter, receiver, and timer. 1075 */ 1076 CSR_WRITE(sc, SONIC_CR, CR_HTX|CR_RXDIS|CR_STP); 1077 for (i = 0; i < 1000; i++) { 1078 if ((CSR_READ(sc, SONIC_CR) & (CR_TXP|CR_RXEN|CR_ST)) == 0) 1079 break; 1080 delay(2); 1081 } 1082 if ((CSR_READ(sc, SONIC_CR) & (CR_TXP|CR_RXEN|CR_ST)) != 0) 1083 printf("%s: SONIC failed to stop\n", device_xname(sc->sc_dev)); 1084 1085 /* 1086 * Release any queued transmit buffers. 1087 */ 1088 for (i = 0; i < SONIC_NTXDESC; i++) { 1089 ds = &sc->sc_txsoft[i]; 1090 if (ds->ds_mbuf != NULL) { 1091 bus_dmamap_unload(sc->sc_dmat, ds->ds_dmamap); 1092 m_freem(ds->ds_mbuf); 1093 ds->ds_mbuf = NULL; 1094 } 1095 } 1096 1097 /* 1098 * Mark the interface down and cancel the watchdog timer. 1099 */ 1100 ifp->if_flags &= ~(IFF_RUNNING | IFF_OACTIVE); 1101 ifp->if_timer = 0; 1102 1103 if (disable) 1104 sonic_rxdrain(sc); 1105} 1106 1107/* 1108 * sonic_add_rxbuf: 1109 * 1110 * Add a receive buffer to the indicated descriptor. 1111 */ 1112int 1113sonic_add_rxbuf(struct sonic_softc *sc, int idx) 1114{ 1115 struct sonic_descsoft *ds = &sc->sc_rxsoft[idx]; 1116 struct mbuf *m; 1117 int error; 1118 1119 MGETHDR(m, M_DONTWAIT, MT_DATA); 1120 if (m == NULL) 1121 return ENOBUFS; 1122 1123 MCLGET(m, M_DONTWAIT); 1124 if ((m->m_flags & M_EXT) == 0) { 1125 m_freem(m); 1126 return ENOBUFS; 1127 } 1128 1129 if (ds->ds_mbuf != NULL) 1130 bus_dmamap_unload(sc->sc_dmat, ds->ds_dmamap); 1131 1132 ds->ds_mbuf = m; 1133 1134 error = bus_dmamap_load(sc->sc_dmat, ds->ds_dmamap, 1135 m->m_ext.ext_buf, m->m_ext.ext_size, NULL, 1136 BUS_DMA_READ|BUS_DMA_NOWAIT); 1137 if (error) { 1138 printf("%s: can't load rx DMA map %d, error = %d\n", 1139 device_xname(sc->sc_dev), idx, error); 1140 panic("sonic_add_rxbuf"); /* XXX */ 1141 } 1142 1143 bus_dmamap_sync(sc->sc_dmat, ds->ds_dmamap, 0, 1144 ds->ds_dmamap->dm_mapsize, BUS_DMASYNC_PREREAD); 1145 1146 SONIC_INIT_RXDESC(sc, idx); 1147 1148 return 0; 1149} 1150 1151static void 1152sonic_set_camentry(struct sonic_softc *sc, int entry, const uint8_t *enaddr) 1153{ 1154 1155 if (sc->sc_32bit) { 1156 struct sonic_cda32 *cda = &sc->sc_cda32[entry]; 1157 1158 cda->cda_entry = htosonic32(sc, entry); 1159 cda->cda_addr0 = htosonic32(sc, enaddr[0] | (enaddr[1] << 8)); 1160 cda->cda_addr1 = htosonic32(sc, enaddr[2] | (enaddr[3] << 8)); 1161 cda->cda_addr2 = htosonic32(sc, enaddr[4] | (enaddr[5] << 8)); 1162 } else { 1163 struct sonic_cda16 *cda = &sc->sc_cda16[entry]; 1164 1165 cda->cda_entry = htosonic16(sc, entry); 1166 cda->cda_addr0 = htosonic16(sc, enaddr[0] | (enaddr[1] << 8)); 1167 cda->cda_addr1 = htosonic16(sc, enaddr[2] | (enaddr[3] << 8)); 1168 cda->cda_addr2 = htosonic16(sc, enaddr[4] | (enaddr[5] << 8)); 1169 } 1170} 1171 1172/* 1173 * sonic_set_filter: 1174 * 1175 * Set the SONIC receive filter. 1176 */ 1177void 1178sonic_set_filter(struct sonic_softc *sc) 1179{ 1180 struct ethercom *ec = &sc->sc_ethercom; 1181 struct ifnet *ifp = &sc->sc_ethercom.ec_if; 1182 struct ether_multi *enm; 1183 struct ether_multistep step; 1184 int i, entry = 0; 1185 uint16_t camvalid = 0; 1186 uint16_t rcr = 0; 1187 1188 if (ifp->if_flags & IFF_BROADCAST) 1189 rcr |= RCR_BRD; 1190 1191 if (ifp->if_flags & IFF_PROMISC) { 1192 rcr |= RCR_PRO; 1193 goto allmulti; 1194 } 1195 1196 /* Put our station address in the first CAM slot. */ 1197 sonic_set_camentry(sc, entry, CLLADDR(ifp->if_sadl)); 1198 camvalid |= (1U << entry); 1199 entry++; 1200 1201 /* Add the multicast addresses to the CAM. */ 1202 ETHER_FIRST_MULTI(step, ec, enm); 1203 while (enm != NULL) { 1204 if (memcmp(enm->enm_addrlo, enm->enm_addrhi, ETHER_ADDR_LEN)) { 1205 /* 1206 * We must listen to a range of multicast addresses. 1207 * The only way to do this on the SONIC is to enable 1208 * reception of all multicast packets. 1209 */ 1210 goto allmulti; 1211 } 1212 1213 if (entry == SONIC_NCAMENT) { 1214 /* 1215 * Out of CAM slots. Have to enable reception 1216 * of all multicast addresses. 1217 */ 1218 goto allmulti; 1219 } 1220 1221 sonic_set_camentry(sc, entry, enm->enm_addrlo); 1222 camvalid |= (1U << entry); 1223 entry++; 1224 1225 ETHER_NEXT_MULTI(step, enm); 1226 } 1227 1228 ifp->if_flags &= ~IFF_ALLMULTI; 1229 goto setit; 1230 1231 allmulti: 1232 /* Use only the first CAM slot (station address). */ 1233 camvalid = 0x0001; 1234 entry = 1; 1235 rcr |= RCR_AMC; 1236 1237 setit: 1238 /* set mask for the CAM Enable register */ 1239 if (sc->sc_32bit) { 1240 if (entry == SONIC_NCAMENT) 1241 sc->sc_cdaenable32 = htosonic32(sc, camvalid); 1242 else 1243 sc->sc_cda32[entry].cda_entry = 1244 htosonic32(sc, camvalid); 1245 } else { 1246 if (entry == SONIC_NCAMENT) 1247 sc->sc_cdaenable16 = htosonic16(sc, camvalid); 1248 else 1249 sc->sc_cda16[entry].cda_entry = 1250 htosonic16(sc, camvalid); 1251 } 1252 1253 /* Load the CAM. */ 1254 SONIC_CDCAMSYNC(sc, BUS_DMASYNC_PREWRITE); 1255 CSR_WRITE(sc, SONIC_CDP, SONIC_CDCAMADDR(sc) & 0xffff); 1256 CSR_WRITE(sc, SONIC_CDC, entry); 1257 CSR_WRITE(sc, SONIC_CR, CR_LCAM); 1258 for (i = 0; i < 10000; i++) { 1259 if ((CSR_READ(sc, SONIC_CR) & CR_LCAM) == 0) 1260 break; 1261 delay(2); 1262 } 1263 if (CSR_READ(sc, SONIC_CR) & CR_LCAM) 1264 printf("%s: CAM load failed\n", device_xname(sc->sc_dev)); 1265 SONIC_CDCAMSYNC(sc, BUS_DMASYNC_POSTWRITE); 1266 1267 /* Set the receive control register. */ 1268 CSR_WRITE(sc, SONIC_RCR, rcr); 1269} 1270