1 /* $NetBSD: if_ec.c,v 1.32 2008/03/12 14:31:11 cube Exp $ */ 2 3 /*- 4 * Copyright (c) 1997, 1998 The NetBSD Foundation, Inc. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to The NetBSD Foundation 8 * by Jason R. Thorpe of the Numerical Aerospace Simulation Facility, 9 * NASA Ames Research Center. 10 * 11 * Redistribution and use in source and binary forms, with or without 12 * modification, are permitted provided that the following conditions 13 * are met: 14 * 1. Redistributions of source code must retain the above copyright 15 * notice, this list of conditions and the following disclaimer. 16 * 2. Redistributions in binary form must reproduce the above copyright 17 * notice, this list of conditions and the following disclaimer in the 18 * documentation and/or other materials provided with the distribution. 19 * 3. All advertising materials mentioning features or use of this software 20 * must display the following acknowledgement: 21 * This product includes software developed by the NetBSD 22 * Foundation, Inc. and its contributors. 23 * 4. Neither the name of The NetBSD Foundation nor the names of its 24 * contributors may be used to endorse or promote products derived 25 * from this software without specific prior written permission. 26 * 27 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 28 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 29 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 30 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 31 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 32 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 33 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 34 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 35 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 36 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 37 * POSSIBILITY OF SUCH DAMAGE. 38 */ 39 40 /* 41 * Device driver for National Semiconductor DS8390/WD83C690 based ethernet 42 * adapters. 43 * 44 * Copyright (c) 1994, 1995 Charles M. Hannum. All rights reserved. 45 * 46 * Copyright (C) 1993, David Greenman. This software may be used, modified, 47 * copied, distributed, and sold, in both source and binary form provided that 48 * the above copyright and these terms are retained. Under no circumstances is 49 * the author responsible for the proper functioning of this software, nor does 50 * the author assume any responsibility for damages incurred with its use. 51 */ 52 53 /* 54 * Device driver for the 3Com Etherlink II (3c503). 55 */ 56 57 #include <sys/cdefs.h> 58 __KERNEL_RCSID(0, "$NetBSD: if_ec.c,v 1.32 2008/03/12 14:31:11 cube Exp $"); 59 60 #include <sys/param.h> 61 #include <sys/systm.h> 62 #include <sys/device.h> 63 #include <sys/socket.h> 64 #include <sys/mbuf.h> 65 #include <sys/syslog.h> 66 67 #include <net/if.h> 68 #include <net/if_dl.h> 69 #include <net/if_types.h> 70 #include <net/if_media.h> 71 72 #include <net/if_ether.h> 73 74 #include <sys/bus.h> 75 #include <sys/intr.h> 76 77 #include <dev/isa/isareg.h> 78 #include <dev/isa/isavar.h> 79 80 #include <dev/ic/dp8390reg.h> 81 #include <dev/ic/dp8390var.h> 82 83 #include <dev/isa/if_ecreg.h> 84 85 struct ec_softc { 86 struct dp8390_softc sc_dp8390; 87 88 bus_space_tag_t sc_asict; /* space tag for ASIC */ 89 bus_space_handle_t sc_asich; /* space handle for ASIC */ 90 91 int sc_16bitp; /* are we 16 bit? */ 92 93 void *sc_ih; /* interrupt handle */ 94 }; 95 96 int ec_probe(device_t, cfdata_t, void *); 97 void ec_attach(device_t, device_t, void *); 98 99 CFATTACH_DECL_NEW(ec, sizeof(struct ec_softc), 100 ec_probe, ec_attach, NULL, NULL); 101 102 int ec_set_media(struct ec_softc *, int); 103 104 void ec_media_init(struct dp8390_softc *); 105 106 int ec_mediachange(struct dp8390_softc *); 107 void ec_mediastatus(struct dp8390_softc *, struct ifmediareq *); 108 109 void ec_init_card(struct dp8390_softc *); 110 int ec_write_mbuf(struct dp8390_softc *, struct mbuf *, int); 111 int ec_ring_copy(struct dp8390_softc *, int, void *, u_short); 112 void ec_read_hdr(struct dp8390_softc *, int, struct dp8390_ring *); 113 int ec_fake_test_mem(struct dp8390_softc *); 114 int ec_test_mem(struct dp8390_softc *); 115 116 inline void ec_readmem(struct ec_softc *, int, u_int8_t *, int); 117 118 static const int ec_iobase[] = { 119 0x2e0, 0x2a0, 0x280, 0x250, 0x350, 0x330, 0x310, 0x300, 120 }; 121 #define NEC_IOBASE (sizeof(ec_iobase) / sizeof(ec_iobase[0])) 122 123 static const int ec_membase[] = { 124 -1, -1, -1, -1, 125 0xc8000, 0xcc000, 0xd8000, 0xdc000, 126 }; 127 #define NEC_MEMBASE (sizeof(ec_membase) / sizeof(ec_membase[0])) 128 129 int 130 ec_probe(device_t parent, cfdata_t match, void *aux) 131 { 132 struct isa_attach_args *ia = aux; 133 bus_space_tag_t nict, asict, memt; 134 bus_space_handle_t nich, asich, memh; 135 bus_size_t memsize; 136 int nich_valid, asich_valid, memh_valid; 137 int i, rv = 0; 138 u_int8_t x; 139 140 nict = asict = ia->ia_iot; 141 memt = ia->ia_memt; 142 143 nich_valid = asich_valid = memh_valid = 0; 144 145 /* 146 * Hmm, a 16-bit card has 16k of memory, but only an 8k window 147 * to it. 148 */ 149 memsize = 8192; 150 151 if (ia->ia_nio < 1) 152 return (0); 153 if (ia->ia_niomem < 1) 154 return (0); 155 if (ia->ia_nirq < 1) 156 return (0); 157 158 if (ISA_DIRECT_CONFIG(ia)) 159 return (0); 160 161 /* Disallow wildcarded i/o addresses. */ 162 if (ia->ia_io[0].ir_addr == ISA_UNKNOWN_PORT) 163 return (0); 164 165 /* Disallow wildcarded mem address. */ 166 if (ia->ia_iomem[0].ir_addr == ISA_UNKNOWN_IOMEM) 167 return (0); 168 169 /* Validate the i/o base. */ 170 for (i = 0; i < NEC_IOBASE; i++) 171 if (ia->ia_io[0].ir_addr == ec_iobase[i]) 172 break; 173 if (i == NEC_IOBASE) 174 return (0); 175 176 /* Validate the mem base. */ 177 for (i = 0; i < NEC_MEMBASE; i++) { 178 if (ec_membase[i] == -1) 179 continue; 180 if (ia->ia_iomem[0].ir_addr == ec_membase[i]) 181 break; 182 } 183 if (i == NEC_MEMBASE) 184 return (0); 185 186 /* Attempt to map the NIC space. */ 187 if (bus_space_map(nict, ia->ia_io[0].ir_addr + ELINK2_NIC_OFFSET, 188 ELINK2_NIC_PORTS, 0, &nich)) 189 goto out; 190 nich_valid = 1; 191 192 /* Attempt to map the ASIC space. */ 193 if (bus_space_map(asict, ia->ia_io[0].ir_addr + ELINK2_ASIC_OFFSET, 194 ELINK2_ASIC_PORTS, 0, &asich)) 195 goto out; 196 asich_valid = 1; 197 198 /* Attempt to map the memory space. */ 199 if (bus_space_map(memt, ia->ia_iomem[0].ir_addr, memsize, 0, &memh)) 200 goto out; 201 memh_valid = 1; 202 203 /* 204 * Verify that the kernel configured I/O address matches the 205 * board configured I/O address. 206 * 207 * This is really only useful to see if something that looks like 208 * the board is there; after all, we're already talking to it at 209 * this point. 210 */ 211 x = bus_space_read_1(asict, asich, ELINK2_BCFR); 212 if (x == 0 || (x & (x - 1)) != 0) 213 goto out; 214 i = ffs(x) - 1; 215 if (ia->ia_io[0].ir_addr != ec_iobase[i]) 216 goto out; 217 218 /* 219 * ...and for the memory address. Note we do not support 220 * cards configured with shared memory disabled. 221 */ 222 x = bus_space_read_1(asict, asich, ELINK2_PCFR); 223 if (x == 0 || (x & (x - 1)) != 0) 224 goto out; 225 i = ffs(x) - 1; 226 if (ia->ia_iomem[0].ir_addr != ec_membase[i]) 227 goto out; 228 229 /* So, we say we've found it! */ 230 ia->ia_nio = 1; /* XXX Really 2! */ 231 ia->ia_io[0].ir_size = ELINK2_NIC_PORTS; 232 233 ia->ia_niomem = 1; 234 ia->ia_iomem[0].ir_size = memsize; 235 236 ia->ia_nirq = 1; 237 238 ia->ia_ndrq = 0; 239 240 rv = 1; 241 242 out: 243 if (nich_valid) 244 bus_space_unmap(nict, nich, ELINK2_NIC_PORTS); 245 if (asich_valid) 246 bus_space_unmap(asict, asich, ELINK2_ASIC_PORTS); 247 if (memh_valid) 248 bus_space_unmap(memt, memh, memsize); 249 return (rv); 250 } 251 252 void 253 ec_attach(device_t parent, device_t self, void *aux) 254 { 255 struct ec_softc *esc = device_private(self); 256 struct dp8390_softc *sc = &esc->sc_dp8390; 257 struct isa_attach_args *ia = aux; 258 bus_space_tag_t nict, asict, memt; 259 bus_space_handle_t nich, asich, memh; 260 bus_size_t memsize; 261 u_int8_t tmp; 262 int i; 263 264 sc->sc_dev = self; 265 aprint_normal("\n"); 266 267 nict = asict = ia->ia_iot; 268 memt = ia->ia_memt; 269 270 /* 271 * Hmm, a 16-bit card has 16k of memory, but only an 8k window 272 * to it. 273 */ 274 memsize = ia->ia_iomem[0].ir_size; 275 276 /* Map the NIC space. */ 277 if (bus_space_map(nict, ia->ia_io[0].ir_addr + ELINK2_NIC_OFFSET, 278 ELINK2_NIC_PORTS, 0, &nich)) { 279 aprint_error_dev(self, "can't map nic i/o space\n"); 280 return; 281 } 282 283 /* Map the ASIC space. */ 284 if (bus_space_map(asict, ia->ia_io[0].ir_addr + ELINK2_ASIC_OFFSET, 285 ELINK2_ASIC_PORTS, 0, &asich)) { 286 aprint_error_dev(self, "can't map asic i/o space\n"); 287 return; 288 } 289 290 /* Map the memory space. */ 291 if (bus_space_map(memt, ia->ia_iomem[0].ir_addr, memsize, 0, &memh)) { 292 aprint_error_dev(self, "can't map shared memory\n"); 293 return; 294 } 295 296 esc->sc_asict = asict; 297 esc->sc_asich = asich; 298 299 sc->sc_regt = nict; 300 sc->sc_regh = nich; 301 302 sc->sc_buft = memt; 303 sc->sc_bufh = memh; 304 305 /* Interface is always enabled. */ 306 sc->sc_enabled = 1; 307 308 /* Registers are linear. */ 309 for (i = 0; i < 16; i++) 310 sc->sc_reg_map[i] = i; 311 312 /* Now we can use the NIC_{GET,PUT}() macros. */ 313 314 /* 315 * Reset NIC and ASIC. Enable on-board transeiver throughout 316 * reset sequence since it will lock up if the cable isn't 317 * connected if we don't. 318 */ 319 bus_space_write_1(asict, asich, ELINK2_CR, 320 ELINK2_CR_RST | ELINK2_CR_XSEL); 321 322 /* Wait for a while, then un-reset it. */ 323 delay(50); 324 325 /* 326 * The 3Com ASIC defaults to rather strange settings for the CR 327 * after a reset. It's important to set it again after the 328 * following write (this is done when we map the PROM below). 329 */ 330 bus_space_write_1(asict, asich, ELINK2_CR, ELINK2_CR_XSEL); 331 332 /* Wait a bit for the NIC to recover from the reset. */ 333 delay(5000); 334 335 /* 336 * Get the station address from on-board ROM. 337 * 338 * First, map Ethernet address PROM over the top of where the NIC 339 * registers normally appear. 340 */ 341 bus_space_write_1(asict, asich, ELINK2_CR, 342 ELINK2_CR_XSEL | ELINK2_CR_EALO); 343 344 for (i = 0; i < ETHER_ADDR_LEN; i++) 345 sc->sc_enaddr[i] = NIC_GET(nict, nich, i); 346 347 /* 348 * Unmap PROM - select NIC registers. The proper setting of the 349 * transceiver is set in later in ec_init_card() via dp8390_init(). 350 */ 351 bus_space_write_1(asict, asich, ELINK2_CR, ELINK2_CR_XSEL); 352 353 /* Determine if this is an 8-bit or 16-bit board. */ 354 355 /* Select page 0 registers. */ 356 NIC_PUT(nict, nich, ED_P0_CR, ED_CR_RD2 | ED_CR_PAGE_0 | ED_CR_STP); 357 358 /* 359 * Attempt to clear WTS. If it doesn't clear, then this is a 360 * 16-bit board. 361 */ 362 NIC_PUT(nict, nich, ED_P0_DCR, 0); 363 364 /* Select page 2 registers. */ 365 NIC_PUT(nict, nich, ED_P0_CR, ED_CR_RD2 | ED_CR_PAGE_2 | ED_CR_STP); 366 367 /* The 3c503 forces the WTS bit to a one if this is a 16-bit board. */ 368 if (NIC_GET(nict, nich, ED_P2_DCR) & ED_DCR_WTS) 369 esc->sc_16bitp = 1; 370 else 371 esc->sc_16bitp = 0; 372 373 aprint_normal_dev(self, "3Com 3c503 Ethernet (%s-bit)\n", 374 esc->sc_16bitp ? "16" : "8"); 375 376 /* Select page 0 registers. */ 377 NIC_PUT(nict, nich, ED_P2_CR, ED_CR_RD2 | ED_CR_PAGE_0 | ED_CR_STP); 378 379 sc->cr_proto = ED_CR_RD2; 380 381 /* 382 * DCR gets: 383 * 384 * FIFO threshold to 8, No auto-init Remote DMA, 385 * byte order=80x86. 386 * 387 * 16-bit cards also get word-wide DMA transfers. 388 */ 389 sc->dcr_reg = ED_DCR_FT1 | ED_DCR_LS | 390 (esc->sc_16bitp ? ED_DCR_WTS : 0); 391 392 sc->test_mem = ec_fake_test_mem; 393 sc->ring_copy = ec_ring_copy; 394 sc->write_mbuf = ec_write_mbuf; 395 sc->read_hdr = ec_read_hdr; 396 sc->init_card = ec_init_card; 397 398 sc->sc_media_init = ec_media_init; 399 400 sc->sc_mediachange = ec_mediachange; 401 sc->sc_mediastatus = ec_mediastatus; 402 403 sc->mem_start = 0; 404 sc->mem_size = memsize; 405 406 /* Do generic parts of attach. */ 407 if (dp8390_config(sc)) { 408 aprint_error_dev(self, " configuration failed\n"); 409 return; 410 } 411 412 /* 413 * We need to override the way dp8390_config() set up our 414 * shared memory. 415 * 416 * We have an entire 8k window to put the transmit buffers on the 417 * 16-bit boards. But since the 16bit 3c503's shared memory is only 418 * fast enough to overlap the loading of one full-size packet, trying 419 * to load more than 2 buffers can actually leave the transmitter idle 420 * during the load. So 2 seems the best value. (Although a mix of 421 * variable-sized packets might change this assumption. Nonetheless, 422 * we optimize for linear transfers of same-size packets.) 423 */ 424 if (esc->sc_16bitp) { 425 if (device_cfdata(sc->sc_dev)->cf_flags & 426 DP8390_NO_MULTI_BUFFERING) 427 sc->txb_cnt = 1; 428 else 429 sc->txb_cnt = 2; 430 431 sc->tx_page_start = ELINK2_TX_PAGE_OFFSET_16BIT; 432 sc->rec_page_start = ELINK2_RX_PAGE_OFFSET_16BIT; 433 sc->rec_page_stop = (memsize >> ED_PAGE_SHIFT) + 434 sc->rec_page_start; 435 sc->mem_ring = sc->mem_start; 436 } else { 437 sc->txb_cnt = 1; 438 sc->tx_page_start = ELINK2_TX_PAGE_OFFSET_8BIT; 439 sc->rec_page_start = sc->tx_page_start + ED_TXBUF_SIZE; 440 sc->rec_page_stop = (memsize >> ED_PAGE_SHIFT) + 441 sc->tx_page_start; 442 sc->mem_ring = sc->mem_start + 443 (ED_TXBUF_SIZE << ED_PAGE_SHIFT); 444 } 445 446 /* 447 * Initialize CA page start/stop registers. Probably only needed 448 * if doing DMA, but what the Hell. 449 */ 450 bus_space_write_1(asict, asich, ELINK2_PSTR, sc->rec_page_start); 451 bus_space_write_1(asict, asich, ELINK2_PSPR, sc->rec_page_stop); 452 453 /* 454 * Program the IRQ. 455 */ 456 switch (ia->ia_irq[0].ir_irq) { 457 case 9: tmp = ELINK2_IDCFR_IRQ2; break; 458 case 3: tmp = ELINK2_IDCFR_IRQ3; break; 459 case 4: tmp = ELINK2_IDCFR_IRQ4; break; 460 case 5: tmp = ELINK2_IDCFR_IRQ5; break; 461 break; 462 463 case ISA_UNKNOWN_IRQ: 464 aprint_error_dev(self, "wildcarded IRQ is not allowed\n"); 465 return; 466 467 default: 468 aprint_error_dev(self, "invalid IRQ %d, must be 3, 4, 5, " 469 "or 9\n", ia->ia_irq[0].ir_irq); 470 return; 471 } 472 473 bus_space_write_1(asict, asich, ELINK2_IDCFR, tmp); 474 475 /* 476 * Initialize the GA configuration register. Set bank and enable 477 * shared memory. 478 */ 479 bus_space_write_1(asict, asich, ELINK2_GACFR, 480 ELINK2_GACFR_RSEL | ELINK2_GACFR_MBS0); 481 482 /* 483 * Intialize "Vector Pointer" registers. These gawd-awful things 484 * are compared to 20 bits of the address on the ISA, and if they 485 * match, the shared memory is disabled. We set them to 0xffff0... 486 * allegedly the reset vector. 487 */ 488 bus_space_write_1(asict, asich, ELINK2_VPTR2, 0xff); 489 bus_space_write_1(asict, asich, ELINK2_VPTR1, 0xff); 490 bus_space_write_1(asict, asich, ELINK2_VPTR0, 0x00); 491 492 /* 493 * Now run the real memory test. 494 */ 495 if (ec_test_mem(sc)) { 496 aprint_error_dev(self, "memory test failed\n"); 497 return; 498 } 499 500 /* Establish interrupt handler. */ 501 esc->sc_ih = isa_intr_establish(ia->ia_ic, ia->ia_irq[0].ir_irq, 502 IST_EDGE, IPL_NET, dp8390_intr, sc); 503 if (esc->sc_ih == NULL) 504 aprint_error_dev(self, "can't establish interrupt\n"); 505 } 506 507 int 508 ec_fake_test_mem(struct dp8390_softc *sc) 509 { 510 511 /* 512 * We have to do this after we initialize the GA, but we 513 * have to do that after calling dp8390_config(), which 514 * wants to test memory. Put this noop here, and then 515 * actually test memory later. 516 */ 517 return (0); 518 } 519 520 int 521 ec_test_mem(struct dp8390_softc *sc) 522 { 523 struct ec_softc *esc = (struct ec_softc *)sc; 524 bus_space_tag_t memt = sc->sc_buft; 525 bus_space_handle_t memh = sc->sc_bufh; 526 bus_size_t memsize = sc->mem_size; 527 int i; 528 529 if (esc->sc_16bitp) 530 bus_space_set_region_2(memt, memh, 0, 0, memsize >> 1); 531 else 532 bus_space_set_region_1(memt, memh, 0, 0, memsize); 533 534 if (esc->sc_16bitp) { 535 for (i = 0; i < memsize; i += 2) { 536 if (bus_space_read_2(memt, memh, i) != 0) 537 goto fail; 538 } 539 } else { 540 for (i = 0; i < memsize; i++) { 541 if (bus_space_read_1(memt, memh, i) != 0) 542 goto fail; 543 } 544 } 545 546 return (0); 547 548 fail: 549 aprint_error_dev(sc->sc_dev, 550 "failed to clear shared memory at offset 0x%x\n", i); 551 return (1); 552 } 553 554 /* 555 * Given a NIC memory source address and a host memory destination address, 556 * copy 'len' from NIC to host using shared memory. The 'len' is rounded 557 * up to a word - ok as long as mbufs are word-sized. 558 */ 559 inline void 560 ec_readmem(struct ec_softc *esc, int from, uint8_t *to, int len) 561 { 562 bus_space_tag_t memt = esc->sc_dp8390.sc_buft; 563 bus_space_handle_t memh = esc->sc_dp8390.sc_bufh; 564 565 if (len & 1) 566 ++len; 567 568 if (esc->sc_16bitp) 569 bus_space_read_region_2(memt, memh, from, (u_int16_t *)to, 570 len >> 1); 571 else 572 bus_space_read_region_1(memt, memh, from, to, len); 573 } 574 575 int 576 ec_write_mbuf(struct dp8390_softc *sc, struct mbuf *m, int buf) 577 { 578 struct ec_softc *esc = (struct ec_softc *)sc; 579 bus_space_tag_t asict = esc->sc_asict; 580 bus_space_handle_t asich = esc->sc_asich; 581 bus_space_tag_t memt = esc->sc_dp8390.sc_buft; 582 bus_space_handle_t memh = esc->sc_dp8390.sc_bufh; 583 u_int8_t *data, savebyte[2]; 584 int savelen, len, leftover; 585 #ifdef DIAGNOSTIC 586 u_int8_t *lim; 587 #endif 588 589 savelen = m->m_pkthdr.len; 590 591 /* 592 * 8-bit boards are simple: we're already in the correct 593 * page, and no alignment tricks are necessary. 594 */ 595 if (esc->sc_16bitp == 0) { 596 for (; m != NULL; buf += m->m_len, m = m->m_next) 597 bus_space_write_region_1(memt, memh, buf, 598 mtod(m, u_int8_t *), m->m_len); 599 if (savelen < ETHER_MIN_LEN - ETHER_CRC_LEN) { 600 bus_space_set_region_1(memt, memh, buf, 601 0, ETHER_MIN_LEN - ETHER_CRC_LEN - savelen); 602 savelen = ETHER_MIN_LEN - ETHER_CRC_LEN; 603 } 604 return (savelen); 605 } 606 607 /* 608 * If it's a 16-bit board, we have transmit buffers 609 * in a different page; switch to it. 610 */ 611 if (esc->sc_16bitp) 612 bus_space_write_1(asict, asich, ELINK2_GACFR, 613 ELINK2_GACFR_RSEL); 614 615 /* Start out with no leftover data. */ 616 leftover = 0; 617 savebyte[0] = savebyte[1] = 0; 618 619 for (; m != NULL; m = m->m_next) { 620 len = m->m_len; 621 if (len == 0) 622 continue; 623 data = mtod(m, u_int8_t *); 624 #ifdef DIAGNOSTIC 625 lim = data + len; 626 #endif 627 while (len > 0) { 628 if (leftover) { 629 /* 630 * Data left over (from mbuf or realignment). 631 * Buffer the next byte, and write it and 632 * the leftover data out. 633 */ 634 savebyte[1] = *data++; 635 len--; 636 bus_space_write_2(memt, memh, buf, 637 *(u_int16_t *)savebyte); 638 buf += 2; 639 leftover = 0; 640 } else if (BUS_SPACE_ALIGNED_POINTER(data, u_int16_t) 641 == 0) { 642 /* 643 * Unaligned data; buffer the next byte. 644 */ 645 savebyte[0] = *data++; 646 len--; 647 leftover = 1; 648 } else { 649 /* 650 * Aligned data; output contiguous words as 651 * much as we can, then buffer the remaining 652 * byte, if any. 653 */ 654 leftover = len & 1; 655 len &= ~1; 656 bus_space_write_region_2(memt, memh, buf, 657 (u_int16_t *)data, len >> 1); 658 data += len; 659 buf += len; 660 if (leftover) 661 savebyte[0] = *data++; 662 len = 0; 663 } 664 } 665 if (len < 0) 666 panic("ec_write_mbuf: negative len"); 667 #ifdef DIAGNOSTIC 668 if (data != lim) 669 panic("ec_write_mbuf: data != lim"); 670 #endif 671 } 672 if (leftover) { 673 savebyte[1] = 0; 674 bus_space_write_2(memt, memh, buf, *(u_int16_t *)savebyte); 675 buf += 2; 676 } 677 if (savelen < ETHER_MIN_LEN - ETHER_CRC_LEN) { 678 bus_space_set_region_2(memt, memh, buf, 679 0, (ETHER_MIN_LEN - ETHER_CRC_LEN - savelen) >> 1); 680 savelen = ETHER_MIN_LEN - ETHER_CRC_LEN; 681 } 682 683 /* 684 * Switch back to receive page. 685 */ 686 if (esc->sc_16bitp) 687 bus_space_write_1(asict, asich, ELINK2_GACFR, 688 ELINK2_GACFR_RSEL | ELINK2_GACFR_MBS0); 689 690 return (savelen); 691 } 692 693 int 694 ec_ring_copy(struct dp8390_softc *sc, int src, void *dst, u_short amount) 695 { 696 struct ec_softc *esc = (struct ec_softc *)sc; 697 u_short tmp_amount; 698 699 /* Does copy wrap to lower addr in ring buffer? */ 700 if (src + amount > sc->mem_end) { 701 tmp_amount = sc->mem_end - src; 702 703 /* Copy amount up to end of NIC memory. */ 704 ec_readmem(esc, src, dst, tmp_amount); 705 706 amount -= tmp_amount; 707 src = sc->mem_ring; 708 dst = (char *)dst + tmp_amount; 709 } 710 711 ec_readmem(esc, src, dst, amount); 712 713 return (src + amount); 714 } 715 716 void 717 ec_read_hdr(struct dp8390_softc *sc, int packet_ptr, 718 struct dp8390_ring *packet_hdrp) 719 { 720 struct ec_softc *esc = (struct ec_softc *)sc; 721 722 ec_readmem(esc, packet_ptr, (u_int8_t *)packet_hdrp, 723 sizeof(struct dp8390_ring)); 724 #if BYTE_ORDER == BIG_ENDIAN 725 packet_hdrp->count = bswap16(packet_hdrp->count); 726 #endif 727 } 728 729 void 730 ec_media_init(struct dp8390_softc *sc) 731 { 732 733 ifmedia_init(&sc->sc_media, 0, dp8390_mediachange, dp8390_mediastatus); 734 ifmedia_add(&sc->sc_media, IFM_ETHER|IFM_10_2, 0, NULL); 735 ifmedia_add(&sc->sc_media, IFM_ETHER|IFM_10_5, 0, NULL); 736 ifmedia_set(&sc->sc_media, IFM_ETHER|IFM_10_2); 737 } 738 739 int 740 ec_mediachange(struct dp8390_softc *sc) 741 { 742 struct ec_softc *esc = (struct ec_softc *)sc; 743 struct ifmedia *ifm = &sc->sc_media; 744 745 return (ec_set_media(esc, ifm->ifm_media)); 746 } 747 748 void 749 ec_mediastatus(struct dp8390_softc *sc, struct ifmediareq *ifmr) 750 { 751 struct ifmedia *ifm = &sc->sc_media; 752 753 /* 754 * The currently selected media is always the active media. 755 */ 756 ifmr->ifm_active = ifm->ifm_cur->ifm_media; 757 } 758 759 void 760 ec_init_card(struct dp8390_softc *sc) 761 { 762 struct ec_softc *esc = (struct ec_softc *)sc; 763 struct ifmedia *ifm = &sc->sc_media; 764 765 (void) ec_set_media(esc, ifm->ifm_cur->ifm_media); 766 } 767 768 int 769 ec_set_media(struct ec_softc *esc, int media) 770 { 771 u_int8_t new; 772 773 if (IFM_TYPE(media) != IFM_ETHER) 774 return (EINVAL); 775 776 switch (IFM_SUBTYPE(media)) { 777 case IFM_10_2: 778 new = ELINK2_CR_XSEL; 779 break; 780 781 case IFM_10_5: 782 new = 0; 783 break; 784 785 default: 786 return (EINVAL); 787 } 788 789 bus_space_write_1(esc->sc_asict, esc->sc_asich, ELINK2_CR, new); 790 return (0); 791 } 792