|
|
1.1 ! root 1: #ifndef lint ! 2: static char sccsid[] = "@(#)if_ie.c 1.1 86/02/03 Copyr 1985 Sun Micro"; ! 3: #endif ! 4: ! 5: /* ! 6: * Copyright (c) 1985 by Sun Microsystems, Inc. ! 7: */ ! 8: ! 9: /* ! 10: * Parameters controlling TIMEBOMB action: times out if chip hangs. ! 11: * ! 12: */ ! 13: #define TIMEBOMB 1000000 /* One million times around is all... */ ! 14: #define TIMEOUT -1 /* if (function()) return (TIMEOUT); */ ! 15: #define OK 0 /* Traditional OK value */ ! 16: ! 17: ! 18: /* ! 19: * Sun Intel Ethernet Controller interface ! 20: */ ! 21: #include "saio.h" ! 22: #include "param.h" ! 23: #include "../h/socket.h" ! 24: #include "../sunif/if_iereg.h" ! 25: #include "../sunif/if_mie.h" ! 26: #include "../sunif/if_obie.h" ! 27: #include "../mon/idprom.h" ! 28: #include "../mon/cpu.map.h" ! 29: ! 30: int iexmit(), iepoll(), iereset(); ! 31: ! 32: unsigned long iestd[] = { 0x88000, 0x8C000 }; ! 33: #define NSTD 2 ! 34: ! 35: struct saif ieif = { ! 36: iexmit, ! 37: iepoll, ! 38: iereset, ! 39: }; ! 40: ! 41: #define IEVVSIZ 1024 /* # of pages in page map */ ! 42: #define IEPHYMEMSIZ (16*1024) ! 43: #define IEVIRMEMSIZ (16*1024) ! 44: #define IEPAGSIZ 1024 ! 45: #define IERBUFSIZ 1600 ! 46: #define IEXBUFSIZ 1600 ! 47: ! 48: #ifdef SUN2 ! 49: #define IEDMABASE 0x000000 /* Can access all of memory */ ! 50: #endif SUN2 ! 51: #ifdef SUN3 ! 52: #define IEDMABASE 0x0F000000 /* Can access top 16MB of memory */ ! 53: #endif SUN3 ! 54: ! 55: /* Location in virtual memory of the SCP (System Configuration Pointer) */ ! 56: #define SCP_LOC (char *)(IEDMABASE+IESCPADDR) ! 57: ! 58: /* controller types */ ! 59: #define IE_MB 1 /* Multibus */ ! 60: #define IE_OB 2 /* onboard */ ! 61: ! 62: struct ie_softc { ! 63: /* ! 64: * This first item does two things. First, it reserves space for ! 65: * all the various protocols that need to put their locals somewhere ! 66: * (it was decided that HERE is convenient!). Second, it fills ! 67: * out the structure to align es_scp to the wierd-in address ! 68: * that Intel (thanks guys) fetches it from. ! 69: */ ! 70: char es_fill[PROTOSCRATCH-sizeof(struct iescp)]; /* Align */ ! 71: struct iescp es_scp; /* System config pointer (used once) */ ! 72: struct ieiscp es_iscp; /* Intermediate sys config ptr (once) */ ! 73: struct iescb es_scb; /* Sys Control Block, the real mama */ ! 74: struct ierbd es_rbd; ! 75: struct ierbd es_rbd2; /* Hack for 82586 ucode bugs */ ! 76: struct ierfd es_rfd; ! 77: struct ietfd es_tfd; ! 78: struct ietbd es_tbd; ! 79: struct mie_device *es_mie; ! 80: struct obie_device *es_obie; ! 81: short es_type; ! 82: struct ieiaddr es_iaddr; /* Cmd to set up our Ethernet addr */ ! 83: struct ieconf es_ic; /* Cmd to configure the chip */ ! 84: char es_rbuf[IERBUFSIZ]; ! 85: char es_xbuf[IEXBUFSIZ]; /* buffer accessible by chip */ ! 86: char es_rbuf2[10]; /* Hack for 82586 ucode bugs */ ! 87: }; ! 88: ! 89: /* ! 90: * This initializes the onboard Ethernet control reg to: ! 91: * Reset is active ! 92: * Loopback is NOT active ! 93: * Channel Attn is not active ! 94: * Interrupt enable is not active. ! 95: * Loopback is deactivated due to a bug in the Intel serial interface ! 96: * chip. This chip powers-up in a locked up state if Loopback is active. ! 97: * It "unlocks" itself if you release Loopback; then it's OK to reassert it. ! 98: */ ! 99: struct obie_device obie_reset = {0, 1, 0, 0, 0, 0, 0}; ! 100: ! 101: ieoff_t to_ieoff(); ! 102: ieaddr_t to_ieaddr(); ! 103: ! 104: #ifdef DEBUG ! 105: ieint_t from_ieint(); ! 106: #endif DEBUG ! 107: ! 108: struct devinfo ieinfo = { ! 109: sizeof (struct mie_device), ! 110: sizeof(struct ie_softc), ! 111: 0, ! 112: NSTD, ! 113: iestd, ! 114: MAP_MBMEM, ! 115: 0, /* transfer size handled by ND */ ! 116: }; ! 117: ! 118: int xxprobe(), xxboot(), ieopen(), ieclose(), etherstrategy(), nullsys(); ! 119: ! 120: struct boottab iedriver = { ! 121: "ie", xxprobe, xxboot, ieopen, ieclose, ! 122: etherstrategy, "ie: Sun/Intel Ethernet", &ieinfo, ! 123: }; ! 124: ! 125: /* ! 126: * Open Intel Ethernet nd connection, return -1 for errors. ! 127: */ ! 128: ieopen(sip) ! 129: struct saioreq *sip; ! 130: { ! 131: register int result; ! 132: ! 133: sip->si_sif = &ieif; ! 134: if ( ieinit(sip) || (result = etheropen(sip)) < 0 ) { ! 135: ieclose(sip); /* Make sure we kill chip */ ! 136: return (-1); ! 137: } ! 138: return (result); ! 139: } ! 140: ! 141: /* ! 142: * Set up memory maps and Ethernet chip. ! 143: * Returns 1 for error, 0 for ok. ! 144: */ ! 145: int ! 146: ieinit(sip) ! 147: struct saioreq *sip; ! 148: { ! 149: register struct ie_softc *es; ! 150: int paddr; ! 151: int i; ! 152: struct idprom id; ! 153: ! 154: if (idprom(IDFORM_1, &id) == IDFORM_1 && ! 155: id.id_machine != IDM_SUN2_MULTI && ! 156: (sip->si_ctlr == 0 || sip->si_ctlr == iestd[0])) { ! 157: /* onboard Ethernet */ ! 158: register struct obie_device *obie; ! 159: ! 160: es = (struct ie_softc *)sip->si_dmaaddr; ! 161: bzero((char *)es, sizeof *es); ! 162: es->es_type = IE_OB; ! 163: es->es_obie = obie = (struct obie_device *) ! 164: devalloc(MAP_OBIO, VIOPG_ETHER << BYTES_PG_SHIFT, ! 165: sizeof(*obie)); ! 166: } else { ! 167: register struct mie_device *mie; ! 168: struct miepg *pg; ! 169: short *ap; ! 170: ! 171: mie = (struct mie_device *) sip->si_devaddr; ! 172: mie->mie_peack = 1; ! 173: mie->mie_noloop = 0; ! 174: mie->mie_ie = 0; ! 175: mie->mie_pie = 0; ! 176: paddr = mie->mie_mbmhi << 16; ! 177: ap = (short *)mie->mie_pgmap; ! 178: for (i=0; i<IEVVSIZ; i++) /* note: sets p2mem -> 0 */ ! 179: *ap++ = 0; ! 180: for (i=0; i<IEPHYMEMSIZ/IEPAGSIZ; i++) { ! 181: mie->mie_pgmap[0].mp_pfnum = i; ! 182: } ! 183: pg = &mie->mie_pgmap[0]; ! 184: for (i=0; i<IEVIRMEMSIZ/IEPAGSIZ; i++) { ! 185: pg->mp_swab = 1; ! 186: pg->mp_pfnum = i; ! 187: pg++; ! 188: } ! 189: /* last page for chip init */ ! 190: mie->mie_pgmap[IEVVSIZ-1].mp_pfnum = (PROTOSCRATCH/IEPAGSIZ)-1; ! 191: es = (struct ie_softc *) ! 192: devalloc(MAP_MBMEM, paddr, sizeof(struct ie_softc)); ! 193: bzero((char *)es, sizeof *es); ! 194: es->es_type = IE_MB; ! 195: es->es_mie = mie; ! 196: } ! 197: /* FIXME, release multibus resources ifdef. */ ! 198: sip->si_devdata = (caddr_t)es; ! 199: return iereset(es, sip); ! 200: } ! 201: ! 202: /* ! 203: * Basic 82586 initialization ! 204: * Returns 1 for error, 0 for ok. ! 205: */ ! 206: int ! 207: iereset(es, sip) ! 208: register struct ie_softc *es; ! 209: struct saioreq *sip; ! 210: { ! 211: struct ieiscp *iscp = &es->es_iscp; ! 212: struct iescb *scb = &es->es_scb; ! 213: struct ieiaddr *iad = &es->es_iaddr; ! 214: struct ieconf *ic = &es->es_ic; ! 215: int j; ! 216: int savepmap; ! 217: register struct mie_device *mie = es->es_mie; ! 218: register struct obie_device *obie = es->es_obie; ! 219: ! 220: for (j = 0; j < 10; j++) { ! 221: /* Set up the control blocks for initializing the chip */ ! 222: bzero((caddr_t)&es->es_scp, sizeof (struct iescp)); ! 223: es->es_scp.ie_iscp = to_ieaddr(es, (caddr_t)iscp); ! 224: bzero((caddr_t)iscp, sizeof (struct ieiscp)); ! 225: iscp->ie_busy = 1; ! 226: iscp->ie_scb = to_ieoff(es, (caddr_t)scb); ! 227: iscp->ie_cbbase = to_ieaddr(es, (caddr_t)es); ! 228: bzero((caddr_t)scb, sizeof (struct iescb)); ! 229: if (es->es_type == IE_OB) { ! 230: /* ! 231: * The 82586 has bugs that require us to be in ! 232: * loopback mode while we initialize it, to avoid ! 233: * transitions on CRS (carrier sense). ! 234: * ! 235: * However, the Intel serial interface chip used ! 236: * on Carrera also has bugs: if it powers-up in ! 237: * loopback, you have to release loopback at least ! 238: * once to make it behave -- it powers up with ! 239: * CRS and CDT permanently active, which rapes the 586. ! 240: * ! 241: * How do you spell "broken"? I-N-T-E-L... ! 242: */ ! 243: *obie = obie_reset; /* Reset chip & interface */ ! 244: DELAY(20); ! 245: obie->obie_noloop = 0; /* Put it in loopback now */ ! 246: DELAY(20); ! 247: obie->obie_noreset = 1; /* Release Reset on 82586 */ ! 248: DELAY(200); ! 249: /* ! 250: * Now set up to let the Ethernet chip read the SCP. ! 251: * Intel wired in the address of the SCP. It happens ! 252: * to be 0xFFFFF6. ! 253: */ ! 254: savepmap = getpgmap(SCP_LOC); ! 255: setpgmap(SCP_LOC, getpgmap((char *)&es->es_scp)); ! 256: } else { ! 257: mie->mie_reset = 1; ! 258: DELAY(20); ! 259: mie->mie_reset = 0; ! 260: DELAY(200); ! 261: } ! 262: ! 263: /* ! 264: * We are set up. Give the chip a zap, then wait up to ! 265: * 1 sec, or until chip comes ready. ! 266: */ ! 267: ieca(es); ! 268: CDELAY(iscp->ie_busy != 1, 1000); ! 269: ! 270: /* Whether or not it worked, we have to clean up. */ ! 271: if (es->es_type == IE_OB) { ! 272: /* If it didn't init, reset chip again. */ ! 273: if (iscp->ie_busy == 1) ! 274: obie->obie_noreset = 0; ! 275: setpgmap(SCP_LOC, savepmap); ! 276: } ! 277: if (iscp->ie_busy == 1) ! 278: continue; /* Continue loop until we get it */ ! 279: ! 280: /* ! 281: * Now try to run a few simple commands before we say "OK". ! 282: */ ! 283: bzero((caddr_t)iad, sizeof (struct ieiaddr)); ! 284: iad->ieia_cb.ie_cmd = IE_IADDR; ! 285: myetheraddr((struct ether_addr *)iad->ieia_addr); ! 286: if (iesimple(es, &iad->ieia_cb)) { ! 287: printf("ie: hang while setting Ethernet address.\n"); ! 288: continue; ! 289: } ! 290: ! 291: iedefaultconf(ic); ! 292: if (iesimple(es, &ic->ieconf_cb)) { ! 293: printf("ie: hang while setting chip config.\n"); ! 294: continue; ! 295: } ! 296: ! 297: /* ! 298: * Take the Ethernet interface chip out of loopback mode, i.e. ! 299: * put us on the wire. We can't do this before having ! 300: * initialized the Ethernet chip because the chip does random ! 301: * things if its 'wire' is active between the time it's reset ! 302: * and the first CA. Also, the IA-setup and configure commands ! 303: * will hang under some conditions unless the interface is ! 304: * very quiet and still. ! 305: */ ! 306: if (es->es_type == IE_OB) ! 307: obie->obie_noloop = 1; ! 308: if (es->es_type == IE_MB) ! 309: mie->mie_noloop = 1; ! 310: if (ierustart(es)) { ! 311: printf("ie: hang while starting receiver.\n"); ! 312: continue; ! 313: } ! 314: ! 315: return 0; /* It all worked! */ ! 316: } ! 317: ! 318: /* We tried a bunch of times, no luck. */ ! 319: printf("ie: cannot initialize\n"); ! 320: return 1; ! 321: } ! 322: ! 323: /* ! 324: * Initialize and start the Receive Unit ! 325: */ ! 326: int ! 327: ierustart(es) ! 328: register struct ie_softc *es; ! 329: { ! 330: register struct ierbd *rbd = &es->es_rbd; ! 331: struct ierbd *rbd2 = &es->es_rbd2; ! 332: register struct ierfd *rfd = &es->es_rfd; ! 333: register struct iescb *scb = &es->es_scb; ! 334: int timebomb = TIMEBOMB; ! 335: ! 336: /* ! 337: * Stop the RU, since we're sharing buffers with it. ! 338: * Then wait until it has really stopped. ! 339: */ ! 340: while (scb->ie_rus == IERUS_READY) { ! 341: while (scb->ie_cmd != 0) /* XXX */ ! 342: if (timebomb-- <= 0) return TIMEOUT; ! 343: scb->ie_cmd = IECMD_RU_ABORT; ! 344: ieca(es); ! 345: } ! 346: ! 347: while (scb->ie_cmd != 0) /* XXX */ ! 348: if (timebomb-- <= 0) return TIMEOUT; ! 349: ! 350: /* Real receive buffer descriptor */ ! 351: *(short *)rbd = 0; ! 352: rbd->ierbd_next = to_ieoff(es, (caddr_t)rbd2); /* Fake */ ! 353: rbd->ierbd_el = 0; /* Fake */ ! 354: rbd->ierbd_buf = to_ieaddr(es, es->es_rbuf); ! 355: rbd->ierbd_sizehi = IERBUFSIZ >> 8; ! 356: rbd->ierbd_sizelo = IERBUFSIZ & 0xFF; ! 357: ! 358: /* Fake receive buffer to avoid chip lockups in B0 mask */ ! 359: *(short *)rbd2 = 0; ! 360: rbd2->ierbd_next = -1; /* unnecessary since el = 1 */ ! 361: rbd2->ierbd_el = 1; ! 362: rbd2->ierbd_buf = to_ieaddr(es, es->es_rbuf2); ! 363: rbd2->ierbd_sizehi = 0; ! 364: rbd2->ierbd_sizelo = sizeof(es->es_rbuf2) & 0xFF; ! 365: ! 366: /* Real receive frame descriptor */ ! 367: *(short *)rfd = 0; ! 368: rfd->ierfd_next = -1; /* Unused since el = 1 */ ! 369: rfd->ierfd_el = 1; ! 370: rfd->ierfd_susp = 1; /* Suspend after receiving one */ ! 371: rfd->ierfd_rbd = to_ieoff(es, (caddr_t)rbd); ! 372: ! 373: /* ! 374: * Start the RU again. ! 375: */ ! 376: scb->ie_rfa = to_ieoff(es, (caddr_t)rfd); ! 377: scb->ie_cmd = IECMD_RU_START; ! 378: ieca(es); ! 379: return OK; ! 380: } ! 381: ! 382: ieca(es) ! 383: register struct ie_softc *es; ! 384: { ! 385: if (es->es_type == IE_OB) { ! 386: es->es_obie->obie_ca = 1; ! 387: es->es_obie->obie_ca = 0; ! 388: } else { ! 389: es->es_mie->mie_ca = 1; ! 390: es->es_mie->mie_ca = 0; ! 391: } ! 392: } ! 393: ! 394: int ! 395: iesimple(es, cb) ! 396: register struct ie_softc *es; ! 397: register struct iecb *cb; ! 398: { ! 399: register struct iescb *scb = &es->es_scb; ! 400: register timebomb = TIMEBOMB; ! 401: ! 402: *(short *)cb = 0; /* clear status bits */ ! 403: cb->ie_el = 1; ! 404: cb->ie_next = 0; ! 405: ! 406: /* start CU */ ! 407: while (scb->ie_cmd != 0) /* XXX */ ! 408: if (timebomb-- <= 0) return TIMEOUT; ! 409: scb->ie_cbl = to_ieoff(es, (caddr_t)cb); ! 410: scb->ie_cmd = IECMD_CU_START; ! 411: if (scb->ie_cx) ! 412: scb->ie_cmd |= IECMD_ACK_CX; ! 413: if (scb->ie_cnr) ! 414: scb->ie_cmd |= IECMD_ACK_CNR; ! 415: ieca(es); ! 416: while (!cb->ie_done) /* XXX */ ! 417: if (timebomb-- <= 0) return TIMEOUT; ! 418: while (scb->ie_cmd != 0) /* XXX */ ! 419: if (timebomb-- <= 0) return TIMEOUT; ! 420: if (scb->ie_cx) ! 421: scb->ie_cmd |= IECMD_ACK_CX; ! 422: if (scb->ie_cnr) ! 423: scb->ie_cmd |= IECMD_ACK_CNR; ! 424: ieca(es); ! 425: return OK; ! 426: } ! 427: ! 428: /* ! 429: * Transmit a packet. ! 430: * Always copy the packet for the sake of Multibus ! 431: * boards and Sun3's. This is not a performance critical situation ! 432: */ ! 433: iexmit(es, buf, count) ! 434: register struct ie_softc *es; ! 435: char *buf; ! 436: int count; ! 437: { ! 438: register struct ietbd *tbd = &es->es_tbd; ! 439: register struct ietfd *td = &es->es_tfd; ! 440: ! 441: bzero((caddr_t)tbd, sizeof *tbd); ! 442: tbd->ietbd_eof = 1; ! 443: tbd->ietbd_cntlo = count & 0xFF; ! 444: tbd->ietbd_cnthi = count >> 8; ! 445: bcopy(buf, es->es_xbuf, count); ! 446: tbd->ietbd_buf = to_ieaddr(es, es->es_xbuf); ! 447: td->ietfd_tbd = to_ieoff(es, (caddr_t)tbd); ! 448: td->ietfd_cmd = IE_TRANSMIT; ! 449: if (iesimple(es, (struct iecb *)td)) { ! 450: printf("ie: xmit hang\n"); ! 451: return -1; ! 452: } ! 453: #ifdef DEBUG ! 454: if (!td->ietfd_ok) { ! 455: /* Print status bits from transmit command */ ! 456: printf("ie xmit failed: %x\n", *(unsigned short *)td); ! 457: } ! 458: #endif DEBUG ! 459: if (td->ietfd_ok) ! 460: return (0); ! 461: if (td->ietfd_xcoll) ! 462: printf("ie: Ethernet cable problem\n"); ! 463: return (-1); ! 464: } ! 465: ! 466: ! 467: ! 468: int ! 469: iepoll(es, buf) ! 470: register struct ie_softc *es; ! 471: char *buf; ! 472: { ! 473: register struct ierbd *rbd = &es->es_rbd; ! 474: register struct ierfd *rfd = &es->es_rfd; ! 475: register struct iescb *scb = &es->es_scb; ! 476: int len; ! 477: int timebomb = TIMEBOMB; ! 478: ! 479: #ifdef DEBUG ! 480: /* Check for error status, and printf if so */ ! 481: /* ! 482: * Resource errors should be ignored, they happen even when we ! 483: * are not interested in listening. ! 484: */ ! 485: if (scb->ie_crcerrs || scb->ie_alnerrs || scb->ie_ovrnerrs) { ! 486: printf("ie recv %x CRC %d, ALN %d, OVRN %d\n", ! 487: scb->ie_rus, ! 488: from_ieint(scb->ie_crcerrs), ! 489: from_ieint(scb->ie_alnerrs), ! 490: from_ieint(scb->ie_ovrnerrs)); ! 491: scb->ie_crcerrs = 0; ! 492: scb->ie_alnerrs = 0; ! 493: scb->ie_ovrnerrs = 0; ! 494: } ! 495: #endif DEBUG ! 496: ! 497: /* ! 498: * Note, this assumes that the RU is set up to get out of READY ! 499: * state after receiving one packet. ! 500: */ ! 501: if (scb->ie_rus == IERUS_READY) { ! 502: return (0); /* No packet yet */ ! 503: } else { ! 504: /* RU not ready, see if because we got a packet. */ ! 505: if (!rfd->ierfd_done || !rbd->ierbd_eof) { ! 506: /* No, randomness zapped it. */ ! 507: #ifdef DEBUG ! 508: printf("ie recv restart from %x: scb %x frm %x buf %x\n" ! 509: , scb->ie_rus, ! 510: *(unsigned short *)scb, *(unsigned short *)rfd, ! 511: *(unsigned short *)rbd); ! 512: #endif DEBUG ! 513: ierustart(es); ! 514: return (0); ! 515: } ! 516: } ! 517: ! 518: /* ! 519: * We got a packet. ! 520: */ ! 521: len = (rbd->ierbd_cnthi << 8) + rbd->ierbd_cntlo; ! 522: bcopy(es->es_rbuf, buf, len); ! 523: while (scb->ie_cmd != 0) /* XXX */ ! 524: if (timebomb-- <= 0) return TIMEOUT; ! 525: if (scb->ie_fr) ! 526: scb->ie_cmd |= IECMD_ACK_FR; ! 527: if (scb->ie_rnr) ! 528: scb->ie_cmd |= IECMD_ACK_RNR; ! 529: ieca(es); ! 530: ierustart(es); ! 531: return (len); ! 532: } ! 533: ! 534: /* ! 535: * Convert a CPU virtual address into an Ethernet virtual address. ! 536: * ! 537: * For Multibus, we assume it's in the Ethernet's memory space, and we ! 538: * just subtract off the start of the memory space (==es). For Model 50, ! 539: * the Ethernet chip has full access to supervisor virtual memory. ! 540: * For Carrera, the chip can access the top 16MB of virtual memory, ! 541: * but we never give it addresses outside that range, so the high ! 542: * order bits can be ignored. ! 543: */ ! 544: ieaddr_t ! 545: to_ieaddr(es, cp) ! 546: struct ie_softc *es; ! 547: caddr_t cp; ! 548: { ! 549: union { ! 550: int n; ! 551: char c[4]; ! 552: } a, b; ! 553: ! 554: #ifdef SUN3 ! 555: #ifdef DEBUG ! 556: if (cp < (char *)0x0F000000 || cp >= (char *)0x10000000) { ! 557: /* printf("Bad ptr to_ieaddr(%x)\n", cp); */ ! 558: ; asm(" .word 0xFFFF") ; ; ! 559: } ! 560: #endif DEBUG ! 561: #endif SUN3 ! 562: if (es->es_type == IE_MB) ! 563: a.n = cp - (caddr_t)es; ! 564: else /* if (es->es_type == IE_OB) */ ! 565: a.n = (int)cp; ! 566: b.c[0] = a.c[3]; ! 567: b.c[1] = a.c[2]; ! 568: b.c[2] = a.c[1]; ! 569: b.c[3] = 0; ! 570: return (b.n); ! 571: } ! 572: ! 573: /* ! 574: * Convert a CPU virtual address into a 16-bit offset for the Ethernet ! 575: * chip. ! 576: * ! 577: * This is the same for Onboard and Multibus, since the offset is based ! 578: * on the absolute address supplied in the initial system configuration ! 579: * block -- which we customize for Multibus or Onboard. ! 580: */ ! 581: ieoff_t ! 582: to_ieoff(es, addr) ! 583: register struct ie_softc *es; ! 584: caddr_t addr; ! 585: { ! 586: union { ! 587: short s; ! 588: char c[2]; ! 589: } a, b; ! 590: ! 591: a.s = (short)(addr - (caddr_t)es); ! 592: b.c[0] = a.c[1]; ! 593: b.c[1] = a.c[0]; ! 594: return (b.s); ! 595: } ! 596: ! 597: ! 598: #ifdef DEBUG ! 599: ieint_t ! 600: from_ieint(n) ! 601: short n; ! 602: { ! 603: union { ! 604: short s; ! 605: char c[2]; ! 606: } a, b; ! 607: ! 608: a.s = n; ! 609: b.c[0] = a.c[1]; ! 610: b.c[1] = a.c[0]; ! 611: return (b.s); ! 612: } ! 613: #endif DEBUG ! 614: ! 615: /* ! 616: * Set default configuration parameters ! 617: * As spec'd by Intel, except acloc == 1 for header in data ! 618: */ ! 619: iedefaultconf(ic) ! 620: register struct ieconf *ic; ! 621: { ! 622: bzero((caddr_t)ic, sizeof (struct ieconf)); ! 623: ic->ieconf_cb.ie_cmd = IE_CONFIG; ! 624: ic->ieconf_bytes = 12; ! 625: ic->ieconf_fifolim = 8; ! 626: ic->ieconf_pream = 2; /* 8 byte preamble */ ! 627: ic->ieconf_alen = 6; ! 628: ic->ieconf_acloc = 1; ! 629: ic->ieconf_space = 96; ! 630: ic->ieconf_slttmh = 512 >> 8; ! 631: ic->ieconf_minfrm = 64; ! 632: ic->ieconf_retry = 15; ! 633: } ! 634: ! 635: /* ! 636: * Close down intel ethernet device. ! 637: * On the Model 50, we reset the chip and take it off the wire, since ! 638: * it is sharing main memory with us (occasionally reading and writing), ! 639: * and most programs don't know how to deal with that -- they just assume ! 640: * that main memory is theirs to play with. ! 641: */ ! 642: ieclose(sip) ! 643: struct saioreq *sip; ! 644: { ! 645: register struct ie_softc *es = (struct ie_softc *) sip->si_devdata; ! 646: ! 647: if (es->es_type == IE_OB) ! 648: *es->es_obie = obie_reset; ! 649: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.