if_ep.c revision 16471
1/* 2 * Copyright (c) 1994 Herb Peyerl <hpeyerl@novatel.ca> 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, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 3. All advertising materials mentioning features or use of this software 14 * must display the following acknowledgement: 15 * This product includes software developed by Herb Peyerl. 16 * 4. The name of Herb Peyerl may not be used to endorse or promote products 17 * derived from this software without specific prior written permission. 18 * 19 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 20 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 21 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 22 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 23 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 24 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 25 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 26 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 28 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 29 * 30 * if_ep.c,v 1.19 1995/01/24 20:53:45 davidg Exp 31 */ 32 33/* 34 * Modified from the FreeBSD 1.1.5.1 version by: 35 * Andres Vega Garcia 36 * INRIA - Sophia Antipolis, France 37 * avega@sophia.inria.fr 38 */ 39 40/* 41 * $Id: if_ep.c,v 1.48 1996/06/15 00:43:03 nate Exp $ 42 * 43 * Promiscuous mode added and interrupt logic slightly changed 44 * to reduce the number of adapter failures. Transceiver select 45 * logic changed to use value from EEPROM. Autoconfiguration 46 * features added. 47 * Done by: 48 * Serge Babkin 49 * Chelindbank (Chelyabinsk, Russia) 50 * babkin@hq.icb.chel.su 51 */ 52 53/* 54 * Pccard support for 3C589 by: 55 * HAMADA Naoki 56 * nao@tom-yam.or.jp 57 */ 58 59#include "ep.h" 60#if NEP > 0 61 62#include "bpfilter.h" 63 64#include <sys/param.h> 65#if defined(__FreeBSD__) 66#include <sys/systm.h> 67#include <sys/kernel.h> 68#include <sys/conf.h> 69#include <sys/devconf.h> 70#endif 71#include <sys/mbuf.h> 72#include <sys/socket.h> 73#include <sys/ioctl.h> 74#include <sys/errno.h> 75#include <sys/syslog.h> 76#if defined(__NetBSD__) 77#include <sys/select.h> 78#endif 79 80#include <net/if.h> 81#include <net/if_dl.h> 82#include <net/if_types.h> 83 84#ifdef INET 85#include <netinet/in.h> 86#include <netinet/in_systm.h> 87#include <netinet/in_var.h> 88#include <netinet/ip.h> 89#include <netinet/if_ether.h> 90#endif 91 92#ifdef IPX 93#include <netipx/ipx.h> 94#include <netipx/ipx_if.h> 95#endif 96 97#ifdef NS 98#include <netns/ns.h> 99#include <netns/ns_if.h> 100#endif 101 102#if NBPFILTER > 0 103#include <net/bpf.h> 104#include <net/bpfdesc.h> 105#endif 106 107#if defined(__FreeBSD__) 108#include <machine/clock.h> 109#endif 110 111#include <i386/isa/isa_device.h> 112#include <i386/isa/if_epreg.h> 113#include <i386/isa/elink.h> 114 115/* Exported variables */ 116u_long ep_unit; 117int ep_boards; 118struct ep_board ep_board[EP_MAX_BOARDS + 1]; 119 120static int eeprom_rdy __P((struct ep_softc *sc)); 121 122static int ep_isa_probe __P((struct isa_device *)); 123static struct ep_board * ep_look_for_board_at __P((struct isa_device *is)); 124static int ep_isa_attach __P((struct isa_device *)); 125static void ep_isa_registerdev __P((struct ep_softc *sc, 126 struct isa_device *id)); 127static int epioctl __P((struct ifnet * ifp, int, caddr_t)); 128static void epmbuffill __P((caddr_t, int)); 129static void epmbufempty __P((struct ep_softc *)); 130 131static void epinit __P((struct ep_softc *)); 132static void epread __P((struct ep_softc *)); 133void epreset __P((int)); 134static void epstart __P((struct ifnet *)); 135static void epstop __P((struct ep_softc *)); 136static void epwatchdog __P((struct ifnet *)); 137 138#if 0 139static int send_ID_sequence __P((int)); 140#endif 141static int get_eeprom_data __P((int, int)); 142 143static struct ep_softc* ep_softc[NEP]; 144static int ep_current_tag = EP_LAST_TAG + 1; 145static char *ep_conn_type[] = {"UTP", "AUI", "???", "BNC"}; 146 147#define ep_ftst(f) (sc->stat&(f)) 148#define ep_fset(f) (sc->stat|=(f)) 149#define ep_frst(f) (sc->stat&=~(f)) 150 151struct isa_driver epdriver = { 152 ep_isa_probe, 153 ep_isa_attach, 154 "ep", 155 0 156}; 157 158static struct kern_devconf kdc_isa_ep = { 159 0, 0, 0, /* filled in by dev_attach */ 160 "ep", 0, { MDDT_ISA, 0, "net" }, 161 isa_generic_externalize, 0, 0, ISA_EXTERNALLEN, 162 &kdc_isa0, /* parent */ 163 0, /* parentdata */ 164 DC_UNCONFIGURED, /* state */ 165 "3Com 3C509 Ethernet adapter", 166 DC_CLS_NETIF /* class */ 167}; 168 169#include "crd.h" 170 171#if NCRD > 0 172#include "apm.h" 173#include <sys/select.h> 174#include <pccard/card.h> 175#include <pccard/driver.h> 176#include <pccard/slot.h> 177 178/* 179 * PC-Card (PCMCIA) specific code. 180 */ 181static int card_intr __P((struct pccard_dev *)); 182static void ep_unload __P((struct pccard_dev *)); 183static void ep_suspend __P((struct pccard_dev *)); 184static int ep_pccard_init __P((struct pccard_dev *, int)); 185static int ep_pccard_attach __P((struct pccard_dev *)); 186 187static struct pccard_drv ep_info = { 188 "ep", 189 card_intr, 190 ep_unload, 191 ep_suspend, 192 ep_pccard_init, 193 0, /* Attributes - presently unused */ 194 &net_imask 195}; 196 197/* Resume is done by executing ep_pccard_init(dp, 0). */ 198static void 199ep_suspend(dp) 200 struct pccard_dev *dp; 201{ 202 struct ep_softc *sc = ep_softc[dp->isahd.id_unit]; 203 204 printf("ep%d: suspending\n", dp->isahd.id_unit); 205 sc->gone = 1; 206} 207 208/* 209 * 210 */ 211static int 212ep_pccard_init(dp, first) 213 struct pccard_dev *dp; 214 int first; 215{ 216 struct isa_device *is = &dp->isahd; 217 struct ep_softc *sc = ep_softc[is->id_unit]; 218 struct ep_board *epb; 219 int i; 220 221 epb = &ep_board[is->id_unit]; 222 223 if (sc == 0) { 224 if ((sc = ep_alloc(is->id_unit, epb)) == 0) { 225 return (ENXIO); 226 } 227 ep_unit++; 228 ep_isa_registerdev(sc, is); 229 } 230 231 /* get_e() requires these. */ 232 sc->ep_io_addr = is->id_iobase; 233 sc->unit = is->id_unit; 234 235 epb->epb_addr = is->id_iobase; 236 epb->epb_used = 1; 237 epb->prod_id = get_e(sc, EEPROM_PROD_ID); 238 239 if (epb->prod_id != 0x9058) { /* 3C589's product id */ 240 if (first) { 241 printf("ep%d: failed to come ready.\n", is->id_unit); 242 } else { 243 printf("ep%d: failed to resume.\n", is->id_unit); 244 } 245 return (ENXIO); 246 } 247 248 epb->res_cfg = get_e(sc, EEPROM_RESOURCE_CFG); 249 for (i = 0; i < 3; i++) { 250 sc->epb->eth_addr[i] = get_e(sc, EEPROM_NODE_ADDR_0 + i); 251 } 252 253 if (first) { 254 if (ep_pccard_attach(dp) == 0) { 255 return (ENXIO); 256 } 257 sc->arpcom.ac_if.if_snd.ifq_maxlen = ifqmaxlen; 258 } 259 260 if (!first) { 261 sc->kdc->kdc_state = DC_IDLE; 262 sc->gone = 0; 263 printf("ep%d: resumed.\n", is->id_unit); 264 epinit(sc); 265 } 266 267 return (0); 268} 269 270static int 271ep_pccard_attach(dp) 272 struct pccard_dev *dp; 273{ 274 struct isa_device *is = &dp->isahd; 275 struct ep_softc *sc = ep_softc[is->id_unit]; 276 u_short config; 277 278 sc->ep_connectors = 0; 279 config = inw(IS_BASE + EP_W0_CONFIG_CTRL); 280 if (config & IS_BNC) { 281 sc->ep_connectors |= BNC; 282 } 283 if (config & IS_UTP) { 284 sc->ep_connectors |= UTP; 285 } 286 if (!(sc->ep_connectors & 7)) 287 printf("no connectors!"); 288 sc->ep_connector = inw(BASE + EP_W0_ADDRESS_CFG) >> ACF_CONNECTOR_BITS; 289 290 /* ROM size = 0, ROM base = 0 */ 291 /* For now, ignore AUTO SELECT feature of 3C589B and later. */ 292 outw(BASE + EP_W0_ADDRESS_CFG, get_e(sc, EEPROM_ADDR_CFG) & 0xc000); 293 294 /* Fake IRQ must be 3 */ 295 outw(BASE + EP_W0_RESOURCE_CFG, (sc->epb->res_cfg & 0x0fff) | 0x3000); 296 297 outw(BASE + EP_W0_PRODUCT_ID, sc->epb->prod_id); 298 299 ep_attach(sc); 300 301 return 1; 302} 303 304static void 305ep_unload(dp) 306 struct pccard_dev *dp; 307{ 308 struct ep_softc *sc = ep_softc[dp->isahd.id_unit]; 309 310 if (sc->kdc->kdc_state == DC_UNCONFIGURED) { 311 printf("ep%d: already unloaded\n", dp->isahd.id_unit); 312 return; 313 } 314 sc->kdc->kdc_state = DC_UNCONFIGURED; 315 sc->arpcom.ac_if.if_flags &= ~IFF_RUNNING; 316 sc->gone = 1; 317 printf("ep%d: unload\n", dp->isahd.id_unit); 318} 319 320/* 321 * card_intr - Shared interrupt called from 322 * front end of PC-Card handler. 323 */ 324static int 325card_intr(dp) 326 struct pccard_dev *dp; 327{ 328 epintr(dp->isahd.id_unit); 329 return(1); 330} 331 332#endif /* NCRD > 0 */ 333 334static void 335ep_isa_registerdev(sc, id) 336 struct ep_softc *sc; 337 struct isa_device *id; 338{ 339 sc->kdc = (struct kern_devconf *)malloc(sizeof(struct kern_devconf), 340 M_DEVBUF, M_NOWAIT); 341 if (!sc->kdc) { 342 printf("WARNING: ep_isa_registerdev unable to malloc! " 343 "Device kdc will not be registerd\n"); 344 return; 345 } 346 bcopy(&kdc_isa_ep, sc->kdc, sizeof(kdc_isa_ep)); 347 sc->kdc->kdc_unit = sc->unit; 348 sc->kdc->kdc_parentdata = id; 349 dev_attach(sc->kdc); 350} 351 352static int 353eeprom_rdy(sc) 354 struct ep_softc *sc; 355{ 356 int i; 357 358 for (i = 0; is_eeprom_busy(BASE) && i < MAX_EEPROMBUSY; i++); 359 if (i >= MAX_EEPROMBUSY) { 360 printf("ep%d: eeprom failed to come ready.\n", sc->unit); 361 return (0); 362 } 363 return (1); 364} 365 366static struct ep_board * 367ep_look_for_board_at(is) 368 struct isa_device *is; 369{ 370 int data, i, j, id_port = ELINK_ID_PORT; 371 int count = 0; 372 373 if (ep_current_tag == (EP_LAST_TAG + 1)) { 374 /* Come here just one time */ 375 376 ep_current_tag--; 377 378 /* Look for the ISA boards. Init and leave them actived */ 379 outb(id_port, 0); 380 outb(id_port, 0); 381 382 elink_idseq(0xCF); 383 384 elink_reset(); 385 DELAY(10000); 386 for (i = 0; i < EP_MAX_BOARDS; i++) { 387 outb(id_port, 0); 388 outb(id_port, 0); 389 elink_idseq(0xCF); 390 391 data = get_eeprom_data(id_port, EEPROM_MFG_ID); 392 if (data != MFG_ID) 393 break; 394 395 /* resolve contention using the Ethernet address */ 396 397 for (j = 0; j < 3; j++) 398 get_eeprom_data(id_port, j); 399 400 /* and save this address for later use */ 401 402 for (j = 0; j < 3; j++) 403 ep_board[ep_boards].eth_addr[j] = get_eeprom_data(id_port, j); 404 405 ep_board[ep_boards].res_cfg = 406 get_eeprom_data(id_port, EEPROM_RESOURCE_CFG); 407 408 ep_board[ep_boards].prod_id = 409 get_eeprom_data(id_port, EEPROM_PROD_ID); 410 411 ep_board[ep_boards].epb_used = 0; 412 ep_board[ep_boards].epb_addr = 413 (get_eeprom_data(id_port, EEPROM_ADDR_CFG) & 0x1f) * 0x10 + 0x200; 414 415 if(ep_board[ep_boards].epb_addr > 0x3E0) 416 /* Board in EISA configuration mode */ 417 continue; 418 419 outb(id_port, ep_current_tag); /* tags board */ 420 outb(id_port, ACTIVATE_ADAPTER_TO_CONFIG); 421 ep_boards++; 422 count++; 423 ep_current_tag--; 424 } 425 426 ep_board[ep_boards].epb_addr = 0; 427 if (count) { 428 printf("%d 3C5x9 board(s) on ISA found at", count); 429 for (j = 0; ep_board[j].epb_addr; j++) 430 if (ep_board[j].epb_addr <= 0x3E0) 431 printf(" 0x%x", ep_board[j].epb_addr); 432 printf("\n"); 433 } 434 } 435 436 /* we have two cases: 437 * 438 * 1. Device was configured with 'port ?' 439 * In this case we search for the first unused card in list 440 * 441 * 2. Device was configured with 'port xxx' 442 * In this case we search for the unused card with that address 443 * 444 */ 445 446 if(IS_BASE==-1) { /* port? */ 447 for (i = 0; ep_board[i].epb_addr && ep_board[i].epb_used; i++); 448 if(ep_board[i].epb_addr==0) 449 return 0; 450 451 IS_BASE=ep_board[i].epb_addr; 452 ep_board[i].epb_used=1; 453 454 return &ep_board[i]; 455 } else { 456 for (i=0; ep_board[i].epb_addr && ep_board[i].epb_addr != IS_BASE; i++); 457 458 if( ep_board[i].epb_used || ep_board[i].epb_addr != IS_BASE) 459 return 0; 460 461 if (inw(IS_BASE + EP_W0_EEPROM_COMMAND) & EEPROM_TST_MODE) 462 printf("ep%d: 3c5x9 at 0x%x in PnP mode. Disable PnP mode!\n", 463 is->id_unit, IS_BASE); 464 ep_board[i].epb_used=1; 465 466 return &ep_board[i]; 467 } 468} 469 470/* 471 * get_e: gets a 16 bits word from the EEPROM. we must have set the window 472 * before 473 */ 474u_int16_t 475get_e(sc, offset) 476 struct ep_softc *sc; 477 int offset; 478{ 479 if (!eeprom_rdy(sc)) 480 return (0xffff); 481 outw(BASE + EP_W0_EEPROM_COMMAND, EEPROM_CMD_RD | offset); 482 if (!eeprom_rdy(sc)) 483 return (0xffff); 484 return (inw(BASE + EP_W0_EEPROM_DATA)); 485} 486 487struct ep_softc * 488ep_alloc(unit, epb) 489 int unit; 490 struct ep_board *epb; 491{ 492 struct ep_softc *sc; 493 494 if (unit >= NEP) { 495 printf("ep: unit number (%d) too high\n", unit); 496 return NULL; 497 } 498 499 /* 500 * Allocate a storage area for us 501 */ 502 if (ep_softc[unit]) { 503 printf("ep%d: unit number already allocated to another " 504 "adaptor\n", unit); 505 return NULL; 506 } 507 508 sc = malloc(sizeof(struct ep_softc), M_DEVBUF, M_NOWAIT); 509 if(!sc) { 510 printf("ep%d: cannot malloc!\n", unit); 511 return NULL; 512 } 513 bzero(sc, sizeof(struct ep_softc)); 514 ep_softc[unit] = sc; 515 sc->unit = unit; 516 sc->ep_io_addr = epb->epb_addr; 517 sc->epb = epb; 518 519 return(sc); 520} 521 522void 523ep_free(sc) 524 struct ep_softc *sc; 525{ 526 ep_softc[sc->unit] = NULL; 527 free(sc, M_DEVBUF); 528 return; 529} 530 531int 532ep_isa_probe(is) 533 struct isa_device *is; 534{ 535 struct ep_softc *sc; 536 struct ep_board *epb; 537 u_short k; 538 539#if NCRD > 0 540 pccard_add_driver(&ep_info); 541#endif /* NCRD > 0 */ 542 543 if(( epb=ep_look_for_board_at(is) )==0) 544 return (0); 545 546 /* 547 * Allocate a storage area for us 548 */ 549 sc = ep_alloc(ep_unit, epb); 550 if( !sc ) 551 return (0); 552 553 is->id_unit = ep_unit++; 554 555 ep_isa_registerdev(sc, is); 556 557 /* 558 * The iobase was found and MFG_ID was 0x6d50. PROD_ID should be 559 * 0x9[0-f]50 560 */ 561 GO_WINDOW(0); 562 k = sc->epb->prod_id; 563 if ((k & 0xf0ff) != (PROD_ID & 0xf0ff)) { 564 printf("ep_isa_probe: ignoring model %04x\n", k); 565 ep_free(sc); 566 return (0); 567 } 568 569 k = sc->epb->res_cfg; 570 571 k >>= 12; 572 573 /* Now we have two cases again: 574 * 575 * 1. Device was configured with 'irq?' 576 * In this case we use irq read from the board 577 * 578 * 2. Device was configured with 'irq xxx' 579 * In this case we set up the board to use specified interrupt 580 * 581 */ 582 583 if(is->id_irq==0) { /* irq? */ 584 is->id_irq= 1 << ( (k==2) ? 9 : k ); 585 } 586 587 sc->stat = 0; /* 16 bit access */ 588 589 /* By now, the adapter is already activated */ 590 591 return (EP_IOSIZE); /* 16 bytes of I/O space used. */ 592} 593 594static int 595ep_isa_attach(is) 596 struct isa_device *is; 597{ 598 struct ep_softc *sc = ep_softc[is->id_unit]; 599 u_short config; 600 int irq; 601 602 sc->ep_connectors = 0; 603 config = inw(IS_BASE + EP_W0_CONFIG_CTRL); 604 if (config & IS_AUI) { 605 sc->ep_connectors |= AUI; 606 } 607 if (config & IS_BNC) { 608 sc->ep_connectors |= BNC; 609 } 610 if (config & IS_UTP) { 611 sc->ep_connectors |= UTP; 612 } 613 if (!(sc->ep_connectors & 7)) 614 printf("no connectors!"); 615 sc->ep_connector = inw(BASE + EP_W0_ADDRESS_CFG) >> ACF_CONNECTOR_BITS; 616 /* 617 * Write IRQ value to board 618 */ 619 620 irq = ffs(is->id_irq) - 1; 621 if(irq == -1) { 622 printf(" invalid irq... cannot attach\n"); 623 return 0; 624 } 625 626 GO_WINDOW(0); 627 if(irq == 9) 628 irq = 2; 629 outw(BASE + EP_W0_RESOURCE_CFG, SET_IRQ(irq)); 630 631 ep_attach(sc); 632 return 1; 633} 634 635int 636ep_attach(sc) 637 struct ep_softc *sc; 638{ 639 struct ifaddr *ifa; 640 struct ifnet *ifp = &sc->arpcom.ac_if; 641 struct sockaddr_dl *sdl; 642 u_short *p; 643 int i; 644 int attached; 645 646 sc->gone = 0; 647 attached = (ifp->if_softc != 0); 648 649 printf("ep%d: ", sc->unit); 650 /* 651 * Current media type 652 */ 653 if(sc->ep_connectors & AUI) { 654 printf("aui"); 655 if(sc->ep_connectors & ~AUI) 656 printf("/"); 657 } 658 if(sc->ep_connectors & UTP) { 659 printf("utp"); 660 if(sc->ep_connectors & BNC) 661 printf("/"); 662 } 663 if(sc->ep_connectors & BNC) { 664 printf("bnc"); 665 } 666 667 printf("[*%s*]", ep_conn_type[sc->ep_connector]); 668 669 /* 670 * Setup the station address 671 */ 672 p = (u_short *) & sc->arpcom.ac_enaddr; 673 GO_WINDOW(2); 674 for (i = 0; i < 3; i++) { 675 p[i] = htons(sc->epb->eth_addr[i]); 676 outw(BASE + EP_W2_ADDR_0 + (i * 2), ntohs(p[i])); 677 } 678 printf(" address %6D\n", sc->arpcom.ac_enaddr, ":"); 679 680 ifp->if_softc = sc; 681 ifp->if_unit = sc->unit; 682 ifp->if_name = "ep"; 683 ifp->if_mtu = ETHERMTU; 684 ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST; 685 ifp->if_output = ether_output; 686 ifp->if_start = epstart; 687 ifp->if_ioctl = epioctl; 688 ifp->if_watchdog = epwatchdog; 689 690 if (!attached) { 691 if_attach(ifp); 692 ether_ifattach(ifp); 693 } 694 695 /* device attach does transition from UNCONFIGURED to IDLE state */ 696 sc->kdc->kdc_state=DC_IDLE; 697 698 /* 699 * Fill the hardware address into ifa_addr if we find an AF_LINK entry. 700 * We need to do this so bpf's can get the hardware addr of this card. 701 * netstat likes this too! 702 */ 703 ifa = ifp->if_addrlist; 704 while ((ifa != 0) && (ifa->ifa_addr != 0) && 705 (ifa->ifa_addr->sa_family != AF_LINK)) 706 ifa = ifa->ifa_next; 707 708 if ((ifa != 0) && (ifa->ifa_addr != 0)) { 709 sdl = (struct sockaddr_dl *) ifa->ifa_addr; 710 sdl->sdl_type = IFT_ETHER; 711 sdl->sdl_alen = ETHER_ADDR_LEN; 712 sdl->sdl_slen = 0; 713 bcopy(sc->arpcom.ac_enaddr, LLADDR(sdl), ETHER_ADDR_LEN); 714 } 715 /* we give some initial parameters */ 716 sc->rx_avg_pkt = 128; 717 718 /* 719 * NOTE: In all this I multiply everything by 64. 720 * W_s = the speed the CPU is able to write to the TX FIFO. 721 * T_s = the speed the board sends the info to the Ether. 722 * W_s/T_s = 16 (represents 16/64) => W_s = 25 % of T_s. 723 * This will give us for a packet of 1500 bytes 724 * tx_start_thresh=1125 and for a pkt of 64 bytes tx_start_threshold=48. 725 * We prefer to start thinking the CPU is much slower than the Ethernet 726 * transmission. 727 */ 728 sc->tx_rate = TX_INIT_RATE; 729 sc->tx_counter = 0; 730 sc->rx_latency = RX_INIT_LATENCY; 731 sc->rx_early_thresh = RX_INIT_EARLY_THRESH; 732#ifdef EP_LOCAL_STATS 733 sc->rx_no_first = sc->rx_no_mbuf = 734 sc->rx_bpf_disc = sc->rx_overrunf = sc->rx_overrunl = 735 sc->tx_underrun = 0; 736#endif 737 ep_fset(F_RX_FIRST); 738 sc->top = sc->mcur = 0; 739 740#if NBPFILTER > 0 741 if (!attached) { 742 bpfattach(ifp, DLT_EN10MB, sizeof(struct ether_header)); 743 } 744#endif 745 return 0; 746} 747 748 749/* 750 * The order in here seems important. Otherwise we may not receive 751 * interrupts. ?! 752 */ 753static void 754epinit(sc) 755 struct ep_softc *sc; 756{ 757 register struct ifnet *ifp = &sc->arpcom.ac_if; 758 int s, i, j; 759 760 if (sc->gone) 761 return; 762 763 /* 764 if (ifp->if_addrlist == (struct ifaddr *) 0) 765 return; 766 */ 767 768 s = splimp(); 769 while (inw(BASE + EP_STATUS) & S_COMMAND_IN_PROGRESS); 770 771 GO_WINDOW(0); 772 outw(BASE + EP_COMMAND, STOP_TRANSCEIVER); 773 GO_WINDOW(4); 774 outw(BASE + EP_W4_MEDIA_TYPE, DISABLE_UTP); 775 GO_WINDOW(0); 776 777 /* Disable the card */ 778 outw(BASE + EP_W0_CONFIG_CTRL, 0); 779 780 /* Enable the card */ 781 outw(BASE + EP_W0_CONFIG_CTRL, ENABLE_DRQ_IRQ); 782 783 GO_WINDOW(2); 784 785 /* Reload the ether_addr. */ 786 for (i = 0; i < 6; i++) 787 outb(BASE + EP_W2_ADDR_0 + i, sc->arpcom.ac_enaddr[i]); 788 789 outw(BASE + EP_COMMAND, RX_RESET); 790 outw(BASE + EP_COMMAND, TX_RESET); 791 792 /* Window 1 is operating window */ 793 GO_WINDOW(1); 794 for (i = 0; i < 31; i++) 795 inb(BASE + EP_W1_TX_STATUS); 796 797 /* get rid of stray intr's */ 798 outw(BASE + EP_COMMAND, ACK_INTR | 0xff); 799 800 outw(BASE + EP_COMMAND, SET_RD_0_MASK | S_5_INTS); 801 802 outw(BASE + EP_COMMAND, SET_INTR_MASK | S_5_INTS); 803 804 if(ifp->if_flags & IFF_PROMISC) 805 outw(BASE + EP_COMMAND, SET_RX_FILTER | FIL_INDIVIDUAL | 806 FIL_GROUP | FIL_BRDCST | FIL_ALL); 807 else 808 outw(BASE + EP_COMMAND, SET_RX_FILTER | FIL_INDIVIDUAL | 809 FIL_GROUP | FIL_BRDCST); 810 811 /* 812 * S.B. 813 * 814 * Now behavior was slightly changed: 815 * 816 * if any of flags link[0-2] is used and its connector is 817 * physically present the following connectors are used: 818 * 819 * link0 - AUI * highest precedence 820 * link1 - BNC 821 * link2 - UTP * lowest precedence 822 * 823 * If none of them is specified then 824 * connector specified in the EEPROM is used 825 * (if present on card or AUI if not). 826 * 827 */ 828 829 /* Set the xcvr. */ 830 if(ifp->if_flags & IFF_LINK0 && sc->ep_connectors & AUI) { 831 i = ACF_CONNECTOR_AUI; 832 } else if(ifp->if_flags & IFF_LINK1 && sc->ep_connectors & BNC) { 833 i = ACF_CONNECTOR_BNC; 834 } else if(ifp->if_flags & IFF_LINK2 && sc->ep_connectors & UTP) { 835 i = ACF_CONNECTOR_UTP; 836 } else { 837 i = sc->ep_connector; 838 } 839 GO_WINDOW(0); 840 j = inw(BASE + EP_W0_ADDRESS_CFG) & 0x3fff; 841 outw(BASE + EP_W0_ADDRESS_CFG, j | (i << ACF_CONNECTOR_BITS)); 842 843 switch(i) { 844 case ACF_CONNECTOR_UTP: 845 if(sc->ep_connectors & UTP) { 846 GO_WINDOW(4); 847 outw(BASE + EP_W4_MEDIA_TYPE, ENABLE_UTP); 848 } 849 break; 850 case ACF_CONNECTOR_BNC: 851 if(sc->ep_connectors & BNC) { 852 outw(BASE + EP_COMMAND, START_TRANSCEIVER); 853 DELAY(1000); 854 } 855 break; 856 case ACF_CONNECTOR_AUI: 857 /* nothing to do */ 858 break; 859 default: 860 printf("ep%d: strange connector type in EEPROM: assuming AUI\n", 861 sc->unit); 862 break; 863 } 864 865 outw(BASE + EP_COMMAND, RX_ENABLE); 866 outw(BASE + EP_COMMAND, TX_ENABLE); 867 868 ifp->if_flags |= IFF_RUNNING; 869 ifp->if_flags &= ~IFF_OACTIVE; /* just in case */ 870 871 sc->tx_rate = TX_INIT_RATE; 872 sc->tx_counter = 0; 873 sc->rx_latency = RX_INIT_LATENCY; 874 sc->rx_early_thresh = RX_INIT_EARLY_THRESH; 875#ifdef EP_LOCAL_STATS 876 sc->rx_no_first = sc->rx_no_mbuf = 877 sc->rx_bpf_disc = sc->rx_overrunf = sc->rx_overrunl = 878 sc->tx_underrun = 0; 879#endif 880 ep_fset(F_RX_FIRST); 881 ep_frst(F_RX_TRAILER); 882 if (sc->top) { 883 m_freem(sc->top); 884 sc->top = sc->mcur = 0; 885 } 886 outw(BASE + EP_COMMAND, SET_RX_EARLY_THRESH | sc->rx_early_thresh); 887 888 /* 889 * These clever computations look very interesting 890 * but the fixed threshold gives near no output errors 891 * and if it as low as 16 bytes it gives the max. throughput. 892 * We think that processor is anyway quicker than Ethernet 893 * (and this should be true for any 386 and higher) 894 */ 895 896 outw(BASE + EP_COMMAND, SET_TX_START_THRESH | 16); 897 898 /* 899 * Store up a bunch of mbuf's for use later. (MAX_MBS). First we free up 900 * any that we had in case we're being called from intr or somewhere 901 * else. 902 */ 903 sc->last_mb = 0; 904 sc->next_mb = 0; 905 epmbuffill((caddr_t) sc, 0); 906 907 GO_WINDOW(1); 908 epstart(ifp); 909 910 splx(s); 911} 912 913static const char padmap[] = {0, 3, 2, 1}; 914 915static void 916epstart(ifp) 917 struct ifnet *ifp; 918{ 919 register struct ep_softc *sc = ifp->if_softc; 920 register u_int len; 921 register struct mbuf *m; 922 struct mbuf *top; 923 int s, pad; 924 925 if (sc->gone) { 926 return; 927 } 928 929 s = splimp(); 930 if (ifp->if_flags & IFF_OACTIVE) { 931 splx(s); 932 return; 933 } 934startagain: 935 /* Sneak a peek at the next packet */ 936 m = ifp->if_snd.ifq_head; 937 if (m == 0) { 938 splx(s); 939 return; 940 } 941 for (len = 0, top = m; m; m = m->m_next) 942 len += m->m_len; 943 944 pad = padmap[len & 3]; 945 946 /* 947 * The 3c509 automatically pads short packets to minimum ethernet length, 948 * but we drop packets that are too large. Perhaps we should truncate 949 * them instead? 950 */ 951 if (len + pad > ETHER_MAX_LEN) { 952 /* packet is obviously too large: toss it */ 953 ++ifp->if_oerrors; 954 IF_DEQUEUE(&ifp->if_snd, m); 955 m_freem(m); 956 goto readcheck; 957 } 958 if (inw(BASE + EP_W1_FREE_TX) < len + pad + 4) { 959 /* no room in FIFO */ 960 outw(BASE + EP_COMMAND, SET_TX_AVAIL_THRESH | (len + pad + 4)); 961 ifp->if_flags |= IFF_OACTIVE; 962 splx(s); 963 return; 964 } 965 IF_DEQUEUE(&ifp->if_snd, m); 966 967 outw(BASE + EP_W1_TX_PIO_WR_1, len); 968 outw(BASE + EP_W1_TX_PIO_WR_1, 0x0); /* Second dword meaningless */ 969 970 /* compute the Tx start threshold for this packet */ 971 sc->tx_start_thresh = len = 972 (((len * (64 - sc->tx_rate)) >> 6) & ~3) + 16; 973#if 0 974 /* 975 * The following string does something strange with the card and 976 * we get a lot of output errors due to it so it's commented out 977 * and we use fixed threshold (see above) 978 */ 979 980 outw(BASE + EP_COMMAND, SET_TX_START_THRESH | len); 981#endif 982 983 for (top = m; m != 0; m = m->m_next) 984 if(ep_ftst(F_ACCESS_32_BITS)) { 985 outsl(BASE + EP_W1_TX_PIO_WR_1, mtod(m, caddr_t), 986 m->m_len / 4); 987 if (m->m_len & 3) 988 outsb(BASE + EP_W1_TX_PIO_WR_1, 989 mtod(m, caddr_t) + (m->m_len & (~3)), 990 m->m_len & 3); 991 } else { 992 outsw(BASE + EP_W1_TX_PIO_WR_1, mtod(m, caddr_t), m->m_len / 2); 993 if (m->m_len & 1) 994 outb(BASE + EP_W1_TX_PIO_WR_1, 995 *(mtod(m, caddr_t) + m->m_len - 1)); 996 } 997 998 while (pad--) 999 outb(BASE + EP_W1_TX_PIO_WR_1, 0); /* Padding */ 1000 1001#if NBPFILTER > 0 1002 if (ifp->if_bpf) { 1003 bpf_mtap(ifp, top); 1004 } 1005#endif 1006 1007 ifp->if_timer=2; 1008 ifp->if_opackets++; 1009 m_freem(top); 1010 /* 1011 * Every 1024*4 packets we increment the tx_rate if we haven't had 1012 * errors, that in the case it has abnormaly goten too low 1013 */ 1014 if (!(++sc->tx_counter & (1024 * 4 - 1)) && 1015 sc->tx_rate < TX_INIT_MAX_RATE) 1016 sc->tx_rate++; 1017 1018 /* 1019 * Is another packet coming in? We don't want to overflow the tiny RX 1020 * fifo. 1021 */ 1022readcheck: 1023 if (inw(BASE + EP_W1_RX_STATUS) & RX_BYTES_MASK) { 1024 /* 1025 * we check if we have packets left, in that case we prepare to come 1026 * back later 1027 */ 1028 if (ifp->if_snd.ifq_head) { 1029 outw(BASE + EP_COMMAND, SET_TX_AVAIL_THRESH | 1030 sc->tx_start_thresh); 1031 } 1032 splx(s); 1033 return; 1034 } 1035 goto startagain; 1036} 1037 1038void 1039epintr(unit) 1040 int unit; 1041{ 1042 register struct ep_softc *sc = ep_softc[unit]; 1043 1044 if (sc->gone) { 1045 return; 1046 } 1047 1048 ep_intr(sc); 1049} 1050 1051void 1052ep_intr(arg) 1053 void *arg; 1054{ 1055 struct ep_softc *sc; 1056 register int status; 1057 struct ifnet *ifp; 1058 int x; 1059 1060 x=splbio(); 1061 1062 sc = (struct ep_softc *)arg; 1063 1064 ifp = &sc->arpcom.ac_if; 1065 1066 outw(BASE + EP_COMMAND, SET_INTR_MASK); /* disable all Ints */ 1067 1068rescan: 1069 1070 while ((status = inw(BASE + EP_STATUS)) & S_5_INTS) { 1071 1072 /* first acknowledge all interrupt sources */ 1073 outw(BASE + EP_COMMAND, ACK_INTR | (status & S_MASK)); 1074 1075 if (status & (S_RX_COMPLETE | S_RX_EARLY)) { 1076 epread(sc); 1077 continue; 1078 } 1079 if (status & S_TX_AVAIL) { 1080 /* we need ACK */ 1081 ifp->if_timer=0; 1082 ifp->if_flags &= ~IFF_OACTIVE; 1083 GO_WINDOW(1); 1084 inw(BASE + EP_W1_FREE_TX); 1085 epstart(ifp); 1086 } 1087 if (status & S_CARD_FAILURE) { 1088 ifp->if_timer=0; 1089#ifdef EP_LOCAL_STATS 1090 printf("\nep%d:\n\tStatus: %x\n", sc->unit, status); 1091 GO_WINDOW(4); 1092 printf("\tFIFO Diagnostic: %x\n", inw(BASE + EP_W4_FIFO_DIAG)); 1093 printf("\tStat: %x\n", sc->stat); 1094 printf("\tIpackets=%d, Opackets=%d\n", 1095 ifp->if_ipackets, ifp->if_opackets); 1096 printf("\tNOF=%d, NOMB=%d, BPFD=%d, RXOF=%d, RXOL=%d, TXU=%d\n", 1097 sc->rx_no_first, sc->rx_no_mbuf, sc->rx_bpf_disc, sc->rx_overrunf, 1098 sc->rx_overrunl, sc->tx_underrun); 1099#else 1100 1101#ifdef DIAGNOSTIC 1102 printf("ep%d: Status: %x (input buffer overflow)\n", sc->unit, status); 1103#else 1104 ++ifp->if_ierrors; 1105#endif 1106 1107#endif 1108 epinit(sc); 1109 splx(x); 1110 return; 1111 } 1112 if (status & S_TX_COMPLETE) { 1113 ifp->if_timer=0; 1114 /* we need ACK. we do it at the end */ 1115 /* 1116 * We need to read TX_STATUS until we get a 0 status in order to 1117 * turn off the interrupt flag. 1118 */ 1119 while ((status = inb(BASE + EP_W1_TX_STATUS)) & TXS_COMPLETE) { 1120 if (status & TXS_SUCCES_INTR_REQ); 1121 else if (status & (TXS_UNDERRUN | TXS_JABBER | TXS_MAX_COLLISION)) { 1122 outw(BASE + EP_COMMAND, TX_RESET); 1123 if (status & TXS_UNDERRUN) { 1124 if (sc->tx_rate > 1) { 1125 sc->tx_rate--; /* Actually in steps of 1/64 */ 1126 sc->tx_counter = 0; /* We reset it */ 1127 } 1128#ifdef EP_LOCAL_STATS 1129 sc->tx_underrun++; 1130#endif 1131 } else { 1132 if (status & TXS_JABBER); 1133 else /* TXS_MAX_COLLISION - we shouldn't get here */ 1134 ++ifp->if_collisions; 1135 } 1136 ++ifp->if_oerrors; 1137 outw(BASE + EP_COMMAND, TX_ENABLE); 1138 /* 1139 * To have a tx_avail_int but giving the chance to the 1140 * Reception 1141 */ 1142 if (ifp->if_snd.ifq_head) { 1143 outw(BASE + EP_COMMAND, SET_TX_AVAIL_THRESH | 8); 1144 } 1145 } 1146 outb(BASE + EP_W1_TX_STATUS, 0x0); /* pops up the next 1147 * status */ 1148 } /* while */ 1149 ifp->if_flags &= ~IFF_OACTIVE; 1150 GO_WINDOW(1); 1151 inw(BASE + EP_W1_FREE_TX); 1152 epstart(ifp); 1153 } /* end TX_COMPLETE */ 1154 } 1155 1156 outw(BASE + EP_COMMAND, C_INTR_LATCH); /* ACK int Latch */ 1157 1158 if ((status = inw(BASE + EP_STATUS)) & S_5_INTS) 1159 goto rescan; 1160 1161 /* re-enable Ints */ 1162 outw(BASE + EP_COMMAND, SET_INTR_MASK | S_5_INTS); 1163 1164 splx(x); 1165} 1166 1167static void 1168epread(sc) 1169 register struct ep_softc *sc; 1170{ 1171 struct ether_header *eh; 1172 struct mbuf *top, *mcur, *m; 1173 struct ifnet *ifp; 1174 int lenthisone; 1175 1176 short rx_fifo2, status; 1177 register short delta; 1178 register short rx_fifo; 1179 1180 ifp = &sc->arpcom.ac_if; 1181 status = inw(BASE + EP_W1_RX_STATUS); 1182 1183read_again: 1184 1185 if (status & ERR_RX) { 1186 ++ifp->if_ierrors; 1187 if (status & ERR_RX_OVERRUN) { 1188 /* 1189 * we can think the rx latency is actually greather than we 1190 * expect 1191 */ 1192#ifdef EP_LOCAL_STATS 1193 if (ep_ftst(F_RX_FIRST)) 1194 sc->rx_overrunf++; 1195 else 1196 sc->rx_overrunl++; 1197#endif 1198 if (sc->rx_latency < ETHERMTU) 1199 sc->rx_latency += 16; 1200 } 1201 goto out; 1202 } 1203 rx_fifo = rx_fifo2 = status & RX_BYTES_MASK; 1204 1205 if (ep_ftst(F_RX_FIRST)) { 1206 if (m = sc->mb[sc->next_mb]) { 1207 sc->mb[sc->next_mb] = 0; 1208 sc->next_mb = (sc->next_mb + 1) % MAX_MBS; 1209 m->m_data = m->m_pktdat; 1210 m->m_flags = M_PKTHDR; 1211 } else { 1212 MGETHDR(m, M_DONTWAIT, MT_DATA); 1213 if (!m) 1214 goto out; 1215 } 1216 sc->top = sc->mcur = top = m; 1217#define EROUND ((sizeof(struct ether_header) + 3) & ~3) 1218#define EOFF (EROUND - sizeof(struct ether_header)) 1219 top->m_data += EOFF; 1220 1221 /* Read what should be the header. */ 1222 insw(BASE + EP_W1_RX_PIO_RD_1, 1223 mtod(top, caddr_t), sizeof(struct ether_header) / 2); 1224 top->m_len = sizeof(struct ether_header); 1225 rx_fifo -= sizeof(struct ether_header); 1226 sc->cur_len = rx_fifo2; 1227 } else { 1228 /* come here if we didn't have a complete packet last time */ 1229 top = sc->top; 1230 m = sc->mcur; 1231 sc->cur_len += rx_fifo2; 1232 if (ep_ftst(F_RX_TRAILER)) 1233 /* We don't read the trailer */ 1234 rx_fifo -= sizeof(struct ether_header); 1235 } 1236 1237 /* Reads what is left in the RX FIFO */ 1238 while (rx_fifo > 0) { 1239 lenthisone = min(rx_fifo, M_TRAILINGSPACE(m)); 1240 if (lenthisone == 0) { /* no room in this one */ 1241 mcur = m; 1242 if (m = sc->mb[sc->next_mb]) { 1243 sc->mb[sc->next_mb] = 0; 1244 sc->next_mb = (sc->next_mb + 1) % MAX_MBS; 1245 } else { 1246 MGET(m, M_DONTWAIT, MT_DATA); 1247 if (!m) 1248 goto out; 1249 } 1250 1251 if (rx_fifo >= MINCLSIZE) 1252 MCLGET(m, M_DONTWAIT); 1253 m->m_len = 0; 1254 mcur->m_next = m; 1255 lenthisone = min(rx_fifo, M_TRAILINGSPACE(m)); 1256 } 1257 if (ep_ftst(F_ACCESS_32_BITS)) { /* default for EISA configured cards*/ 1258 insl(BASE + EP_W1_RX_PIO_RD_1, mtod(m, caddr_t) + m->m_len, 1259 lenthisone / 4); 1260 m->m_len += (lenthisone & ~3); 1261 if (lenthisone & 3) 1262 insb(BASE + EP_W1_RX_PIO_RD_1, 1263 mtod(m, caddr_t) + m->m_len, 1264 lenthisone & 3); 1265 m->m_len += (lenthisone & 3); 1266 } else { 1267 insw(BASE + EP_W1_RX_PIO_RD_1, mtod(m, caddr_t) + m->m_len, 1268 lenthisone / 2); 1269 m->m_len += lenthisone; 1270 if (lenthisone & 1) 1271 *(mtod(m, caddr_t) + m->m_len - 1) = inb(BASE + EP_W1_RX_PIO_RD_1); 1272 } 1273 rx_fifo -= lenthisone; 1274 } 1275 1276 if (ep_ftst(F_RX_TRAILER)) {/* reads the trailer */ 1277 if (m = sc->mb[sc->next_mb]) { 1278 sc->mb[sc->next_mb] = 0; 1279 sc->next_mb = (sc->next_mb + 1) % MAX_MBS; 1280 m->m_data = m->m_pktdat; 1281 m->m_flags = M_PKTHDR; 1282 } else { 1283 MGETHDR(m, M_DONTWAIT, MT_DATA); 1284 if (!m) 1285 goto out; 1286 } 1287 insw(BASE + EP_W1_RX_PIO_RD_1, mtod(m, caddr_t), 1288 sizeof(struct ether_header)); 1289 m->m_len = sizeof(struct ether_header); 1290 m->m_next = top; 1291 sc->top = top = m; 1292 /* XXX Accomodate for type and len from beginning of trailer */ 1293 sc->cur_len -= (2 * sizeof(u_short)); 1294 ep_frst(F_RX_TRAILER); 1295 goto all_pkt; 1296 } 1297 1298 if (status & ERR_RX_INCOMPLETE) { /* we haven't received the complete 1299 * packet */ 1300 sc->mcur = m; 1301#ifdef EP_LOCAL_STATS 1302 sc->rx_no_first++; /* to know how often we come here */ 1303#endif 1304 /* 1305 * Re-compute rx_latency, the factor used is 1/4 to go up and 1/32 to 1306 * go down 1307 */ 1308 delta = rx_fifo2 - sc->rx_early_thresh; /* last latency seen LLS */ 1309 delta -= sc->rx_latency;/* LLS - estimated_latency */ 1310 if (delta >= 0) 1311 sc->rx_latency += (delta / 4); 1312 else 1313 sc->rx_latency += (delta / 32); 1314 ep_frst(F_RX_FIRST); 1315 if (!((status = inw(BASE + EP_W1_RX_STATUS)) & ERR_RX_INCOMPLETE)) { 1316 /* we see if by now, the packet has completly arrived */ 1317 goto read_again; 1318 } 1319 /* compute rx_early_threshold */ 1320 delta = (sc->rx_avg_pkt - sc->cur_len - sc->rx_latency - 16) & ~3; 1321 if (delta < MIN_RX_EARLY_THRESHL) 1322 delta = MIN_RX_EARLY_THRESHL; 1323 1324 outw(BASE + EP_COMMAND, SET_RX_EARLY_THRESH | 1325 (sc->rx_early_thresh = delta)); 1326 return; 1327 } 1328all_pkt: 1329 outw(BASE + EP_COMMAND, RX_DISCARD_TOP_PACK); 1330 /* 1331 * recompute average packet's length, the factor used is 1/8 to go down 1332 * and 1/32 to go up 1333 */ 1334 delta = sc->cur_len - sc->rx_avg_pkt; 1335 if (delta > 0) 1336 sc->rx_avg_pkt += (delta / 32); 1337 else 1338 sc->rx_avg_pkt += (delta / 8); 1339 delta = (sc->rx_avg_pkt - sc->rx_latency - 16) & ~3; 1340 if (delta < MIN_RX_EARLY_THRESHF) 1341 delta = MIN_RX_EARLY_THRESHF; 1342 sc->rx_early_thresh = delta; 1343 ++ifp->if_ipackets; 1344 ep_fset(F_RX_FIRST); 1345 ep_frst(F_RX_TRAILER); 1346 top->m_pkthdr.rcvif = &sc->arpcom.ac_if; 1347 top->m_pkthdr.len = sc->cur_len; 1348 1349#if NBPFILTER > 0 1350 if (ifp->if_bpf) { 1351 bpf_mtap(ifp, top); 1352 1353 /* 1354 * Note that the interface cannot be in promiscuous mode if there are 1355 * no BPF listeners. And if we are in promiscuous mode, we have to 1356 * check if this packet is really ours. 1357 */ 1358 eh = mtod(top, struct ether_header *); 1359 if ((ifp->if_flags & IFF_PROMISC) && 1360 (eh->ether_dhost[0] & 1) == 0 && 1361 bcmp(eh->ether_dhost, sc->arpcom.ac_enaddr, 1362 sizeof(eh->ether_dhost)) != 0 && 1363 bcmp(eh->ether_dhost, etherbroadcastaddr, 1364 sizeof(eh->ether_dhost)) != 0) { 1365 if (sc->top) { 1366 m_freem(sc->top); 1367 sc->top = 0; 1368 } 1369 ep_fset(F_RX_FIRST); 1370 ep_frst(F_RX_TRAILER); 1371#ifdef EP_LOCAL_STATS 1372 sc->rx_bpf_disc++; 1373#endif 1374 while (inw(BASE + EP_STATUS) & S_COMMAND_IN_PROGRESS); 1375 outw(BASE + EP_COMMAND, SET_RX_EARLY_THRESH | delta); 1376 return; 1377 } 1378 } 1379#endif 1380 1381 eh = mtod(top, struct ether_header *); 1382 m_adj(top, sizeof(struct ether_header)); 1383 ether_input(ifp, eh, top); 1384 if (!sc->mb[sc->next_mb]) 1385 epmbuffill((caddr_t) sc, 0); 1386 sc->top = 0; 1387 while (inw(BASE + EP_STATUS) & S_COMMAND_IN_PROGRESS); 1388 outw(BASE + EP_COMMAND, SET_RX_EARLY_THRESH | delta); 1389 return; 1390 1391out: 1392 outw(BASE + EP_COMMAND, RX_DISCARD_TOP_PACK); 1393 if (sc->top) { 1394 m_freem(sc->top); 1395 sc->top = 0; 1396#ifdef EP_LOCAL_STATS 1397 sc->rx_no_mbuf++; 1398#endif 1399 } 1400 delta = (sc->rx_avg_pkt - sc->rx_latency - 16) & ~3; 1401 if (delta < MIN_RX_EARLY_THRESHF) 1402 delta = MIN_RX_EARLY_THRESHF; 1403 ep_fset(F_RX_FIRST); 1404 ep_frst(F_RX_TRAILER); 1405 while (inw(BASE + EP_STATUS) & S_COMMAND_IN_PROGRESS); 1406 outw(BASE + EP_COMMAND, SET_RX_EARLY_THRESH | 1407 (sc->rx_early_thresh = delta)); 1408} 1409 1410/* 1411 * Look familiar? 1412 */ 1413static int 1414epioctl(ifp, cmd, data) 1415 register struct ifnet *ifp; 1416 int cmd; 1417 caddr_t data; 1418{ 1419 register struct ifaddr *ifa = (struct ifaddr *) data; 1420 struct ep_softc *sc = ifp->if_softc; 1421 struct ifreq *ifr = (struct ifreq *) data; 1422 int s, error = 0; 1423 1424 s = splimp(); 1425 1426 switch (cmd) { 1427 case SIOCSIFADDR: 1428 ifp->if_flags |= IFF_UP; 1429 1430 /* netifs are BUSY when UP */ 1431 sc->kdc->kdc_state=DC_BUSY; 1432 1433 switch (ifa->ifa_addr->sa_family) { 1434#ifdef INET 1435 case AF_INET: 1436 epinit(sc); /* before arpwhohas */ 1437 arp_ifinit((struct arpcom *)ifp, ifa); 1438 break; 1439#endif 1440#ifdef IPX 1441 case AF_IPX: 1442 { 1443 register struct ipx_addr *ina = &(IA_SIPX(ifa)->sipx_addr); 1444 1445 if (ipx_nullhost(*ina)) 1446 ina->x_host = 1447 *(union ipx_host *) (sc->arpcom.ac_enaddr); 1448 else { 1449 ifp->if_flags &= ~IFF_RUNNING; 1450 bcopy((caddr_t) ina->x_host.c_host, 1451 (caddr_t) sc->arpcom.ac_enaddr, 1452 sizeof(sc->arpcom.ac_enaddr)); 1453 } 1454 epinit(sc); 1455 break; 1456 } 1457#endif 1458#ifdef NS 1459 case AF_NS: 1460 { 1461 register struct ns_addr *ina = &(IA_SNS(ifa)->sns_addr); 1462 1463 if (ns_nullhost(*ina)) 1464 ina->x_host = 1465 *(union ns_host *) (sc->arpcom.ac_enaddr); 1466 else { 1467 ifp->if_flags &= ~IFF_RUNNING; 1468 bcopy((caddr_t) ina->x_host.c_host, 1469 (caddr_t) sc->arpcom.ac_enaddr, 1470 sizeof(sc->arpcom.ac_enaddr)); 1471 } 1472 epinit(sc); 1473 break; 1474 } 1475#endif 1476 default: 1477 epinit(sc); 1478 break; 1479 } 1480 break; 1481 case SIOCGIFADDR: 1482 { 1483 struct sockaddr *sa; 1484 1485 sa = (struct sockaddr *) & ifr->ifr_data; 1486 bcopy((caddr_t) sc->arpcom.ac_enaddr, 1487 (caddr_t) sa->sa_data, ETHER_ADDR_LEN); 1488 } 1489 break; 1490 case SIOCSIFFLAGS: 1491 /* UP controls BUSY/IDLE */ 1492 sc->kdc->kdc_state= ( (ifp->if_flags & IFF_UP) 1493 ? DC_BUSY 1494 : DC_IDLE ); 1495 1496 if ((ifp->if_flags & IFF_UP) == 0 && ifp->if_flags & IFF_RUNNING) { 1497 ifp->if_flags &= ~IFF_RUNNING; 1498 epstop(sc); 1499 epmbufempty(sc); 1500 break; 1501 } else { 1502 /* reinitialize card on any parameter change */ 1503 epinit(sc); 1504 break; 1505 } 1506 1507 /* NOTREACHED */ 1508 break; 1509#ifdef notdef 1510 case SIOCGHWADDR: 1511 bcopy((caddr_t) sc->sc_addr, (caddr_t) & ifr->ifr_data, 1512 sizeof(sc->sc_addr)); 1513 break; 1514#endif 1515 case SIOCSIFMTU: 1516 1517 /* 1518 * Set the interface MTU. 1519 */ 1520 if (ifr->ifr_mtu > ETHERMTU) { 1521 error = EINVAL; 1522 } else { 1523 ifp->if_mtu = ifr->ifr_mtu; 1524 } 1525 break; 1526 case SIOCADDMULTI: 1527 case SIOCDELMULTI: 1528 /* Now this driver has no support for programmable 1529 * multicast filters. If some day it will gain this 1530 * support this part of code must be extended. 1531 */ 1532 error=0; 1533 break; 1534 default: 1535 error = EINVAL; 1536 } 1537 1538 splx(s); 1539 1540 return (error); 1541} 1542 1543static void 1544epwatchdog(ifp) 1545 struct ifnet *ifp; 1546{ 1547 struct ep_softc *sc = ifp->if_softc; 1548 1549 /* 1550 printf("ep: watchdog\n"); 1551 1552 log(LOG_ERR, "ep%d: watchdog\n", ifp->if_unit); 1553 ifp->if_oerrors++; 1554 */ 1555 1556 if (sc->gone) { 1557 return; 1558 } 1559 1560 ifp->if_flags &= ~IFF_OACTIVE; 1561 epstart(ifp); 1562 ep_intr(ifp->if_softc); 1563} 1564 1565static void 1566epstop(sc) 1567 struct ep_softc *sc; 1568{ 1569 if (sc->gone) { 1570 return; 1571 } 1572 1573 outw(BASE + EP_COMMAND, RX_DISABLE); 1574 outw(BASE + EP_COMMAND, RX_DISCARD_TOP_PACK); 1575 while (inw(BASE + EP_STATUS) & S_COMMAND_IN_PROGRESS); 1576 outw(BASE + EP_COMMAND, TX_DISABLE); 1577 outw(BASE + EP_COMMAND, STOP_TRANSCEIVER); 1578 outw(BASE + EP_COMMAND, RX_RESET); 1579 outw(BASE + EP_COMMAND, TX_RESET); 1580 outw(BASE + EP_COMMAND, C_INTR_LATCH); 1581 outw(BASE + EP_COMMAND, SET_RD_0_MASK); 1582 outw(BASE + EP_COMMAND, SET_INTR_MASK); 1583 outw(BASE + EP_COMMAND, SET_RX_FILTER); 1584} 1585 1586 1587#if 0 1588static int 1589send_ID_sequence(port) 1590 int port; 1591{ 1592 int cx, al; 1593 1594 for (al = 0xff, cx = 0; cx < 255; cx++) { 1595 outb(port, al); 1596 al <<= 1; 1597 if (al & 0x100) 1598 al ^= 0xcf; 1599 } 1600 return (1); 1601} 1602#endif 1603 1604 1605/* 1606 * We get eeprom data from the id_port given an offset into the eeprom. 1607 * Basically; after the ID_sequence is sent to all of the cards; they enter 1608 * the ID_CMD state where they will accept command requests. 0x80-0xbf loads 1609 * the eeprom data. We then read the port 16 times and with every read; the 1610 * cards check for contention (ie: if one card writes a 0 bit and another 1611 * writes a 1 bit then the host sees a 0. At the end of the cycle; each card 1612 * compares the data on the bus; if there is a difference then that card goes 1613 * into ID_WAIT state again). In the meantime; one bit of data is returned in 1614 * the AX register which is conveniently returned to us by inb(). Hence; we 1615 * read 16 times getting one bit of data with each read. 1616 */ 1617static int 1618get_eeprom_data(id_port, offset) 1619 int id_port; 1620 int offset; 1621{ 1622 int i, data = 0; 1623 outb(id_port, 0x80 + offset); 1624 DELAY(1000); 1625 for (i = 0; i < 16; i++) 1626 data = (data << 1) | (inw(id_port) & 1); 1627 return (data); 1628} 1629 1630/* 1631 * We suppose this is always called inside a splimp(){...}splx() region 1632 */ 1633static void 1634epmbuffill(sp, dummy_arg) 1635 caddr_t sp; 1636 int dummy_arg; 1637{ 1638 struct ep_softc *sc = (struct ep_softc *) sp; 1639 int i; 1640 1641 i = sc->last_mb; 1642 do { 1643 if (sc->mb[i] == NULL) 1644 MGET(sc->mb[i], M_DONTWAIT, MT_DATA); 1645 if (sc->mb[i] == NULL) 1646 break; 1647 i = (i + 1) % MAX_MBS; 1648 } while (i != sc->next_mb); 1649 sc->last_mb = i; 1650} 1651 1652static void 1653epmbufempty(sc) 1654 struct ep_softc *sc; 1655{ 1656 int s, i; 1657 1658 s = splimp(); 1659 for (i = 0; i < MAX_MBS; i++) { 1660 if (sc->mb[i]) { 1661 m_freem(sc->mb[i]); 1662 sc->mb[i] = NULL; 1663 } 1664 } 1665 sc->last_mb = sc->next_mb = 0; 1666 splx(s); 1667} 1668 1669#endif /* NEP > 0 */ 1670