seeq8005.c revision 1.8
1/* $NetBSD: seeq8005.c,v 1.8 2000/12/23 16:37:20 bjh21 Exp $ */ 2 3/* 4 * Copyright (c) 2000 Ben Harris 5 * Copyright (c) 1995 Mark Brinicombe 6 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions 10 * are met: 11 * 1. Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * 2. Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in the 15 * documentation and/or other materials provided with the distribution. 16 * 3. All advertising materials mentioning features or use of this software 17 * must display the following acknowledgement: 18 * This product includes software developed by Mark Brinicombe. 19 * 4. The name of the company nor the name of the author may be used to 20 * endorse or promote products derived from this software without specific 21 * prior written permission. 22 * 23 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED 24 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 25 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 26 * IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, 27 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 28 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 29 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 30 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 31 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 32 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 33 * SUCH DAMAGE. 34 */ 35/* 36 * seeq8005.c - SEEQ 8005 device driver 37 */ 38/* 39 * This driver currently supports the following chip: 40 * SEEQ 8005 Advanced Ethernet Data Link Controller 41 */ 42/* 43 * This driver is based on the arm32 ea(4) driver, hence the names of many 44 * of the functions. 45 */ 46/* 47 * Bugs/possible improvements: 48 * - Does not currently support DMA 49 * - Does not currently support multicasts 50 * - Does not transmit multiple packets in one go 51 * - Does not support big-endian hosts 52 * - Does not support 8-bit busses 53 */ 54 55#include "opt_inet.h" 56#include "opt_ns.h" 57 58#include <sys/types.h> 59#include <sys/param.h> 60 61__RCSID("$NetBSD: seeq8005.c,v 1.8 2000/12/23 16:37:20 bjh21 Exp $"); 62 63#include <sys/systm.h> 64#include <sys/endian.h> 65#include <sys/errno.h> 66#include <sys/ioctl.h> 67#include <sys/mbuf.h> 68#include <sys/socket.h> 69#include <sys/syslog.h> 70#include <sys/device.h> 71 72#include <net/if.h> 73#include <net/if_dl.h> 74#include <net/if_types.h> 75#include <net/if_ether.h> 76 77#ifdef INET 78#include <netinet/in.h> 79#include <netinet/in_systm.h> 80#include <netinet/in_var.h> 81#include <netinet/ip.h> 82#include <netinet/if_inarp.h> 83#endif 84 85#ifdef NS 86#include <netns/ns.h> 87#include <netns/ns_if.h> 88#endif 89 90#include "bpfilter.h" 91#if NBPFILTER > 0 92#include <net/bpf.h> 93#include <net/bpfdesc.h> 94#endif 95 96#include <machine/bus.h> 97#include <machine/intr.h> 98 99#include <dev/ic/seeq8005reg.h> 100#include <dev/ic/seeq8005var.h> 101 102#ifndef EA_TIMEOUT 103#define EA_TIMEOUT 60 104#endif 105 106#define EA_TX_BUFFER_SIZE 0x4000 107#define EA_RX_BUFFER_SIZE 0xC000 108 109/*#define EA_TX_DEBUG*/ 110/*#define EA_RX_DEBUG*/ 111/*#define EA_DEBUG*/ 112/*#define EA_PACKET_DEBUG*/ 113 114/* for debugging convenience */ 115#ifdef EA_DEBUG 116#define dprintf(x) printf x 117#else 118#define dprintf(x) 119#endif 120 121/* 122 * prototypes 123 */ 124 125static int ea_init(struct ifnet *); 126static int ea_ioctl(struct ifnet *, u_long, caddr_t); 127static void ea_start(struct ifnet *); 128static void ea_watchdog(struct ifnet *); 129static void ea_chipreset(struct seeq8005_softc *); 130static void ea_ramtest(struct seeq8005_softc *); 131static int ea_stoptx(struct seeq8005_softc *); 132static int ea_stoprx(struct seeq8005_softc *); 133static void ea_stop(struct ifnet *, int); 134static void ea_await_fifo_empty(struct seeq8005_softc *); 135static void ea_await_fifo_full(struct seeq8005_softc *); 136static void ea_writebuf(struct seeq8005_softc *, u_char *, u_int, size_t); 137static void ea_readbuf(struct seeq8005_softc *, u_char *, u_int, size_t); 138static void ea_select_buffer(struct seeq8005_softc *, int); 139static void ea_set_address(struct seeq8005_softc *, int, const u_int8_t *); 140static void earead(struct seeq8005_softc *, int, int); 141static struct mbuf *eaget(struct seeq8005_softc *, int, int, struct ifnet *); 142static void eagetpackets(struct seeq8005_softc *); 143static void eatxpacket(struct seeq8005_softc *); 144static void ea_mc_reset(struct seeq8005_softc *); 145 146 147#ifdef EA_PACKET_DEBUG 148void ea_dump_buffer(struct seeq8005_softc *, int); 149#endif 150 151 152#ifdef EA_PACKET_DEBUG 153/* 154 * Dump the interface buffer 155 */ 156 157void 158ea_dump_buffer(struct seeq8005_softc *sc, u_int offset) 159{ 160 bus_space_tag_t iot = sc->sc_iot; 161 bus_space_handle_t ioh = sc->sc_ioh; 162 u_int addr; 163 int loop, ctrl, ptr; 164 size_t size; 165 166 addr = offset; 167 168 do { 169 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 170 sc->sc_command | EA_CMD_FIFO_READ); 171 bus_space_write_2(iot, ioh, EA_8005_CONFIG1, 172 sc->sc_config1 | EA_BUFCODE_LOCAL_MEM); 173 bus_space_write_2(iot, ioh, EA_8005_DMA_ADDR, addr); 174 175 ptr = bus_space_read_2(iot, ioh, EA_8005_BUFWIN); 176 ctrl = bus_space_read_2(iot, ioh, EA_8005_BUFWIN); 177 ptr = ((ptr & 0xff) << 8) | ((ptr >> 8) & 0xff); 178 179 if (ptr == 0) break; 180 size = ptr - addr; 181 182 printf("addr=%04x size=%04x ", addr, size); 183 printf("cmd=%02x st=%02x\n", ctrl & 0xff, ctrl >> 8); 184 185 for (loop = 0; loop < size - 4; loop += 2) 186 printf("%04x ", 187 bus_space_read_2(iot, ioh, EA_8005_BUFWIN)); 188 printf("\n"); 189 addr = ptr; 190 } while (size != 0); 191} 192#endif 193 194/* 195 * Attach chip. 196 */ 197 198void 199seeq8005_attach(struct seeq8005_softc *sc, const u_int8_t *myaddr) 200{ 201 struct ifnet *ifp = &sc->sc_ethercom.ec_if; 202 u_int id; 203 204 printf(" address %s", ether_sprintf(myaddr)); 205 206 /* Stop the board. */ 207 208 ea_chipreset(sc); 209 210 /* Get the product ID */ 211 212 ea_select_buffer(sc, EA_BUFCODE_PRODUCTID); 213 id = bus_space_read_2(sc->sc_iot, sc->sc_ioh, EA_8005_BUFWIN); 214 215 if ((id & 0xf0) == 0xa0) { 216 sc->sc_flags |= SEEQ8005_80C04; 217 printf(", SEEQ 80C04 rev %02x", id); 218 } else 219 printf(", SEEQ 8005"); 220 221 /* Initialise ifnet structure. */ 222 223 bcopy(sc->sc_dev.dv_xname, ifp->if_xname, IFNAMSIZ); 224 ifp->if_softc = sc; 225 ifp->if_start = ea_start; 226 ifp->if_ioctl = ea_ioctl; 227 ifp->if_init = ea_init; 228 ifp->if_stop = ea_stop; 229 ifp->if_watchdog = ea_watchdog; 230 ifp->if_flags = IFF_BROADCAST | IFF_MULTICAST | IFF_NOTRAILERS; 231 IFQ_SET_READY(&ifp->if_snd); 232 233 /* Now we can attach the interface. */ 234 235 if_attach(ifp); 236 ether_ifattach(ifp, myaddr); 237 238 /* Test the RAM */ 239 ea_ramtest(sc); 240 241 printf("\n"); 242} 243 244 245/* 246 * Test the RAM on the ethernet card. 247 */ 248 249void 250ea_ramtest(struct seeq8005_softc *sc) 251{ 252 bus_space_tag_t iot = sc->sc_iot; 253 bus_space_handle_t ioh = sc->sc_ioh; 254 int loop; 255 u_int sum = 0; 256 257/* dprintf(("ea_ramtest()\n"));*/ 258 259 /* 260 * Test the buffer memory on the board. 261 * Write simple pattens to it and read them back. 262 */ 263 264 /* Set up the whole buffer RAM for writing */ 265 266 ea_select_buffer(sc, EA_BUFCODE_TX_EAP); 267 bus_space_write_2(iot, ioh, EA_8005_BUFWIN, (EA_BUFFER_SIZE >> 8) - 1); 268 bus_space_write_2(iot, ioh, EA_8005_TX_PTR, 0x0000); 269 bus_space_write_2(iot, ioh, EA_8005_RX_PTR, EA_BUFFER_SIZE - 2); 270 271#define EA_RAMTEST_LOOP(value) \ 272do { \ 273 /* Set the write start address and write a pattern */ \ 274 ea_writebuf(sc, NULL, 0x0000, 0); \ 275 for (loop = 0; loop < EA_BUFFER_SIZE; loop += 2) \ 276 bus_space_write_2(iot, ioh, EA_8005_BUFWIN, (value)); \ 277 \ 278 /* Set the read start address and verify the pattern */ \ 279 ea_readbuf(sc, NULL, 0x0000, 0); \ 280 for (loop = 0; loop < EA_BUFFER_SIZE; loop += 2) \ 281 if (bus_space_read_2(iot, ioh, EA_8005_BUFWIN) != (value)) \ 282 ++sum; \ 283 if (sum != 0) \ 284 dprintf(("sum=%d\n", sum)); \ 285} while (/*CONSTCOND*/0) 286 287 EA_RAMTEST_LOOP(loop); 288 EA_RAMTEST_LOOP(loop ^ (EA_BUFFER_SIZE - 1)); 289 EA_RAMTEST_LOOP(0xaa55); 290 EA_RAMTEST_LOOP(0x55aa); 291 292 /* Report */ 293 294 if (sum > 0) 295 printf("%s: buffer RAM failed self test, %d faults\n", 296 sc->sc_dev.dv_xname, sum); 297} 298 299 300/* 301 * Stop the tx interface. 302 * 303 * Returns 0 if the tx was already stopped or 1 if it was active 304 */ 305 306static int 307ea_stoptx(struct seeq8005_softc *sc) 308{ 309 bus_space_tag_t iot = sc->sc_iot; 310 bus_space_handle_t ioh = sc->sc_ioh; 311 int timeout; 312 int status; 313 314 dprintf(("ea_stoptx()\n")); 315 316 status = bus_space_read_2(iot, ioh, EA_8005_STATUS); 317 if (!(status & EA_STATUS_TX_ON)) 318 return 0; 319 320 /* Stop any tx and wait for confirmation */ 321 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 322 sc->sc_command | EA_CMD_TX_OFF); 323 324 timeout = 20000; 325 do { 326 status = bus_space_read_2(iot, ioh, EA_8005_STATUS); 327 } while ((status & EA_STATUS_TX_ON) && --timeout > 0); 328 if (timeout == 0) 329 dprintf(("ea_stoptx: timeout waiting for tx termination\n")); 330 331 /* Clear any pending tx interrupt */ 332 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 333 sc->sc_command | EA_CMD_TX_INTACK); 334 return 1; 335} 336 337 338/* 339 * Stop the rx interface. 340 * 341 * Returns 0 if the tx was already stopped or 1 if it was active 342 */ 343 344static int 345ea_stoprx(struct seeq8005_softc *sc) 346{ 347 bus_space_tag_t iot = sc->sc_iot; 348 bus_space_handle_t ioh = sc->sc_ioh; 349 int timeout; 350 int status; 351 352 dprintf(("ea_stoprx()\n")); 353 354 status = bus_space_read_2(iot, ioh, EA_8005_STATUS); 355 if (!(status & EA_STATUS_RX_ON)) 356 return 0; 357 358 /* Stop any rx and wait for confirmation */ 359 360 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 361 sc->sc_command | EA_CMD_RX_OFF); 362 363 timeout = 20000; 364 do { 365 status = bus_space_read_2(iot, ioh, EA_8005_STATUS); 366 } while ((status & EA_STATUS_RX_ON) && --timeout > 0); 367 if (timeout == 0) 368 dprintf(("ea_stoprx: timeout waiting for rx termination\n")); 369 370 /* Clear any pending rx interrupt */ 371 372 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 373 sc->sc_command | EA_CMD_RX_INTACK); 374 return 1; 375} 376 377 378/* 379 * Stop interface. 380 * Stop all IO and shut the interface down 381 */ 382 383static void 384ea_stop(struct ifnet *ifp, int disable) 385{ 386 struct seeq8005_softc *sc = ifp->if_softc; 387 bus_space_tag_t iot = sc->sc_iot; 388 bus_space_handle_t ioh = sc->sc_ioh; 389 390 dprintf(("ea_stop()\n")); 391 392 /* Stop all IO */ 393 ea_stoptx(sc); 394 ea_stoprx(sc); 395 396 /* Disable rx and tx interrupts */ 397 sc->sc_command &= (EA_CMD_RX_INTEN | EA_CMD_TX_INTEN); 398 399 /* Clear any pending interrupts */ 400 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 401 sc->sc_command | EA_CMD_RX_INTACK | 402 EA_CMD_TX_INTACK | EA_CMD_DMA_INTACK | 403 EA_CMD_BW_INTACK); 404 dprintf(("st=%08x", bus_space_read_2(iot, ioh, EA_8005_STATUS))); 405 406 /* Cancel any watchdog timer */ 407 sc->sc_ethercom.ec_if.if_timer = 0; 408} 409 410 411/* 412 * Reset the chip 413 * Following this the software registers are reset 414 */ 415 416static void 417ea_chipreset(struct seeq8005_softc *sc) 418{ 419 bus_space_tag_t iot = sc->sc_iot; 420 bus_space_handle_t ioh = sc->sc_ioh; 421 422 dprintf(("ea_chipreset()\n")); 423 424 /* Reset the controller. Min of 4us delay here */ 425 426 bus_space_write_2(iot, ioh, EA_8005_CONFIG2, EA_CFG2_RESET); 427 delay(4); 428 429 sc->sc_command = 0; 430 sc->sc_config1 = 0; 431 sc->sc_config2 = 0; 432} 433 434 435/* 436 * If the DMA FIFO's in write mode, wait for it to empty. Needed when 437 * switching the FIFO from write to read. We also use it when changing 438 * the address for writes. 439 */ 440static void 441ea_await_fifo_empty(struct seeq8005_softc *sc) 442{ 443 bus_space_tag_t iot = sc->sc_iot; 444 bus_space_handle_t ioh = sc->sc_ioh; 445 int timeout; 446 447 timeout = 20000; 448 if ((bus_space_read_2(iot, ioh, EA_8005_STATUS) & 449 EA_STATUS_FIFO_DIR) != 0) 450 return; /* FIFO is reading anyway. */ 451 while ((bus_space_read_2(iot, ioh, EA_8005_STATUS) & 452 EA_STATUS_FIFO_EMPTY) == 0 && 453 --timeout > 0) 454 continue; 455} 456 457/* 458 * Wait for the DMA FIFO to fill before reading from it. 459 */ 460static void 461ea_await_fifo_full(struct seeq8005_softc *sc) 462{ 463 bus_space_tag_t iot = sc->sc_iot; 464 bus_space_handle_t ioh = sc->sc_ioh; 465 int timeout; 466 467 timeout = 20000; 468 while ((bus_space_read_2(iot, ioh, EA_8005_STATUS) & 469 EA_STATUS_FIFO_FULL) == 0 && 470 --timeout > 0) 471 continue; 472} 473 474/* 475 * write to the buffer memory on the interface 476 * 477 * The buffer address is set to ADDR. 478 * If len != 0 then data is copied from the address starting at buf 479 * to the interface buffer. 480 * BUF must be usable as a u_int16_t *. 481 * If LEN is odd, it must be safe to overwrite one extra byte. 482 */ 483 484static void 485ea_writebuf(struct seeq8005_softc *sc, u_char *buf, u_int addr, size_t len) 486{ 487 bus_space_tag_t iot = sc->sc_iot; 488 bus_space_handle_t ioh = sc->sc_ioh; 489 490 dprintf(("writebuf: st=%04x\n", 491 bus_space_read_2(iot, ioh, EA_8005_STATUS))); 492 493#ifdef DIAGNOSTIC 494 if (__predict_false(!ALIGNED_POINTER(buf, u_int16_t))) 495 panic("%s: unaligned writebuf", sc->sc_dev.dv_xname); 496#endif 497 if (__predict_false(addr >= EA_BUFFER_SIZE)) 498 panic("%s: writebuf out of range", sc->sc_dev.dv_xname); 499 500 /* Assume that copying too much is safe. */ 501 if (len % 2 != 0) 502 len++; 503 504 ea_await_fifo_empty(sc); 505 506 ea_select_buffer(sc, EA_BUFCODE_LOCAL_MEM); 507 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 508 sc->sc_command | EA_CMD_FIFO_WRITE); 509 bus_space_write_2(iot, ioh, EA_8005_DMA_ADDR, addr); 510 511 if (len > 0) 512 bus_space_write_multi_2(iot, ioh, EA_8005_BUFWIN, 513 (u_int16_t *)buf, len / 2); 514 /* Leave FIFO to empty in the background */ 515} 516 517 518/* 519 * read from the buffer memory on the interface 520 * 521 * The buffer address is set to ADDR. 522 * If len != 0 then data is copied from the interface buffer to the 523 * address starting at buf. 524 * BUF must be usable as a u_int16_t *. 525 * If LEN is odd, it must be safe to overwrite one extra byte. 526 */ 527 528static void 529ea_readbuf(struct seeq8005_softc *sc, u_char *buf, u_int addr, size_t len) 530{ 531 532 bus_space_tag_t iot = sc->sc_iot; 533 bus_space_handle_t ioh = sc->sc_ioh; 534 535 dprintf(("readbuf: st=%04x addr=%04x len=%d\n", 536 bus_space_read_2(iot, ioh, EA_8005_STATUS), addr, len)); 537 538#ifdef DIAGNOSTIC 539 if (!ALIGNED_POINTER(buf, u_int16_t)) 540 panic("%s: unaligned readbuf", sc->sc_dev.dv_xname); 541#endif 542 if (addr >= EA_BUFFER_SIZE) 543 panic("%s: writebuf out of range", sc->sc_dev.dv_xname); 544 545 /* Assume that copying too much is safe. */ 546 if (len % 2 != 0) 547 len++; 548 549 ea_await_fifo_empty(sc); 550 551 ea_select_buffer(sc, EA_BUFCODE_LOCAL_MEM); 552 bus_space_write_2(iot, ioh, EA_8005_DMA_ADDR, addr); 553 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 554 sc->sc_command | EA_CMD_FIFO_READ); 555 556 ea_await_fifo_full(sc); 557 558 if (len > 0) 559 bus_space_read_multi_2(iot, ioh, EA_8005_BUFWIN, 560 (u_int16_t *)buf, len / 2); 561} 562 563static void 564ea_select_buffer(struct seeq8005_softc *sc, int bufcode) 565{ 566 567 bus_space_write_2(sc->sc_iot, sc->sc_ioh, EA_8005_CONFIG1, 568 sc->sc_config1 | bufcode); 569} 570 571/* Must be called at splnet */ 572static void 573ea_set_address(struct seeq8005_softc *sc, int which, u_int8_t const *ea) 574{ 575 int i; 576 577 ea_select_buffer(sc, EA_BUFCODE_STATION_ADDR0 + which); 578 for (i = 0; i < ETHER_ADDR_LEN; ++i) 579 bus_space_write_2(sc->sc_iot, sc->sc_ioh, EA_8005_BUFWIN, 580 ea[i]); 581} 582 583/* 584 * Initialize interface. 585 * 586 * This should leave the interface in a state for packet reception and 587 * transmission. 588 */ 589 590static int 591ea_init(struct ifnet *ifp) 592{ 593 struct seeq8005_softc *sc = ifp->if_softc; 594 bus_space_tag_t iot = sc->sc_iot; 595 bus_space_handle_t ioh = sc->sc_ioh; 596 int s; 597 598 dprintf(("ea_init()\n")); 599 600 s = splnet(); 601 602 /* First, reset the board. */ 603 604 ea_chipreset(sc); 605 606 /* Set up defaults for the registers */ 607 608 sc->sc_command = 0x00; 609 sc->sc_config1 = 0x00; /* XXX DMA settings? */ 610#if BYTE_ORDER == BIG_ENDIAN 611 sc->sc_config2 = EA_CFG2_BYTESWAP 612#else 613 sc->sc_config2 = 0; 614#endif 615 616 bus_space_write_2(iot, ioh, EA_8005_COMMAND, sc->sc_command); 617 bus_space_write_2(iot, ioh, EA_8005_CONFIG1, sc->sc_config1); 618 bus_space_write_2(iot, ioh, EA_8005_CONFIG2, sc->sc_config2); 619 620 /* Split board memory into Rx and Tx. */ 621 ea_select_buffer(sc, EA_BUFCODE_TX_EAP); 622 bus_space_write_2(iot, ioh, EA_8005_BUFWIN, 623 (EA_TX_BUFFER_SIZE >> 8) - 1); 624 625 /* Write the station address - the receiver must be off */ 626 ea_set_address(sc, 0, LLADDR(ifp->if_sadl)); 627 628 /* Configure rx. */ 629 dprintf(("Configuring rx...\n")); 630 if (ifp->if_flags & IFF_PROMISC) 631 sc->sc_config1 = EA_CFG1_PROMISCUOUS; 632 else 633 sc->sc_config1 = EA_CFG1_BROADCAST; 634 sc->sc_config1 |= EA_CFG1_STATION_ADDR0; 635 bus_space_write_2(iot, ioh, EA_8005_CONFIG1, sc->sc_config1); 636 637 /* Setup the Rx pointers */ 638 sc->sc_rx_ptr = EA_TX_BUFFER_SIZE; 639 640 bus_space_write_2(iot, ioh, EA_8005_RX_PTR, sc->sc_rx_ptr); 641 bus_space_write_2(iot, ioh, EA_8005_RX_END, sc->sc_rx_ptr >> 8); 642 643 644 /* Place a NULL header at the beginning of the receive area */ 645 ea_writebuf(sc, NULL, sc->sc_rx_ptr, 0); 646 647 bus_space_write_2(iot, ioh, EA_8005_BUFWIN, 0x0000); 648 bus_space_write_2(iot, ioh, EA_8005_BUFWIN, 0x0000); 649 650 651 /* Turn on Rx */ 652 sc->sc_command |= EA_CMD_RX_INTEN; 653 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 654 sc->sc_command | EA_CMD_RX_ON); 655 656 657 /* Configure TX. */ 658 dprintf(("Configuring tx...\n")); 659 660 bus_space_write_2(iot, ioh, EA_8005_TX_PTR, 0x0000); 661 662 sc->sc_config2 |= EA_CFG2_OUTPUT; 663 bus_space_write_2(iot, ioh, EA_8005_CONFIG2, sc->sc_config2); 664 665 666 /* Place a NULL header at the beginning of the transmit area */ 667 ea_writebuf(sc, NULL, 0x0000, 0); 668 669 bus_space_write_2(iot, ioh, EA_8005_BUFWIN, 0x0000); 670 bus_space_write_2(iot, ioh, EA_8005_BUFWIN, 0x0000); 671 672 sc->sc_command |= EA_CMD_TX_INTEN; 673 bus_space_write_2(iot, ioh, EA_8005_COMMAND, sc->sc_command); 674 675 /* TX_ON gets set by ea_txpacket when there's something to transmit. */ 676 677 678 /* Set flags appropriately. */ 679 ifp->if_flags |= IFF_RUNNING; 680 ifp->if_flags &= ~IFF_OACTIVE; 681 682 dprintf(("init: st=%04x\n", 683 bus_space_read_2(iot, ioh, EA_8005_STATUS))); 684 685 686 /* And start output. */ 687 ea_start(ifp); 688 689 splx(s); 690 return 0; 691} 692 693 694/* 695 * Start output on interface. Get datagrams from the queue and output them, 696 * giving the receiver a chance between datagrams. Call only from splnet or 697 * interrupt level! 698 */ 699 700static void 701ea_start(struct ifnet *ifp) 702{ 703 struct seeq8005_softc *sc = ifp->if_softc; 704 int s; 705 706 s = splnet(); 707#ifdef EA_TX_DEBUG 708 dprintf(("ea_start()...\n")); 709#endif 710 711 /* Don't do anything if output is active. */ 712 713 if (ifp->if_flags & IFF_OACTIVE) 714 return; 715 716 /* Mark interface as output active */ 717 718 ifp->if_flags |= IFF_OACTIVE; 719 720 /* tx packets */ 721 722 eatxpacket(sc); 723 splx(s); 724} 725 726 727/* 728 * Transfer a packet to the interface buffer and start transmission 729 * 730 * Called at splnet() 731 */ 732 733void 734eatxpacket(struct seeq8005_softc *sc) 735{ 736 bus_space_tag_t iot = sc->sc_iot; 737 bus_space_handle_t ioh = sc->sc_ioh; 738 struct mbuf *m, *m0; 739 struct ifnet *ifp; 740 int len, nextpacket; 741 u_int8_t hdr[4]; 742 743 ifp = &sc->sc_ethercom.ec_if; 744 745 /* Dequeue the next packet. */ 746 IFQ_DEQUEUE(&ifp->if_snd, m0); 747 748 /* If there's nothing to send, return. */ 749 if (!m0) { 750 ifp->if_flags &= ~IFF_OACTIVE; 751 sc->sc_config2 |= EA_CFG2_OUTPUT; 752 bus_space_write_2(iot, ioh, EA_8005_CONFIG2, sc->sc_config2); 753#ifdef EA_TX_DEBUG 754 dprintf(("tx finished\n")); 755#endif 756 return; 757 } 758 759#if NBPFILTER > 0 760 /* Give the packet to the bpf, if any. */ 761 if (ifp->if_bpf) 762 bpf_mtap(ifp->if_bpf, m0); 763#endif 764 765#ifdef EA_TX_DEBUG 766 dprintf(("Tx new packet\n")); 767#endif 768 769 sc->sc_config2 &= ~EA_CFG2_OUTPUT; 770 bus_space_write_2(iot, ioh, EA_8005_CONFIG2, sc->sc_config2); 771 772 /* 773 * Copy the frame to the start of the transmit area on the card, 774 * leaving four bytes for the transmit header. 775 */ 776 len = 0; 777 for (m = m0; m; m = m->m_next) { 778 if (m->m_len == 0) 779 continue; 780 ea_writebuf(sc, mtod(m, caddr_t), 4 + len, m->m_len); 781 len += m->m_len; 782 } 783 m_freem(m0); 784 785 786 /* If packet size is odd round up to the next 16 bit boundry */ 787 if (len % 2) 788 ++len; 789 790 len = max(len, ETHER_MIN_LEN); 791 792 if (len > (ETHER_MAX_LEN - ETHER_CRC_LEN)) 793 log(LOG_WARNING, "%s: oversize packet = %d bytes\n", 794 sc->sc_dev.dv_xname, len); 795 796#if 0 /*def EA_TX_DEBUG*/ 797 dprintf(("ea: xfr pkt length=%d...\n", len)); 798 799 dprintf(("%s-->", ether_sprintf(sc->sc_pktbuf+6))); 800 dprintf(("%s\n", ether_sprintf(sc->sc_pktbuf))); 801#endif 802 803/* dprintf(("st=%04x\n", bus_space_read_2(iot, ioh, EA_8005_STATUS)));*/ 804 805 /* Follow it with a NULL packet header */ 806 bus_space_write_2(iot, ioh, EA_8005_BUFWIN, 0x0000); 807 bus_space_write_2(iot, ioh, EA_8005_BUFWIN, 0x0000); 808 809 810 /* Write the packet header */ 811 812 nextpacket = len + 4; 813 hdr[0] = (nextpacket >> 8) & 0xff; 814 hdr[1] = nextpacket & 0xff; 815 hdr[2] = EA_PKTHDR_TX | EA_PKTHDR_DATA_FOLLOWS | 816 EA_TXHDR_XMIT_SUCCESS_INT | EA_TXHDR_COLLISION_INT; 817 hdr[3] = 0; /* Status byte -- will be update by hardware. */ 818 ea_writebuf(sc, hdr, 0x0000, 4); 819 820 bus_space_write_2(iot, ioh, EA_8005_TX_PTR, 0x0000); 821 822/* dprintf(("st=%04x\n", bus_space_read_2(iot, ioh, EA_8005_STATUS)));*/ 823 824#ifdef EA_PACKET_DEBUG 825 ea_dump_buffer(sc, 0); 826#endif 827 828 829 /* Now transmit the datagram. */ 830/* dprintf(("st=%04x\n", bus_space_read_2(iot, ioh, EA_8005_STATUS)));*/ 831 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 832 sc->sc_command | EA_CMD_TX_ON); 833#ifdef EA_TX_DEBUG 834 dprintf(("st=%04x\n", bus_space_read_2(iot, ioh, EA_8005_STATUS))); 835 dprintf(("tx: queued\n")); 836#endif 837} 838 839 840/* 841 * Ethernet controller interrupt. 842 */ 843 844int 845seeq8005intr(void *arg) 846{ 847 struct seeq8005_softc *sc = arg; 848 bus_space_tag_t iot = sc->sc_iot; 849 bus_space_handle_t ioh = sc->sc_ioh; 850 struct ifnet *ifp = &sc->sc_ethercom.ec_if; 851 int status, s, handled; 852 u_int8_t txhdr[4]; 853 u_int txstatus; 854 855 handled = 0; 856 dprintf(("eaintr: ")); 857 858 859 /* Get the controller status */ 860 status = bus_space_read_2(iot, ioh, EA_8005_STATUS); 861 dprintf(("st=%04x ", status)); 862 863 864 /* Tx interrupt ? */ 865 if (status & EA_STATUS_TX_INT) { 866 dprintf(("txint ")); 867 handled = 1; 868 869 /* Acknowledge the interrupt */ 870 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 871 sc->sc_command | EA_CMD_TX_INTACK); 872 873 ea_readbuf(sc, txhdr, 0x0000, 4); 874 875#ifdef EA_TX_DEBUG 876 dprintf(("txstatus=%02x %02x %02x %02x\n", 877 txhdr[0], txhdr[1], txhdr[2], txhdr[3])); 878#endif 879 txstatus = txhdr[3]; 880 881 /* 882 * Did it succeed ? Did we collide ? 883 * 884 * The exact proceedure here is not clear. We should get 885 * an interrupt on a sucessfull tx or on a collision. 886 * The done flag is set after successfull tx or 16 collisions 887 * We should thus get a interrupt for each of collision 888 * and the done bit should not be set. However it does appear 889 * to be set at the same time as the collision bit ... 890 * 891 * So we will count collisions and output errors and will 892 * assume that if the done bit is set the packet was 893 * transmitted. Stats may be wrong if 16 collisions occur on 894 * a packet as the done flag should be set but the packet 895 * may not have been transmitted. so the output count might 896 * not require incrementing if the 16 collisions flags is 897 * set. I don;t know abou this until it happens. 898 */ 899 900 if (txstatus & EA_TXHDR_COLLISION) 901 ifp->if_collisions++; 902 else if (txstatus & EA_TXHDR_ERROR_MASK) 903 ifp->if_oerrors++; 904 905#if 0 906 if (txstatus & EA_TXHDR_ERROR_MASK) 907 log(LOG_WARNING, "tx packet error =%02x\n", txstatus); 908#endif 909 910 if (txstatus & EA_PKTHDR_DONE) { 911 ifp->if_opackets++; 912 913 /* Tx next packet */ 914 915 s = splnet(); 916 eatxpacket(sc); 917 splx(s); 918 } 919 } 920 921 922 /* Rx interrupt ? */ 923 if (status & EA_STATUS_RX_INT) { 924 dprintf(("rxint ")); 925 handled = 1; 926 927 /* Acknowledge the interrupt */ 928 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 929 sc->sc_command | EA_CMD_RX_INTACK); 930 931 /* Install a watchdog timer needed atm to fixed rx lockups */ 932 ifp->if_timer = EA_TIMEOUT; 933 934 /* Processes the received packets */ 935 eagetpackets(sc); 936 937 938#if 0 939 /* Make sure the receiver is on */ 940 if ((status & EA_STATUS_RX_ON) == 0) { 941 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 942 sc->sc_command | EA_CMD_RX_ON); 943 printf("rxintr: rx is off st=%04x\n",status); 944 } 945#endif 946 } 947 948#ifdef EA_DEBUG 949 status = bus_space_read_2(iot, ioh, EA_8005_STATUS); 950 dprintf(("st=%04x\n", status)); 951#endif 952 953 return handled; 954} 955 956 957void 958eagetpackets(struct seeq8005_softc *sc) 959{ 960 bus_space_tag_t iot = sc->sc_iot; 961 bus_space_handle_t ioh = sc->sc_ioh; 962 u_int addr; 963 int len; 964 int ctrl; 965 int ptr; 966 int pack; 967 int status; 968 u_int8_t rxhdr[4]; 969 struct ifnet *ifp; 970 971 ifp = &sc->sc_ethercom.ec_if; 972 973 974 /* We start from the last rx pointer position */ 975 addr = sc->sc_rx_ptr; 976 sc->sc_config2 &= ~EA_CFG2_OUTPUT; 977 bus_space_write_2(iot, ioh, EA_8005_CONFIG2, sc->sc_config2); 978 979 do { 980 /* Read rx header */ 981 ea_readbuf(sc, rxhdr, addr, 4); 982 983 /* Split the packet header */ 984 ptr = (rxhdr[0] << 8) | rxhdr[1]; 985 ctrl = rxhdr[2]; 986 status = rxhdr[3]; 987 988#ifdef EA_RX_DEBUG 989 dprintf(("addr=%04x ptr=%04x ctrl=%02x status=%02x\n", 990 addr, ptr, ctrl, status)); 991#endif 992 993 994 /* Zero packet ptr ? then must be null header so exit */ 995 if (ptr == 0) break; 996 997 998 /* Get packet length */ 999 len = (ptr - addr) - 4; 1000 1001 if (len < 0) 1002 len += EA_RX_BUFFER_SIZE; 1003 1004#ifdef EA_RX_DEBUG 1005 dprintf(("len=%04x\n", len)); 1006#endif 1007 1008 1009 /* Has the packet rx completed ? if not then exit */ 1010 if ((status & EA_PKTHDR_DONE) == 0) 1011 break; 1012 1013 /* 1014 * Did we have any errors? then note error and go to 1015 * next packet 1016 */ 1017 if (__predict_false(status & 0x0f)) { 1018 ++ifp->if_ierrors; 1019 log(LOG_WARNING, 1020 "%s: rx packet error (%02x) - dropping packet\n", 1021 sc->sc_dev.dv_xname, status & 0x0f); 1022 sc->sc_config2 |= EA_CFG2_OUTPUT; 1023 bus_space_write_2(iot, ioh, EA_8005_CONFIG2, 1024 sc->sc_config2); 1025 ea_init(ifp); 1026 return; 1027 } 1028 1029 /* 1030 * Is the packet too big ? - this will probably be trapped 1031 * above as a receive error 1032 */ 1033 if (__predict_false(len > (ETHER_MAX_LEN - ETHER_CRC_LEN))) { 1034 ++ifp->if_ierrors; 1035 log(LOG_WARNING, "%s: rx packet size error len=%d\n", 1036 sc->sc_dev.dv_xname, len); 1037 sc->sc_config2 |= EA_CFG2_OUTPUT; 1038 bus_space_write_2(iot, ioh, EA_8005_CONFIG2, 1039 sc->sc_config2); 1040 ea_init(ifp); 1041 return; 1042 } 1043 1044 ifp->if_ipackets++; 1045 /* Pass data up to upper levels. */ 1046 earead(sc, addr + 4, len); 1047 1048 addr = ptr; 1049 ++pack; 1050 } while (len != 0); 1051 1052 sc->sc_config2 |= EA_CFG2_OUTPUT; 1053 bus_space_write_2(iot, ioh, EA_8005_CONFIG2, sc->sc_config2); 1054 1055#ifdef EA_RX_DEBUG 1056 dprintf(("new rx ptr=%04x\n", addr)); 1057#endif 1058 1059 1060 /* Store new rx pointer */ 1061 sc->sc_rx_ptr = addr; 1062 bus_space_write_2(iot, ioh, EA_8005_RX_END, sc->sc_rx_ptr >> 8); 1063 1064 /* Make sure the receiver is on */ 1065 bus_space_write_2(iot, ioh, EA_8005_COMMAND, 1066 sc->sc_command | EA_CMD_RX_ON); 1067 1068} 1069 1070 1071/* 1072 * Pass a packet up to the higher levels. 1073 */ 1074 1075static void 1076earead(struct seeq8005_softc *sc, int addr, int len) 1077{ 1078 struct mbuf *m; 1079 struct ifnet *ifp; 1080 1081 ifp = &sc->sc_ethercom.ec_if; 1082 1083 /* Pull packet off interface. */ 1084 m = eaget(sc, addr, len, ifp); 1085 if (m == 0) 1086 return; 1087 1088#ifdef EA_RX_DEBUG 1089 dprintf(("%s-->", ether_sprintf(eh->ether_shost))); 1090 dprintf(("%s\n", ether_sprintf(eh->ether_dhost))); 1091#endif 1092 1093#if NBPFILTER > 0 1094 /* 1095 * Check if there's a BPF listener on this interface. 1096 * If so, hand off the raw packet to bpf. 1097 */ 1098 if (ifp->if_bpf) 1099 bpf_mtap(ifp->if_bpf, m); 1100#endif 1101 1102 (*ifp->if_input)(ifp, m); 1103} 1104 1105/* 1106 * Pull read data off a interface. Len is length of data, with local net 1107 * header stripped. We copy the data into mbufs. When full cluster sized 1108 * units are present we copy into clusters. 1109 */ 1110 1111struct mbuf * 1112eaget(struct seeq8005_softc *sc, int addr, int totlen, struct ifnet *ifp) 1113{ 1114 struct mbuf *top, **mp, *m; 1115 int len; 1116 u_int cp, epkt; 1117 1118 cp = addr; 1119 epkt = cp + totlen; 1120 1121 MGETHDR(m, M_DONTWAIT, MT_DATA); 1122 if (m == 0) 1123 return 0; 1124 m->m_pkthdr.rcvif = ifp; 1125 m->m_pkthdr.len = totlen; 1126 m->m_len = MHLEN; 1127 top = 0; 1128 mp = ⊤ 1129 1130 while (totlen > 0) { 1131 if (top) { 1132 MGET(m, M_DONTWAIT, MT_DATA); 1133 if (m == 0) { 1134 m_freem(top); 1135 return 0; 1136 } 1137 m->m_len = MLEN; 1138 } 1139 len = min(totlen, epkt - cp); 1140 if (len >= MINCLSIZE) { 1141 MCLGET(m, M_DONTWAIT); 1142 if (m->m_flags & M_EXT) 1143 m->m_len = len = min(len, MCLBYTES); 1144 else 1145 len = m->m_len; 1146 } else { 1147 /* 1148 * Place initial small packet/header at end of mbuf. 1149 */ 1150 if (len < m->m_len) { 1151 if (top == 0 && len + max_linkhdr <= m->m_len) 1152 m->m_data += max_linkhdr; 1153 m->m_len = len; 1154 } else 1155 len = m->m_len; 1156 } 1157 if (top == 0) { 1158 /* Make sure the payload is aligned */ 1159 caddr_t newdata = (caddr_t) 1160 ALIGN(m->m_data + sizeof(struct ether_header)) - 1161 sizeof(struct ether_header); 1162 len -= newdata - m->m_data; 1163 m->m_len = len; 1164 m->m_data = newdata; 1165 } 1166 ea_readbuf(sc, mtod(m, u_char *), 1167 cp < EA_BUFFER_SIZE ? cp : cp - EA_RX_BUFFER_SIZE, 1168 len); 1169 cp += len; 1170 *mp = m; 1171 mp = &m->m_next; 1172 totlen -= len; 1173 if (cp == epkt) 1174 cp = addr; 1175 } 1176 1177 return top; 1178} 1179 1180/* 1181 * Process an ioctl request. Mostly boilerplate. 1182 */ 1183static int 1184ea_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data) 1185{ 1186 struct seeq8005_softc *sc = ifp->if_softc; 1187 int s, error = 0; 1188 1189 s = splnet(); 1190 switch (cmd) { 1191 1192 default: 1193 error = ether_ioctl(ifp, cmd, data); 1194 if (error == ENETRESET) { 1195 /* 1196 * Multicast list has changed; set the hardware filter 1197 * accordingly. 1198 */ 1199 ea_mc_reset(sc); 1200 error = 0; 1201 } 1202 break; 1203 } 1204 1205 splx(s); 1206 return error; 1207} 1208 1209/* Must be called at splnet() */ 1210static void 1211ea_mc_reset(struct seeq8005_softc *sc) 1212{ 1213 struct ether_multi *enm; 1214 struct ether_multistep step; 1215 int naddr, maxaddrs; 1216 1217 naddr = 0; 1218 maxaddrs = (sc->sc_flags & SEEQ8005_80C04) ? 5 : 0; 1219 ETHER_FIRST_MULTI(step, &sc->sc_ethercom, enm); 1220 while (enm != NULL) { 1221 /* Have we got space? */ 1222 if (naddr >= maxaddrs || 1223 bcmp(enm->enm_addrlo, enm->enm_addrhi, 6) != 0) { 1224 sc->sc_ethercom.ec_if.if_flags |= IFF_ALLMULTI; 1225 ea_ioctl(&sc->sc_ethercom.ec_if, SIOCSIFFLAGS, NULL); 1226 return; 1227 } 1228 ea_set_address(sc, naddr, enm->enm_addrlo); 1229 sc->sc_config1 |= EA_CFG1_STATION_ADDR0 << naddr; 1230 naddr++; 1231 ETHER_NEXT_MULTI(step, enm); 1232 } 1233 for (; naddr < maxaddrs; naddr++) 1234 sc->sc_config1 &= ~(EA_CFG1_STATION_ADDR0 << naddr); 1235 bus_space_write_2(sc->sc_iot, sc->sc_ioh, EA_8005_CONFIG1, 1236 sc->sc_config1); 1237} 1238 1239/* 1240 * Device timeout routine. 1241 * 1242 * Ok I am not sure exactly how the device timeout should work.... 1243 * Currently what will happens is that that the device timeout is only 1244 * set when a packet it received. This indicates we are on an active 1245 * network and thus we should expect more packets. If non arrive in 1246 * in the timeout period then we reinitialise as we may have jammed. 1247 * We zero the timeout at this point so that we don't end up with 1248 * an endless stream of timeouts if the network goes down. 1249 */ 1250 1251static void 1252ea_watchdog(struct ifnet *ifp) 1253{ 1254 struct seeq8005_softc *sc = ifp->if_softc; 1255 1256 log(LOG_ERR, "%s: device timeout\n", sc->sc_dev.dv_xname); 1257 ifp->if_oerrors++; 1258 dprintf(("ea_watchdog: ")); 1259 dprintf(("st=%04x\n", 1260 bus_space_read_2(sc->sc_iot, sc->sc_ioh, EA_8005_STATUS))); 1261 1262 /* Kick the interface */ 1263 1264 ea_init(ifp); 1265 1266/* ifp->if_timer = EA_TIMEOUT;*/ 1267 ifp->if_timer = 0; 1268} 1269 1270/* End of if_ea.c */ 1271