if_ex.c revision 276750
1/*- 2 * Copyright (c) 1996, Javier Mart��n Rueda (jmrueda@diatel.upm.es) 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice unmodified, this list of conditions, and the following 10 * disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 16 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 18 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 19 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 20 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 21 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 22 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 23 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 24 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 25 * SUCH DAMAGE. 26 * 27 * 28 * MAINTAINER: Matthew N. Dodd <winter@jurai.net> 29 * <mdodd@FreeBSD.org> 30 */ 31 32#include <sys/cdefs.h> 33__FBSDID("$FreeBSD: head/sys/dev/ex/if_ex.c 276750 2015-01-06 12:59:37Z rwatson $"); 34 35/* 36 * Intel EtherExpress Pro/10, Pro/10+ Ethernet driver 37 * 38 * Revision history: 39 * 40 * dd-mmm-yyyy: Multicast support ported from NetBSD's if_iy driver. 41 * 30-Oct-1996: first beta version. Inet and BPF supported, but no multicast. 42 */ 43 44#include <sys/param.h> 45#include <sys/systm.h> 46#include <sys/kernel.h> 47#include <sys/sockio.h> 48#include <sys/mbuf.h> 49#include <sys/socket.h> 50 51#include <sys/module.h> 52#include <sys/bus.h> 53 54#include <machine/bus.h> 55#include <machine/resource.h> 56#include <sys/rman.h> 57 58#include <net/if.h> 59#include <net/if_var.h> 60#include <net/if_arp.h> 61#include <net/if_dl.h> 62#include <net/if_media.h> 63#include <net/if_types.h> 64#include <net/ethernet.h> 65#include <net/bpf.h> 66 67#include <netinet/in.h> 68#include <netinet/if_ether.h> 69 70 71#include <isa/isavar.h> 72#include <isa/pnpvar.h> 73 74#include <dev/ex/if_exreg.h> 75#include <dev/ex/if_exvar.h> 76 77#ifdef EXDEBUG 78# define Start_End 1 79# define Rcvd_Pkts 2 80# define Sent_Pkts 4 81# define Status 8 82static int debug_mask = 0; 83# define DODEBUG(level, action) if (level & debug_mask) action 84#else 85# define DODEBUG(level, action) 86#endif 87 88devclass_t ex_devclass; 89 90char irq2eemap[] = 91 { -1, -1, 0, 1, -1, 2, -1, -1, -1, 0, 3, 4, -1, -1, -1, -1 }; 92u_char ee2irqmap[] = 93 { 9, 3, 5, 10, 11, 0, 0, 0 }; 94 95char plus_irq2eemap[] = 96 { -1, -1, -1, 0, 1, 2, -1, 3, -1, 4, 5, 6, 7, -1, -1, -1 }; 97u_char plus_ee2irqmap[] = 98 { 3, 4, 5, 7, 9, 10, 11, 12 }; 99 100/* Network Interface Functions */ 101static void ex_init(void *); 102static void ex_init_locked(struct ex_softc *); 103static void ex_start(struct ifnet *); 104static void ex_start_locked(struct ifnet *); 105static int ex_ioctl(struct ifnet *, u_long, caddr_t); 106static void ex_watchdog(void *); 107 108/* ifmedia Functions */ 109static int ex_ifmedia_upd(struct ifnet *); 110static void ex_ifmedia_sts(struct ifnet *, struct ifmediareq *); 111 112static int ex_get_media(struct ex_softc *); 113 114static void ex_reset(struct ex_softc *); 115static void ex_setmulti(struct ex_softc *); 116 117static void ex_tx_intr(struct ex_softc *); 118static void ex_rx_intr(struct ex_softc *); 119 120void 121ex_get_address(struct ex_softc *sc, u_char *enaddr) 122{ 123 uint16_t eaddr_tmp; 124 125 eaddr_tmp = ex_eeprom_read(sc, EE_Eth_Addr_Lo); 126 enaddr[5] = eaddr_tmp & 0xff; 127 enaddr[4] = eaddr_tmp >> 8; 128 eaddr_tmp = ex_eeprom_read(sc, EE_Eth_Addr_Mid); 129 enaddr[3] = eaddr_tmp & 0xff; 130 enaddr[2] = eaddr_tmp >> 8; 131 eaddr_tmp = ex_eeprom_read(sc, EE_Eth_Addr_Hi); 132 enaddr[1] = eaddr_tmp & 0xff; 133 enaddr[0] = eaddr_tmp >> 8; 134 135 return; 136} 137 138int 139ex_card_type(u_char *enaddr) 140{ 141 if ((enaddr[0] == 0x00) && (enaddr[1] == 0xA0) && (enaddr[2] == 0xC9)) 142 return (CARD_TYPE_EX_10_PLUS); 143 144 return (CARD_TYPE_EX_10); 145} 146 147/* 148 * Caller is responsible for eventually calling 149 * ex_release_resources() on failure. 150 */ 151int 152ex_alloc_resources(device_t dev) 153{ 154 struct ex_softc * sc = device_get_softc(dev); 155 int error = 0; 156 157 sc->ioport = bus_alloc_resource_any(dev, SYS_RES_IOPORT, 158 &sc->ioport_rid, RF_ACTIVE); 159 if (!sc->ioport) { 160 device_printf(dev, "No I/O space?!\n"); 161 error = ENOMEM; 162 goto bad; 163 } 164 165 sc->irq = bus_alloc_resource_any(dev, SYS_RES_IRQ, &sc->irq_rid, 166 RF_ACTIVE); 167 168 if (!sc->irq) { 169 device_printf(dev, "No IRQ?!\n"); 170 error = ENOMEM; 171 goto bad; 172 } 173 174bad: 175 return (error); 176} 177 178void 179ex_release_resources(device_t dev) 180{ 181 struct ex_softc * sc = device_get_softc(dev); 182 183 if (sc->ih) { 184 bus_teardown_intr(dev, sc->irq, sc->ih); 185 sc->ih = NULL; 186 } 187 188 if (sc->ioport) { 189 bus_release_resource(dev, SYS_RES_IOPORT, 190 sc->ioport_rid, sc->ioport); 191 sc->ioport = NULL; 192 } 193 194 if (sc->irq) { 195 bus_release_resource(dev, SYS_RES_IRQ, 196 sc->irq_rid, sc->irq); 197 sc->irq = NULL; 198 } 199 200 if (sc->ifp) 201 if_free(sc->ifp); 202 203 return; 204} 205 206int 207ex_attach(device_t dev) 208{ 209 struct ex_softc * sc = device_get_softc(dev); 210 struct ifnet * ifp; 211 struct ifmedia * ifm; 212 int error; 213 uint16_t temp; 214 215 ifp = sc->ifp = if_alloc(IFT_ETHER); 216 if (ifp == NULL) { 217 device_printf(dev, "can not if_alloc()\n"); 218 return (ENOSPC); 219 } 220 /* work out which set of irq <-> internal tables to use */ 221 if (ex_card_type(sc->enaddr) == CARD_TYPE_EX_10_PLUS) { 222 sc->irq2ee = plus_irq2eemap; 223 sc->ee2irq = plus_ee2irqmap; 224 } else { 225 sc->irq2ee = irq2eemap; 226 sc->ee2irq = ee2irqmap; 227 } 228 229 sc->mem_size = CARD_RAM_SIZE; /* XXX This should be read from the card itself. */ 230 231 /* 232 * Initialize the ifnet structure. 233 */ 234 ifp->if_softc = sc; 235 if_initname(ifp, device_get_name(dev), device_get_unit(dev)); 236 ifp->if_flags = IFF_SIMPLEX | IFF_BROADCAST | IFF_MULTICAST; 237 ifp->if_start = ex_start; 238 ifp->if_ioctl = ex_ioctl; 239 ifp->if_init = ex_init; 240 IFQ_SET_MAXLEN(&ifp->if_snd, ifqmaxlen); 241 242 ifmedia_init(&sc->ifmedia, 0, ex_ifmedia_upd, ex_ifmedia_sts); 243 mtx_init(&sc->lock, device_get_nameunit(dev), MTX_NETWORK_LOCK, 244 MTX_DEF); 245 callout_init_mtx(&sc->timer, &sc->lock, 0); 246 247 temp = ex_eeprom_read(sc, EE_W5); 248 if (temp & EE_W5_PORT_TPE) 249 ifmedia_add(&sc->ifmedia, IFM_ETHER|IFM_10_T, 0, NULL); 250 if (temp & EE_W5_PORT_BNC) 251 ifmedia_add(&sc->ifmedia, IFM_ETHER|IFM_10_2, 0, NULL); 252 if (temp & EE_W5_PORT_AUI) 253 ifmedia_add(&sc->ifmedia, IFM_ETHER|IFM_10_5, 0, NULL); 254 255 ifmedia_add(&sc->ifmedia, IFM_ETHER|IFM_AUTO, 0, NULL); 256 ifmedia_add(&sc->ifmedia, IFM_ETHER|IFM_NONE, 0, NULL); 257 ifmedia_set(&sc->ifmedia, ex_get_media(sc)); 258 259 ifm = &sc->ifmedia; 260 ifm->ifm_media = ifm->ifm_cur->ifm_media; 261 ex_ifmedia_upd(ifp); 262 263 /* 264 * Attach the interface. 265 */ 266 ether_ifattach(ifp, sc->enaddr); 267 268 error = bus_setup_intr(dev, sc->irq, INTR_TYPE_NET | INTR_MPSAFE, 269 NULL, ex_intr, (void *)sc, &sc->ih); 270 if (error) { 271 device_printf(dev, "bus_setup_intr() failed!\n"); 272 ether_ifdetach(ifp); 273 mtx_destroy(&sc->lock); 274 return (error); 275 } 276 277 return(0); 278} 279 280int 281ex_detach(device_t dev) 282{ 283 struct ex_softc *sc; 284 struct ifnet *ifp; 285 286 sc = device_get_softc(dev); 287 ifp = sc->ifp; 288 289 EX_LOCK(sc); 290 ex_stop(sc); 291 EX_UNLOCK(sc); 292 293 ether_ifdetach(ifp); 294 callout_drain(&sc->timer); 295 296 ex_release_resources(dev); 297 mtx_destroy(&sc->lock); 298 299 return (0); 300} 301 302static void 303ex_init(void *xsc) 304{ 305 struct ex_softc * sc = (struct ex_softc *) xsc; 306 307 EX_LOCK(sc); 308 ex_init_locked(sc); 309 EX_UNLOCK(sc); 310} 311 312static void 313ex_init_locked(struct ex_softc *sc) 314{ 315 struct ifnet * ifp = sc->ifp; 316 int i; 317 unsigned short temp_reg; 318 319 DODEBUG(Start_End, printf("%s: ex_init: start\n", ifp->if_xname);); 320 321 sc->tx_timeout = 0; 322 323 /* 324 * Load the ethernet address into the card. 325 */ 326 CSR_WRITE_1(sc, CMD_REG, Bank2_Sel); 327 temp_reg = CSR_READ_1(sc, EEPROM_REG); 328 if (temp_reg & Trnoff_Enable) 329 CSR_WRITE_1(sc, EEPROM_REG, temp_reg & ~Trnoff_Enable); 330 for (i = 0; i < ETHER_ADDR_LEN; i++) 331 CSR_WRITE_1(sc, I_ADDR_REG0 + i, IF_LLADDR(sc->ifp)[i]); 332 333 /* 334 * - Setup transmit chaining and discard bad received frames. 335 * - Match broadcast. 336 * - Clear test mode. 337 * - Set receiving mode. 338 */ 339 CSR_WRITE_1(sc, REG1, CSR_READ_1(sc, REG1) | Tx_Chn_Int_Md | Tx_Chn_ErStp | Disc_Bad_Fr); 340 CSR_WRITE_1(sc, REG2, CSR_READ_1(sc, REG2) | No_SA_Ins | RX_CRC_InMem); 341 CSR_WRITE_1(sc, REG3, CSR_READ_1(sc, REG3) & 0x3f /* XXX constants. */ ); 342 /* 343 * - Set IRQ number, if this part has it. ISA devices have this, 344 * while PC Card devices don't seem to. Either way, we have to 345 * switch to Bank1 as the rest of this code relies on that. 346 */ 347 CSR_WRITE_1(sc, CMD_REG, Bank1_Sel); 348 if (sc->flags & HAS_INT_NO_REG) 349 CSR_WRITE_1(sc, INT_NO_REG, 350 (CSR_READ_1(sc, INT_NO_REG) & 0xf8) | 351 sc->irq2ee[sc->irq_no]); 352 353 /* 354 * Divide the available memory in the card into rcv and xmt buffers. 355 * By default, I use the first 3/4 of the memory for the rcv buffer, 356 * and the remaining 1/4 of the memory for the xmt buffer. 357 */ 358 sc->rx_mem_size = sc->mem_size * 3 / 4; 359 sc->tx_mem_size = sc->mem_size - sc->rx_mem_size; 360 sc->rx_lower_limit = 0x0000; 361 sc->rx_upper_limit = sc->rx_mem_size - 2; 362 sc->tx_lower_limit = sc->rx_mem_size; 363 sc->tx_upper_limit = sc->mem_size - 2; 364 CSR_WRITE_1(sc, RCV_LOWER_LIMIT_REG, sc->rx_lower_limit >> 8); 365 CSR_WRITE_1(sc, RCV_UPPER_LIMIT_REG, sc->rx_upper_limit >> 8); 366 CSR_WRITE_1(sc, XMT_LOWER_LIMIT_REG, sc->tx_lower_limit >> 8); 367 CSR_WRITE_1(sc, XMT_UPPER_LIMIT_REG, sc->tx_upper_limit >> 8); 368 369 /* 370 * Enable receive and transmit interrupts, and clear any pending int. 371 */ 372 CSR_WRITE_1(sc, REG1, CSR_READ_1(sc, REG1) | TriST_INT); 373 CSR_WRITE_1(sc, CMD_REG, Bank0_Sel); 374 CSR_WRITE_1(sc, MASK_REG, All_Int & ~(Rx_Int | Tx_Int)); 375 CSR_WRITE_1(sc, STATUS_REG, All_Int); 376 377 /* 378 * Initialize receive and transmit ring buffers. 379 */ 380 CSR_WRITE_2(sc, RCV_BAR, sc->rx_lower_limit); 381 sc->rx_head = sc->rx_lower_limit; 382 CSR_WRITE_2(sc, RCV_STOP_REG, sc->rx_upper_limit | 0xfe); 383 CSR_WRITE_2(sc, XMT_BAR, sc->tx_lower_limit); 384 sc->tx_head = sc->tx_tail = sc->tx_lower_limit; 385 386 ifp->if_drv_flags |= IFF_DRV_RUNNING; 387 ifp->if_drv_flags &= ~IFF_DRV_OACTIVE; 388 DODEBUG(Status, printf("OIDLE init\n");); 389 callout_reset(&sc->timer, hz, ex_watchdog, sc); 390 391 ex_setmulti(sc); 392 393 /* 394 * Final reset of the board, and enable operation. 395 */ 396 CSR_WRITE_1(sc, CMD_REG, Sel_Reset_CMD); 397 DELAY(2); 398 CSR_WRITE_1(sc, CMD_REG, Rcv_Enable_CMD); 399 400 ex_start_locked(ifp); 401 402 DODEBUG(Start_End, printf("%s: ex_init: finish\n", ifp->if_xname);); 403} 404 405static void 406ex_start(struct ifnet *ifp) 407{ 408 struct ex_softc * sc = ifp->if_softc; 409 410 EX_LOCK(sc); 411 ex_start_locked(ifp); 412 EX_UNLOCK(sc); 413} 414 415static void 416ex_start_locked(struct ifnet *ifp) 417{ 418 struct ex_softc * sc = ifp->if_softc; 419 int i, len, data_len, avail, dest, next; 420 unsigned char tmp16[2]; 421 struct mbuf * opkt; 422 struct mbuf * m; 423 424 DODEBUG(Start_End, printf("ex_start%d: start\n", unit);); 425 426 /* 427 * Main loop: send outgoing packets to network card until there are no 428 * more packets left, or the card cannot accept any more yet. 429 */ 430 while (((opkt = ifp->if_snd.ifq_head) != NULL) && 431 !(ifp->if_drv_flags & IFF_DRV_OACTIVE)) { 432 433 /* 434 * Ensure there is enough free transmit buffer space for 435 * this packet, including its header. Note: the header 436 * cannot wrap around the end of the transmit buffer and 437 * must be kept together, so we allow space for twice the 438 * length of the header, just in case. 439 */ 440 441 for (len = 0, m = opkt; m != NULL; m = m->m_next) { 442 len += m->m_len; 443 } 444 445 data_len = len; 446 447 DODEBUG(Sent_Pkts, printf("1. Sending packet with %d data bytes. ", data_len);); 448 449 if (len & 1) { 450 len += XMT_HEADER_LEN + 1; 451 } else { 452 len += XMT_HEADER_LEN; 453 } 454 455 if ((i = sc->tx_tail - sc->tx_head) >= 0) { 456 avail = sc->tx_mem_size - i; 457 } else { 458 avail = -i; 459 } 460 461 DODEBUG(Sent_Pkts, printf("i=%d, avail=%d\n", i, avail);); 462 463 if (avail >= len + XMT_HEADER_LEN) { 464 IF_DEQUEUE(&ifp->if_snd, opkt); 465 466#ifdef EX_PSA_INTR 467 /* 468 * Disable rx and tx interrupts, to avoid corruption 469 * of the host address register by interrupt service 470 * routines. 471 * XXX Is this necessary with splimp() enabled? 472 */ 473 CSR_WRITE_1(sc, MASK_REG, All_Int); 474#endif 475 476 /* 477 * Compute the start and end addresses of this 478 * frame in the tx buffer. 479 */ 480 dest = sc->tx_tail; 481 next = dest + len; 482 483 if (next > sc->tx_upper_limit) { 484 if ((sc->tx_upper_limit + 2 - sc->tx_tail) <= 485 XMT_HEADER_LEN) { 486 dest = sc->tx_lower_limit; 487 next = dest + len; 488 } else { 489 next = sc->tx_lower_limit + 490 next - sc->tx_upper_limit - 2; 491 } 492 } 493 494 /* 495 * Build the packet frame in the card's ring buffer. 496 */ 497 DODEBUG(Sent_Pkts, printf("2. dest=%d, next=%d. ", dest, next);); 498 499 CSR_WRITE_2(sc, HOST_ADDR_REG, dest); 500 CSR_WRITE_2(sc, IO_PORT_REG, Transmit_CMD); 501 CSR_WRITE_2(sc, IO_PORT_REG, 0); 502 CSR_WRITE_2(sc, IO_PORT_REG, next); 503 CSR_WRITE_2(sc, IO_PORT_REG, data_len); 504 505 /* 506 * Output the packet data to the card. Ensure all 507 * transfers are 16-bit wide, even if individual 508 * mbufs have odd length. 509 */ 510 for (m = opkt, i = 0; m != NULL; m = m->m_next) { 511 DODEBUG(Sent_Pkts, printf("[%d]", m->m_len);); 512 if (i) { 513 tmp16[1] = *(mtod(m, caddr_t)); 514 CSR_WRITE_MULTI_2(sc, IO_PORT_REG, 515 (uint16_t *) tmp16, 1); 516 } 517 CSR_WRITE_MULTI_2(sc, IO_PORT_REG, 518 (uint16_t *) (mtod(m, caddr_t) + i), 519 (m->m_len - i) / 2); 520 if ((i = (m->m_len - i) & 1) != 0) { 521 tmp16[0] = *(mtod(m, caddr_t) + 522 m->m_len - 1); 523 } 524 } 525 if (i) 526 CSR_WRITE_MULTI_2(sc, IO_PORT_REG, 527 (uint16_t *) tmp16, 1); 528 /* 529 * If there were other frames chained, update the 530 * chain in the last one. 531 */ 532 if (sc->tx_head != sc->tx_tail) { 533 if (sc->tx_tail != dest) { 534 CSR_WRITE_2(sc, HOST_ADDR_REG, 535 sc->tx_last + XMT_Chain_Point); 536 CSR_WRITE_2(sc, IO_PORT_REG, dest); 537 } 538 CSR_WRITE_2(sc, HOST_ADDR_REG, 539 sc->tx_last + XMT_Byte_Count); 540 i = CSR_READ_2(sc, IO_PORT_REG); 541 CSR_WRITE_2(sc, HOST_ADDR_REG, 542 sc->tx_last + XMT_Byte_Count); 543 CSR_WRITE_2(sc, IO_PORT_REG, i | Ch_bit); 544 } 545 546 /* 547 * Resume normal operation of the card: 548 * - Make a dummy read to flush the DRAM write 549 * pipeline. 550 * - Enable receive and transmit interrupts. 551 * - Send Transmit or Resume_XMT command, as 552 * appropriate. 553 */ 554 CSR_READ_2(sc, IO_PORT_REG); 555#ifdef EX_PSA_INTR 556 CSR_WRITE_1(sc, MASK_REG, All_Int & ~(Rx_Int | Tx_Int)); 557#endif 558 if (sc->tx_head == sc->tx_tail) { 559 CSR_WRITE_2(sc, XMT_BAR, dest); 560 CSR_WRITE_1(sc, CMD_REG, Transmit_CMD); 561 sc->tx_head = dest; 562 DODEBUG(Sent_Pkts, printf("Transmit\n");); 563 } else { 564 CSR_WRITE_1(sc, CMD_REG, Resume_XMT_List_CMD); 565 DODEBUG(Sent_Pkts, printf("Resume\n");); 566 } 567 568 sc->tx_last = dest; 569 sc->tx_tail = next; 570 571 BPF_MTAP(ifp, opkt); 572 573 sc->tx_timeout = 2; 574 if_inc_counter(ifp, IFCOUNTER_OPACKETS, 1); 575 m_freem(opkt); 576 } else { 577 ifp->if_drv_flags |= IFF_DRV_OACTIVE; 578 DODEBUG(Status, printf("OACTIVE start\n");); 579 } 580 } 581 582 DODEBUG(Start_End, printf("ex_start%d: finish\n", unit);); 583} 584 585void 586ex_stop(struct ex_softc *sc) 587{ 588 589 DODEBUG(Start_End, printf("ex_stop%d: start\n", unit);); 590 591 EX_ASSERT_LOCKED(sc); 592 /* 593 * Disable card operation: 594 * - Disable the interrupt line. 595 * - Flush transmission and disable reception. 596 * - Mask and clear all interrupts. 597 * - Reset the 82595. 598 */ 599 CSR_WRITE_1(sc, CMD_REG, Bank1_Sel); 600 CSR_WRITE_1(sc, REG1, CSR_READ_1(sc, REG1) & ~TriST_INT); 601 CSR_WRITE_1(sc, CMD_REG, Bank0_Sel); 602 CSR_WRITE_1(sc, CMD_REG, Rcv_Stop); 603 sc->tx_head = sc->tx_tail = sc->tx_lower_limit; 604 sc->tx_last = 0; /* XXX I think these two lines are not necessary, because ex_init will always be called again to reinit the interface. */ 605 CSR_WRITE_1(sc, MASK_REG, All_Int); 606 CSR_WRITE_1(sc, STATUS_REG, All_Int); 607 CSR_WRITE_1(sc, CMD_REG, Reset_CMD); 608 DELAY(200); 609 sc->ifp->if_drv_flags &= ~(IFF_DRV_RUNNING | IFF_DRV_OACTIVE); 610 sc->tx_timeout = 0; 611 callout_stop(&sc->timer); 612 613 DODEBUG(Start_End, printf("ex_stop%d: finish\n", unit);); 614 615 return; 616} 617 618void 619ex_intr(void *arg) 620{ 621 struct ex_softc *sc = (struct ex_softc *)arg; 622 struct ifnet *ifp = sc->ifp; 623 int int_status, send_pkts; 624 int loops = 100; 625 626 DODEBUG(Start_End, printf("ex_intr%d: start\n", unit);); 627 628 EX_LOCK(sc); 629 send_pkts = 0; 630 while (loops-- > 0 && 631 (int_status = CSR_READ_1(sc, STATUS_REG)) & (Tx_Int | Rx_Int)) { 632 /* don't loop forever */ 633 if (int_status == 0xff) 634 break; 635 if (int_status & Rx_Int) { 636 CSR_WRITE_1(sc, STATUS_REG, Rx_Int); 637 ex_rx_intr(sc); 638 } else if (int_status & Tx_Int) { 639 CSR_WRITE_1(sc, STATUS_REG, Tx_Int); 640 ex_tx_intr(sc); 641 send_pkts = 1; 642 } 643 } 644 if (loops == 0) 645 printf("100 loops are not enough\n"); 646 647 /* 648 * If any packet has been transmitted, and there are queued packets to 649 * be sent, attempt to send more packets to the network card. 650 */ 651 if (send_pkts && (ifp->if_snd.ifq_head != NULL)) 652 ex_start_locked(ifp); 653 EX_UNLOCK(sc); 654 655 DODEBUG(Start_End, printf("ex_intr%d: finish\n", unit);); 656 657 return; 658} 659 660static void 661ex_tx_intr(struct ex_softc *sc) 662{ 663 struct ifnet * ifp = sc->ifp; 664 int tx_status; 665 666 DODEBUG(Start_End, printf("ex_tx_intr%d: start\n", unit);); 667 668 /* 669 * - Cancel the watchdog. 670 * For all packets transmitted since last transmit interrupt: 671 * - Advance chain pointer to next queued packet. 672 * - Update statistics. 673 */ 674 675 sc->tx_timeout = 0; 676 677 while (sc->tx_head != sc->tx_tail) { 678 CSR_WRITE_2(sc, HOST_ADDR_REG, sc->tx_head); 679 680 if (!(CSR_READ_2(sc, IO_PORT_REG) & Done_bit)) 681 break; 682 683 tx_status = CSR_READ_2(sc, IO_PORT_REG); 684 sc->tx_head = CSR_READ_2(sc, IO_PORT_REG); 685 686 if (tx_status & TX_OK_bit) { 687 if_inc_counter(ifp, IFCOUNTER_OPACKETS, 1); 688 } else { 689 if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); 690 } 691 692 if_inc_counter(ifp, IFCOUNTER_COLLISIONS, tx_status & No_Collisions_bits); 693 } 694 695 /* 696 * The card should be ready to accept more packets now. 697 */ 698 699 ifp->if_drv_flags &= ~IFF_DRV_OACTIVE; 700 701 DODEBUG(Status, printf("OIDLE tx_intr\n");); 702 DODEBUG(Start_End, printf("ex_tx_intr%d: finish\n", unit);); 703 704 return; 705} 706 707static void 708ex_rx_intr(struct ex_softc *sc) 709{ 710 struct ifnet * ifp = sc->ifp; 711 int rx_status; 712 int pkt_len; 713 int QQQ; 714 struct mbuf * m; 715 struct mbuf * ipkt; 716 struct ether_header * eh; 717 718 DODEBUG(Start_End, printf("ex_rx_intr%d: start\n", unit);); 719 720 /* 721 * For all packets received since last receive interrupt: 722 * - If packet ok, read it into a new mbuf and queue it to interface, 723 * updating statistics. 724 * - If packet bad, just discard it, and update statistics. 725 * Finally, advance receive stop limit in card's memory to new location. 726 */ 727 728 CSR_WRITE_2(sc, HOST_ADDR_REG, sc->rx_head); 729 730 while (CSR_READ_2(sc, IO_PORT_REG) == RCV_Done) { 731 732 rx_status = CSR_READ_2(sc, IO_PORT_REG); 733 sc->rx_head = CSR_READ_2(sc, IO_PORT_REG); 734 QQQ = pkt_len = CSR_READ_2(sc, IO_PORT_REG); 735 736 if (rx_status & RCV_OK_bit) { 737 MGETHDR(m, M_NOWAIT, MT_DATA); 738 ipkt = m; 739 if (ipkt == NULL) { 740 if_inc_counter(ifp, IFCOUNTER_IQDROPS, 1); 741 } else { 742 ipkt->m_pkthdr.rcvif = ifp; 743 ipkt->m_pkthdr.len = pkt_len; 744 ipkt->m_len = MHLEN; 745 746 while (pkt_len > 0) { 747 if (pkt_len >= MINCLSIZE) { 748 if (MCLGET(m, M_NOWAIT)) { 749 m->m_len = MCLBYTES; 750 } else { 751 m_freem(ipkt); 752 if_inc_counter(ifp, IFCOUNTER_IQDROPS, 1); 753 goto rx_another; 754 } 755 } 756 m->m_len = min(m->m_len, pkt_len); 757 758 /* 759 * NOTE: I'm assuming that all mbufs allocated are of even length, 760 * except for the last one in an odd-length packet. 761 */ 762 763 CSR_READ_MULTI_2(sc, IO_PORT_REG, 764 mtod(m, uint16_t *), m->m_len / 2); 765 766 if (m->m_len & 1) { 767 *(mtod(m, caddr_t) + m->m_len - 1) = CSR_READ_1(sc, IO_PORT_REG); 768 } 769 pkt_len -= m->m_len; 770 771 if (pkt_len > 0) { 772 MGET(m->m_next, M_NOWAIT, MT_DATA); 773 if (m->m_next == NULL) { 774 m_freem(ipkt); 775 if_inc_counter(ifp, IFCOUNTER_IQDROPS, 1); 776 goto rx_another; 777 } 778 m = m->m_next; 779 m->m_len = MLEN; 780 } 781 } 782 eh = mtod(ipkt, struct ether_header *); 783#ifdef EXDEBUG 784 if (debug_mask & Rcvd_Pkts) { 785 if ((eh->ether_dhost[5] != 0xff) || (eh->ether_dhost[0] != 0xff)) { 786 printf("Receive packet with %d data bytes: %6D -> ", QQQ, eh->ether_shost, ":"); 787 printf("%6D\n", eh->ether_dhost, ":"); 788 } /* QQQ */ 789 } 790#endif 791 EX_UNLOCK(sc); 792 (*ifp->if_input)(ifp, ipkt); 793 EX_LOCK(sc); 794 if_inc_counter(ifp, IFCOUNTER_IPACKETS, 1); 795 } 796 } else { 797 if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); 798 } 799 CSR_WRITE_2(sc, HOST_ADDR_REG, sc->rx_head); 800rx_another: ; 801 } 802 803 if (sc->rx_head < sc->rx_lower_limit + 2) 804 CSR_WRITE_2(sc, RCV_STOP_REG, sc->rx_upper_limit); 805 else 806 CSR_WRITE_2(sc, RCV_STOP_REG, sc->rx_head - 2); 807 808 DODEBUG(Start_End, printf("ex_rx_intr%d: finish\n", unit);); 809 810 return; 811} 812 813 814static int 815ex_ioctl(register struct ifnet *ifp, u_long cmd, caddr_t data) 816{ 817 struct ex_softc * sc = ifp->if_softc; 818 struct ifreq * ifr = (struct ifreq *)data; 819 int error = 0; 820 821 DODEBUG(Start_End, printf("%s: ex_ioctl: start ", ifp->if_xname);); 822 823 switch(cmd) { 824 case SIOCSIFADDR: 825 case SIOCGIFADDR: 826 case SIOCSIFMTU: 827 error = ether_ioctl(ifp, cmd, data); 828 break; 829 830 case SIOCSIFFLAGS: 831 DODEBUG(Start_End, printf("SIOCSIFFLAGS");); 832 EX_LOCK(sc); 833 if ((ifp->if_flags & IFF_UP) == 0 && 834 (ifp->if_drv_flags & IFF_DRV_RUNNING)) { 835 ex_stop(sc); 836 } else { 837 ex_init_locked(sc); 838 } 839 EX_UNLOCK(sc); 840 break; 841 case SIOCADDMULTI: 842 case SIOCDELMULTI: 843 ex_init(sc); 844 error = 0; 845 break; 846 case SIOCSIFMEDIA: 847 case SIOCGIFMEDIA: 848 error = ifmedia_ioctl(ifp, ifr, &sc->ifmedia, cmd); 849 break; 850 default: 851 DODEBUG(Start_End, printf("unknown");); 852 error = EINVAL; 853 } 854 855 DODEBUG(Start_End, printf("\n%s: ex_ioctl: finish\n", ifp->if_xname);); 856 857 return(error); 858} 859 860static void 861ex_setmulti(struct ex_softc *sc) 862{ 863 struct ifnet *ifp; 864 struct ifmultiaddr *maddr; 865 uint16_t *addr; 866 int count; 867 int timeout, status; 868 869 ifp = sc->ifp; 870 871 count = 0; 872 if_maddr_rlock(ifp); 873 TAILQ_FOREACH(maddr, &ifp->if_multiaddrs, ifma_link) { 874 if (maddr->ifma_addr->sa_family != AF_LINK) 875 continue; 876 count++; 877 } 878 if_maddr_runlock(ifp); 879 880 if ((ifp->if_flags & IFF_PROMISC) || (ifp->if_flags & IFF_ALLMULTI) 881 || count > 63) { 882 /* Interface is in promiscuous mode or there are too many 883 * multicast addresses for the card to handle */ 884 CSR_WRITE_1(sc, CMD_REG, Bank2_Sel); 885 CSR_WRITE_1(sc, REG2, CSR_READ_1(sc, REG2) | Promisc_Mode); 886 CSR_WRITE_1(sc, REG3, CSR_READ_1(sc, REG3)); 887 CSR_WRITE_1(sc, CMD_REG, Bank0_Sel); 888 } 889 else if ((ifp->if_flags & IFF_MULTICAST) && (count > 0)) { 890 /* Program multicast addresses plus our MAC address 891 * into the filter */ 892 CSR_WRITE_1(sc, CMD_REG, Bank2_Sel); 893 CSR_WRITE_1(sc, REG2, CSR_READ_1(sc, REG2) | Multi_IA); 894 CSR_WRITE_1(sc, REG3, CSR_READ_1(sc, REG3)); 895 CSR_WRITE_1(sc, CMD_REG, Bank0_Sel); 896 897 /* Borrow space from TX buffer; this should be safe 898 * as this is only called from ex_init */ 899 900 CSR_WRITE_2(sc, HOST_ADDR_REG, sc->tx_lower_limit); 901 CSR_WRITE_2(sc, IO_PORT_REG, MC_Setup_CMD); 902 CSR_WRITE_2(sc, IO_PORT_REG, 0); 903 CSR_WRITE_2(sc, IO_PORT_REG, 0); 904 CSR_WRITE_2(sc, IO_PORT_REG, (count + 1) * 6); 905 906 if_maddr_rlock(ifp); 907 TAILQ_FOREACH(maddr, &ifp->if_multiaddrs, ifma_link) { 908 if (maddr->ifma_addr->sa_family != AF_LINK) 909 continue; 910 911 addr = (uint16_t*)LLADDR((struct sockaddr_dl *) 912 maddr->ifma_addr); 913 CSR_WRITE_2(sc, IO_PORT_REG, *addr++); 914 CSR_WRITE_2(sc, IO_PORT_REG, *addr++); 915 CSR_WRITE_2(sc, IO_PORT_REG, *addr++); 916 } 917 if_maddr_runlock(ifp); 918 919 /* Program our MAC address as well */ 920 /* XXX: Is this necessary? The Linux driver does this 921 * but the NetBSD driver does not */ 922 addr = (uint16_t*)IF_LLADDR(sc->ifp); 923 CSR_WRITE_2(sc, IO_PORT_REG, *addr++); 924 CSR_WRITE_2(sc, IO_PORT_REG, *addr++); 925 CSR_WRITE_2(sc, IO_PORT_REG, *addr++); 926 927 CSR_READ_2(sc, IO_PORT_REG); 928 CSR_WRITE_2(sc, XMT_BAR, sc->tx_lower_limit); 929 CSR_WRITE_1(sc, CMD_REG, MC_Setup_CMD); 930 931 sc->tx_head = sc->tx_lower_limit; 932 sc->tx_tail = sc->tx_head + XMT_HEADER_LEN + (count + 1) * 6; 933 934 for (timeout=0; timeout<100; timeout++) { 935 DELAY(2); 936 if ((CSR_READ_1(sc, STATUS_REG) & Exec_Int) == 0) 937 continue; 938 939 status = CSR_READ_1(sc, CMD_REG); 940 CSR_WRITE_1(sc, STATUS_REG, Exec_Int); 941 break; 942 } 943 944 sc->tx_head = sc->tx_tail; 945 } 946 else 947 { 948 /* No multicast or promiscuous mode */ 949 CSR_WRITE_1(sc, CMD_REG, Bank2_Sel); 950 CSR_WRITE_1(sc, REG2, CSR_READ_1(sc, REG2) & 0xDE); 951 /* ~(Multi_IA | Promisc_Mode) */ 952 CSR_WRITE_1(sc, REG3, CSR_READ_1(sc, REG3)); 953 CSR_WRITE_1(sc, CMD_REG, Bank0_Sel); 954 } 955} 956 957static void 958ex_reset(struct ex_softc *sc) 959{ 960 961 DODEBUG(Start_End, printf("ex_reset%d: start\n", unit);); 962 963 EX_ASSERT_LOCKED(sc); 964 ex_stop(sc); 965 ex_init_locked(sc); 966 967 DODEBUG(Start_End, printf("ex_reset%d: finish\n", unit);); 968 969 return; 970} 971 972static void 973ex_watchdog(void *arg) 974{ 975 struct ex_softc * sc = arg; 976 struct ifnet *ifp = sc->ifp; 977 978 if (sc->tx_timeout && --sc->tx_timeout == 0) { 979 DODEBUG(Start_End, if_printf(ifp, "ex_watchdog: start\n");); 980 981 ifp->if_drv_flags &= ~IFF_DRV_OACTIVE; 982 983 DODEBUG(Status, printf("OIDLE watchdog\n");); 984 985 if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); 986 ex_reset(sc); 987 ex_start_locked(ifp); 988 989 DODEBUG(Start_End, if_printf(ifp, "ex_watchdog: finish\n");); 990 } 991 992 callout_reset(&sc->timer, hz, ex_watchdog, sc); 993} 994 995static int 996ex_get_media(struct ex_softc *sc) 997{ 998 int current; 999 int media; 1000 1001 media = ex_eeprom_read(sc, EE_W5); 1002 1003 CSR_WRITE_1(sc, CMD_REG, Bank2_Sel); 1004 current = CSR_READ_1(sc, REG3); 1005 CSR_WRITE_1(sc, CMD_REG, Bank0_Sel); 1006 1007 if ((current & TPE_bit) && (media & EE_W5_PORT_TPE)) 1008 return(IFM_ETHER|IFM_10_T); 1009 if ((current & BNC_bit) && (media & EE_W5_PORT_BNC)) 1010 return(IFM_ETHER|IFM_10_2); 1011 1012 if (media & EE_W5_PORT_AUI) 1013 return (IFM_ETHER|IFM_10_5); 1014 1015 return (IFM_ETHER|IFM_AUTO); 1016} 1017 1018static int 1019ex_ifmedia_upd(ifp) 1020 struct ifnet * ifp; 1021{ 1022 struct ex_softc * sc = ifp->if_softc; 1023 1024 if (IFM_TYPE(sc->ifmedia.ifm_media) != IFM_ETHER) 1025 return EINVAL; 1026 1027 return (0); 1028} 1029 1030static void 1031ex_ifmedia_sts(ifp, ifmr) 1032 struct ifnet * ifp; 1033 struct ifmediareq * ifmr; 1034{ 1035 struct ex_softc * sc = ifp->if_softc; 1036 1037 EX_LOCK(sc); 1038 ifmr->ifm_active = ex_get_media(sc); 1039 ifmr->ifm_status = IFM_AVALID | IFM_ACTIVE; 1040 EX_UNLOCK(sc); 1041 1042 return; 1043} 1044 1045u_short 1046ex_eeprom_read(struct ex_softc *sc, int location) 1047{ 1048 int i; 1049 u_short data = 0; 1050 int read_cmd = location | EE_READ_CMD; 1051 short ctrl_val = EECS; 1052 1053 CSR_WRITE_1(sc, CMD_REG, Bank2_Sel); 1054 CSR_WRITE_1(sc, EEPROM_REG, EECS); 1055 for (i = 8; i >= 0; i--) { 1056 short outval = (read_cmd & (1 << i)) ? ctrl_val | EEDI : ctrl_val; 1057 CSR_WRITE_1(sc, EEPROM_REG, outval); 1058 CSR_WRITE_1(sc, EEPROM_REG, outval | EESK); 1059 DELAY(3); 1060 CSR_WRITE_1(sc, EEPROM_REG, outval); 1061 DELAY(2); 1062 } 1063 CSR_WRITE_1(sc, EEPROM_REG, ctrl_val); 1064 1065 for (i = 16; i > 0; i--) { 1066 CSR_WRITE_1(sc, EEPROM_REG, ctrl_val | EESK); 1067 DELAY(3); 1068 data = (data << 1) | 1069 ((CSR_READ_1(sc, EEPROM_REG) & EEDO) ? 1 : 0); 1070 CSR_WRITE_1(sc, EEPROM_REG, ctrl_val); 1071 DELAY(2); 1072 } 1073 1074 ctrl_val &= ~EECS; 1075 CSR_WRITE_1(sc, EEPROM_REG, ctrl_val | EESK); 1076 DELAY(3); 1077 CSR_WRITE_1(sc, EEPROM_REG, ctrl_val); 1078 DELAY(2); 1079 CSR_WRITE_1(sc, CMD_REG, Bank0_Sel); 1080 return(data); 1081} 1082