esp.c revision 1.27
1/* $NetBSD: esp.c,v 1.27 2000/12/29 21:31:44 briggs Exp $ */ 2 3/* 4 * Copyright (c) 1997 Jason R. Thorpe. 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 3. All advertising materials mentioning features or use of this software 16 * must display the following acknowledgement: 17 * This product includes software developed for the NetBSD Project 18 * by Jason R. Thorpe. 19 * 4. The name of the author may not be used to endorse or promote products 20 * derived from this software without specific prior written permission. 21 * 22 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 23 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 24 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 25 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 26 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 27 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 28 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 29 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 30 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 31 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 32 */ 33 34/* 35 * Copyright (c) 1994 Peter Galbavy 36 * All rights reserved. 37 * 38 * Redistribution and use in source and binary forms, with or without 39 * modification, are permitted provided that the following conditions 40 * are met: 41 * 1. Redistributions of source code must retain the above copyright 42 * notice, this list of conditions and the following disclaimer. 43 * 2. Redistributions in binary form must reproduce the above copyright 44 * notice, this list of conditions and the following disclaimer in the 45 * documentation and/or other materials provided with the distribution. 46 * 3. All advertising materials mentioning features or use of this software 47 * must display the following acknowledgement: 48 * This product includes software developed by Peter Galbavy 49 * 4. The name of the author may not be used to endorse or promote products 50 * derived from this software without specific prior written permission. 51 * 52 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 53 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 54 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 55 * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, 56 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 57 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 58 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 59 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, 60 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN 61 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 62 * POSSIBILITY OF SUCH DAMAGE. 63 */ 64 65/* 66 * Based on aic6360 by Jarle Greipsland 67 * 68 * Acknowledgements: Many of the algorithms used in this driver are 69 * inspired by the work of Julian Elischer (julian@tfs.com) and 70 * Charles Hannum (mycroft@duality.gnu.ai.mit.edu). Thanks a million! 71 */ 72 73/* 74 * Initial m68k mac support from Allen Briggs <briggs@macbsd.com> 75 * (basically consisting of the match, a bit of the attach, and the 76 * "DMA" glue functions). 77 */ 78 79#include <sys/types.h> 80#include <sys/param.h> 81#include <sys/systm.h> 82#include <sys/kernel.h> 83#include <sys/errno.h> 84#include <sys/ioctl.h> 85#include <sys/device.h> 86#include <sys/buf.h> 87#include <sys/proc.h> 88#include <sys/user.h> 89#include <sys/queue.h> 90 91#include <dev/scsipi/scsi_all.h> 92#include <dev/scsipi/scsipi_all.h> 93#include <dev/scsipi/scsiconf.h> 94#include <dev/scsipi/scsi_message.h> 95 96#include <machine/cpu.h> 97#include <machine/bus.h> 98#include <machine/param.h> 99 100#include <dev/ic/ncr53c9xreg.h> 101#include <dev/ic/ncr53c9xvar.h> 102 103#include <machine/viareg.h> 104 105#include <mac68k/obio/espvar.h> 106#include <mac68k/obio/obiovar.h> 107 108void espattach __P((struct device *, struct device *, void *)); 109int espmatch __P((struct device *, struct cfdata *, void *)); 110 111/* Linkup to the rest of the kernel */ 112struct cfattach esp_ca = { 113 sizeof(struct esp_softc), espmatch, espattach 114}; 115 116/* 117 * Functions and the switch for the MI code. 118 */ 119u_char esp_read_reg __P((struct ncr53c9x_softc *, int)); 120void esp_write_reg __P((struct ncr53c9x_softc *, int, u_char)); 121int esp_dma_isintr __P((struct ncr53c9x_softc *)); 122void esp_dma_reset __P((struct ncr53c9x_softc *)); 123int esp_dma_intr __P((struct ncr53c9x_softc *)); 124int esp_dma_setup __P((struct ncr53c9x_softc *, caddr_t *, 125 size_t *, int, size_t *)); 126void esp_dma_go __P((struct ncr53c9x_softc *)); 127void esp_dma_stop __P((struct ncr53c9x_softc *)); 128int esp_dma_isactive __P((struct ncr53c9x_softc *)); 129void esp_quick_write_reg __P((struct ncr53c9x_softc *, int, u_char)); 130int esp_quick_dma_intr __P((struct ncr53c9x_softc *)); 131int esp_quick_dma_setup __P((struct ncr53c9x_softc *, caddr_t *, 132 size_t *, int, size_t *)); 133void esp_quick_dma_go __P((struct ncr53c9x_softc *)); 134 135void esp_intr __P((void *sc)); 136void esp_dualbus_intr __P((void *sc)); 137static struct esp_softc *esp0 = NULL, *esp1 = NULL; 138 139static __inline__ int esp_dafb_have_dreq __P((struct esp_softc *esc)); 140static __inline__ int esp_iosb_have_dreq __P((struct esp_softc *esc)); 141int (*esp_have_dreq) __P((struct esp_softc *esc)); 142 143struct ncr53c9x_glue esp_glue = { 144 esp_read_reg, 145 esp_write_reg, 146 esp_dma_isintr, 147 esp_dma_reset, 148 esp_dma_intr, 149 esp_dma_setup, 150 esp_dma_go, 151 esp_dma_stop, 152 esp_dma_isactive, 153 NULL, /* gl_clear_latched_intr */ 154}; 155 156int 157espmatch(parent, cf, aux) 158 struct device *parent; 159 struct cfdata *cf; 160 void *aux; 161{ 162 int found = 0; 163 164 if ((cf->cf_unit == 0) && mac68k_machine.scsi96) { 165 found = 1; 166 } 167 if ((cf->cf_unit == 1) && mac68k_machine.scsi96_2) { 168 found = 1; 169 } 170 171 return found; 172} 173 174/* 175 * Attach this instance, and then all the sub-devices 176 */ 177void 178espattach(parent, self, aux) 179 struct device *parent, *self; 180 void *aux; 181{ 182 struct obio_attach_args *oa = (struct obio_attach_args *)aux; 183 extern vaddr_t SCSIBase; 184 struct esp_softc *esc = (void *)self; 185 struct ncr53c9x_softc *sc = &esc->sc_ncr53c9x; 186 int quick = 0; 187 unsigned long reg_offset; 188 189 reg_offset = SCSIBase - IOBase; 190 esc->sc_tag = oa->oa_tag; 191 /* 192 * For Wombat, Primus and Optimus motherboards, DREQ is 193 * visible on bit 0 of the IOSB's emulated VIA2 vIFR (and 194 * the scsi registers are offset 0x1000 bytes from IOBase). 195 * 196 * For the Q700/900/950 it's at f9800024 for bus 0 and 197 * f9800028 for bus 1 (900/950). For these machines, that is also 198 * a (12-bit) configuration register for DAFB's control of the 199 * pseudo-DMA timing. The default value is 0x1d1. 200 */ 201 esp_have_dreq = esp_dafb_have_dreq; 202 if (sc->sc_dev.dv_unit == 0) { 203 if (reg_offset == 0x10000) { 204 quick = 1; 205 esp_have_dreq = esp_iosb_have_dreq; 206 } else if (reg_offset == 0x18000) { 207 quick = 0; 208 } else { 209 if (bus_space_map(esc->sc_tag, 0xf9800024, 210 4, 0, &esc->sc_bsh)) { 211 printf("failed to map 4 at 0xf9800024.\n"); 212 } else { 213 quick = 1; 214 bus_space_write_4(esc->sc_tag, 215 esc->sc_bsh, 0, 0x1d1); 216 } 217 } 218 } else { 219 if (bus_space_map(esc->sc_tag, 0xf9800028, 220 4, 0, &esc->sc_bsh)) { 221 printf("failed to map 4 at 0xf9800028.\n"); 222 } else { 223 quick = 1; 224 bus_space_write_4(esc->sc_tag, esc->sc_bsh, 0, 0x1d1); 225 } 226 } 227 if (quick) { 228 esp_glue.gl_write_reg = esp_quick_write_reg; 229 esp_glue.gl_dma_intr = esp_quick_dma_intr; 230 esp_glue.gl_dma_setup = esp_quick_dma_setup; 231 esp_glue.gl_dma_go = esp_quick_dma_go; 232 } 233 234 /* 235 * Set up the glue for MI code early; we use some of it here. 236 */ 237 sc->sc_glue = &esp_glue; 238 239 /* 240 * Save the regs 241 */ 242 if (sc->sc_dev.dv_unit == 0) { 243 esp0 = esc; 244 245 esc->sc_reg = (volatile u_char *) SCSIBase; 246 via2_register_irq(VIA2_SCSIIRQ, esp_intr, esc); 247 esc->irq_mask = V2IF_SCSIIRQ; 248 if (reg_offset == 0x10000) { 249 /* From the Q650 developer's note */ 250 sc->sc_freq = 16500000; 251 } else { 252 sc->sc_freq = 25000000; 253 } 254 255 if (esp_glue.gl_dma_go == esp_quick_dma_go) { 256 printf(" (quick)"); 257 } 258 } else { 259 esp1 = esc; 260 261 esc->sc_reg = (volatile u_char *) SCSIBase + 0x402; 262 via2_register_irq(VIA2_SCSIIRQ, esp_dualbus_intr, NULL); 263 esc->irq_mask = 0; 264 sc->sc_freq = 25000000; 265 266 if (esp_glue.gl_dma_go == esp_quick_dma_go) { 267 printf(" (quick)"); 268 } 269 } 270 271 printf(": address %p", esc->sc_reg); 272 273 sc->sc_id = 7; 274 275 /* gimme Mhz */ 276 sc->sc_freq /= 1000000; 277 278 /* 279 * It is necessary to try to load the 2nd config register here, 280 * to find out what rev the esp chip is, else the esp_reset 281 * will not set up the defaults correctly. 282 */ 283 sc->sc_cfg1 = sc->sc_id; /* | NCRCFG1_PARENB; */ 284 sc->sc_cfg2 = NCRCFG2_SCSI2; 285 sc->sc_cfg3 = 0; 286 sc->sc_rev = NCR_VARIANT_NCR53C96; 287 288 /* 289 * This is the value used to start sync negotiations 290 * Note that the NCR register "SYNCTP" is programmed 291 * in "clocks per byte", and has a minimum value of 4. 292 * The SCSI period used in negotiation is one-fourth 293 * of the time (in nanoseconds) needed to transfer one byte. 294 * Since the chip's clock is given in MHz, we have the following 295 * formula: 4 * period = (1000 / freq) * 4 296 */ 297 sc->sc_minsync = 1000 / sc->sc_freq; 298 299 /* We need this to fit into the TCR... */ 300 sc->sc_maxxfer = 64 * 1024; 301 302 if (!quick) { 303 sc->sc_minsync = 0; /* No synchronous xfers w/o DMA */ 304 sc->sc_maxxfer = 8 * 1024; 305 } 306 307 /* 308 * Configure interrupts. 309 */ 310 if (esc->irq_mask) { 311 via2_reg(vPCR) = 0x22; 312 via2_reg(vIFR) = esc->irq_mask; 313 via2_reg(vIER) = 0x80 | esc->irq_mask; 314 } 315 316 /* 317 * Now try to attach all the sub-devices 318 */ 319 ncr53c9x_attach(sc, NULL, NULL); 320} 321 322/* 323 * Glue functions. 324 */ 325 326u_char 327esp_read_reg(sc, reg) 328 struct ncr53c9x_softc *sc; 329 int reg; 330{ 331 struct esp_softc *esc = (struct esp_softc *)sc; 332 333 return esc->sc_reg[reg * 16]; 334} 335 336void 337esp_write_reg(sc, reg, val) 338 struct ncr53c9x_softc *sc; 339 int reg; 340 u_char val; 341{ 342 struct esp_softc *esc = (struct esp_softc *)sc; 343 u_char v = val; 344 345 if (reg == NCR_CMD && v == (NCRCMD_TRANS|NCRCMD_DMA)) { 346 v = NCRCMD_TRANS; 347 } 348 esc->sc_reg[reg * 16] = v; 349} 350 351void 352esp_dma_stop(sc) 353 struct ncr53c9x_softc *sc; 354{ 355} 356 357int 358esp_dma_isactive(sc) 359 struct ncr53c9x_softc *sc; 360{ 361 struct esp_softc *esc = (struct esp_softc *)sc; 362 363 return esc->sc_active; 364} 365 366int 367esp_dma_isintr(sc) 368 struct ncr53c9x_softc *sc; 369{ 370 struct esp_softc *esc = (struct esp_softc *)sc; 371 372 return esc->sc_reg[NCR_STAT * 16] & 0x80; 373} 374 375void 376esp_dma_reset(sc) 377 struct ncr53c9x_softc *sc; 378{ 379 struct esp_softc *esc = (struct esp_softc *)sc; 380 381 esc->sc_active = 0; 382 esc->sc_tc = 0; 383} 384 385int 386esp_dma_intr(sc) 387 struct ncr53c9x_softc *sc; 388{ 389 struct esp_softc *esc = (struct esp_softc *)sc; 390 volatile u_char *cmdreg, *intrreg, *statreg, *fiforeg; 391 u_char *p; 392 u_int espphase, espstat, espintr; 393 int cnt, s; 394 395 if (esc->sc_active == 0) { 396 printf("dma_intr--inactive DMA\n"); 397 return -1; 398 } 399 400 if ((sc->sc_espintr & NCRINTR_BS) == 0) { 401 esc->sc_active = 0; 402 return 0; 403 } 404 405 cnt = esc->sc_dmasize; 406 if (esc->sc_dmasize == 0) { 407 printf("data interrupt, but no count left."); 408 } 409 410 p = *esc->sc_dmaaddr; 411 espphase = sc->sc_phase; 412 espstat = (u_int) sc->sc_espstat; 413 espintr = (u_int) sc->sc_espintr; 414 cmdreg = esc->sc_reg + NCR_CMD * 16; 415 fiforeg = esc->sc_reg + NCR_FIFO * 16; 416 statreg = esc->sc_reg + NCR_STAT * 16; 417 intrreg = esc->sc_reg + NCR_INTR * 16; 418 do { 419 if (esc->sc_datain) { 420 *p++ = *fiforeg; 421 cnt--; 422 if (espphase == DATA_IN_PHASE) { 423 *cmdreg = NCRCMD_TRANS; 424 } else { 425 esc->sc_active = 0; 426 } 427 } else { 428 if ( (espphase == DATA_OUT_PHASE) 429 || (espphase == MESSAGE_OUT_PHASE)) { 430 *fiforeg = *p++; 431 cnt--; 432 *cmdreg = NCRCMD_TRANS; 433 } else { 434 esc->sc_active = 0; 435 } 436 } 437 438 if (esc->sc_active) { 439 while (!(*statreg & 0x80)); 440 s = splhigh(); 441 espstat = *statreg; 442 espintr = *intrreg; 443 espphase = (espintr & NCRINTR_DIS) 444 ? /* Disconnected */ BUSFREE_PHASE 445 : espstat & PHASE_MASK; 446 splx(s); 447 } 448 } while (esc->sc_active && (espintr & NCRINTR_BS)); 449 sc->sc_phase = espphase; 450 sc->sc_espstat = (u_char) espstat; 451 sc->sc_espintr = (u_char) espintr; 452 *esc->sc_dmaaddr = p; 453 esc->sc_dmasize = cnt; 454 455 if (esc->sc_dmasize == 0) { 456 esc->sc_tc = NCRSTAT_TC; 457 } 458 sc->sc_espstat |= esc->sc_tc; 459 return 0; 460} 461 462int 463esp_dma_setup(sc, addr, len, datain, dmasize) 464 struct ncr53c9x_softc *sc; 465 caddr_t *addr; 466 size_t *len; 467 int datain; 468 size_t *dmasize; 469{ 470 struct esp_softc *esc = (struct esp_softc *)sc; 471 472 esc->sc_dmaaddr = addr; 473 esc->sc_dmalen = len; 474 esc->sc_datain = datain; 475 esc->sc_dmasize = *dmasize; 476 esc->sc_tc = 0; 477 478 return 0; 479} 480 481void 482esp_dma_go(sc) 483 struct ncr53c9x_softc *sc; 484{ 485 struct esp_softc *esc = (struct esp_softc *)sc; 486 487 if (esc->sc_datain == 0) { 488 esc->sc_reg[NCR_FIFO * 16] = **esc->sc_dmaaddr; 489 (*esc->sc_dmalen)--; 490 (*esc->sc_dmaaddr)++; 491 } 492 esc->sc_active = 1; 493} 494 495void 496esp_quick_write_reg(sc, reg, val) 497 struct ncr53c9x_softc *sc; 498 int reg; 499 u_char val; 500{ 501 struct esp_softc *esc = (struct esp_softc *)sc; 502 503 esc->sc_reg[reg * 16] = val; 504} 505 506#if DEBUG 507int mac68k_esp_debug=0; 508#endif 509 510int 511esp_quick_dma_intr(sc) 512 struct ncr53c9x_softc *sc; 513{ 514 struct esp_softc *esc = (struct esp_softc *)sc; 515 int trans=0, resid=0; 516 517 if (esc->sc_active == 0) 518 panic("dma_intr--inactive DMA\n"); 519 520 esc->sc_active = 0; 521 522 if (esc->sc_dmasize == 0) { 523 int res; 524 525 res = NCR_READ_REG(sc, NCR_TCL); 526 res += NCR_READ_REG(sc, NCR_TCM) << 8; 527 printf("dmaintr: DMA xfer of zero xferred %d\n", res); 528 return 0; 529 } 530 531 if ((sc->sc_espstat & NCRSTAT_TC) == 0) { 532 resid += NCR_READ_REG(sc, NCR_TCL); 533 resid += NCR_READ_REG(sc, NCR_TCM) << 8; 534 if (resid == 0) 535 resid = 65536; 536 } 537 538 trans = esc->sc_dmasize - resid; 539 if (trans < 0) { 540 printf("dmaintr: trans < 0????"); 541 trans = *esc->sc_dmalen; 542 } 543 544 NCR_DMA(("dmaintr: trans %d, resid %d.\n", trans, resid)); 545#if DEBUG 546 if (mac68k_esp_debug) { 547 printf("eqd_intr: trans %d, resid %d.\n", trans, resid); 548 } 549#endif 550 *esc->sc_dmaaddr += trans; 551 *esc->sc_dmalen -= trans; 552 553 return 0; 554} 555 556int 557esp_quick_dma_setup(sc, addr, len, datain, dmasize) 558 struct ncr53c9x_softc *sc; 559 caddr_t *addr; 560 size_t *len; 561 int datain; 562 size_t *dmasize; 563{ 564 struct esp_softc *esc = (struct esp_softc *)sc; 565 566 esc->sc_dmaaddr = addr; 567 esc->sc_dmalen = len; 568 569 if (*len & 1) { 570 esc->sc_pad = 1; 571 } else { 572 esc->sc_pad = 0; 573 } 574 575 esc->sc_datain = datain; 576 esc->sc_dmasize = *dmasize; 577 578#if DIAGNOSTIC 579 if (esc->sc_dmasize == 0) { 580 printf("esp_quick_dma_setup called with %lx, %lx, %d, %lx\n", 581 (long) *addr, (long) *len, datain, (long) esc->sc_dmasize); 582 } 583#endif 584#if DEBUG 585 if (mac68k_esp_debug) { 586 printf("eqd_setup: addr %lx, len %lx, in? %d, dmasize %lx\n", 587 (long) *addr, (long) *len, datain, (long) esc->sc_dmasize); 588 } 589#endif 590 591 return 0; 592} 593 594static __inline__ int 595esp_dafb_have_dreq(esc) 596 struct esp_softc *esc; 597{ 598 return (*(volatile u_int32_t *)(esc->sc_bsh.base) & 0x200); 599} 600 601static __inline__ int 602esp_iosb_have_dreq(esc) 603 struct esp_softc *esc; 604{ 605 return (via2_reg(vIFR) & V2IF_SCSIDRQ); 606} 607 608static volatile int espspl=-1; 609 610/* 611 * Apple "DMA" is weird. 612 * 613 * Basically, the CPU acts like the DMA controller. The DREQ/ off the 614 * chip goes to a register that we've mapped at attach time (on the 615 * IOSB or DAFB, depending on the machine). Apple also provides some 616 * space for which the memory controller handshakes data to/from the 617 * NCR chip with the DACK/ line. This space appears to be mapped over 618 * and over, every 4 bytes, but only the lower 16 bits are valid (but 619 * reading the upper 16 bits will handshake DACK/ just fine, so if you 620 * read *u_int16_t++ = *u_int16_t++ in a loop, you'll get 621 * <databyte><databyte>0xff0xff<databyte><databyte>0xff0xff... 622 * 623 * When you're attempting to read or write memory to this DACK/ed space, 624 * and the NCR is not ready for some timeout period, the system will 625 * generate a bus error. This might be for one of several reasons: 626 * 627 * 1) (on write) The FIFO is full and is not draining. 628 * 2) (on read) The FIFO is empty and is not filling. 629 * 3) An interrupt condition has occurred. 630 * 4) Anything else? 631 * 632 * So if a bus error occurs, we first turn off the nofault bus error handler, 633 * then we check for an interrupt (which would render the first two 634 * possibilities moot). If there's no interrupt, check for a DREQ/. If we 635 * have that, then attempt to resume stuffing (or unstuffing) the FIFO. If 636 * neither condition holds, pause briefly and check again. 637 * 638 * NOTE!!! In order to make allowances for the hardware structure of 639 * the mac, spl values in here are hardcoded!!!!!!!!! 640 * This is done to allow serial interrupts to get in during 641 * scsi transfers. This is ugly. 642 */ 643void 644esp_quick_dma_go(sc) 645 struct ncr53c9x_softc *sc; 646{ 647 struct esp_softc *esc = (struct esp_softc *)sc; 648 extern long mac68k_a2_fromfault; 649 extern int *nofault; 650 label_t faultbuf; 651 u_int16_t volatile *pdma; 652 u_int16_t *addr; 653 int len, res; 654 u_short cnt32, cnt2; 655 u_char volatile *statreg; 656 657 esc->sc_active = 1; 658 659 espspl = splhigh(); 660 661 addr = (u_int16_t *) *esc->sc_dmaaddr; 662 len = esc->sc_dmasize; 663 664restart_dmago: 665#if DEBUG 666 if (mac68k_esp_debug) { 667 printf("eqdg: a %lx, l %lx, in? %d ... ", 668 (long) addr, (long) len, esc->sc_datain); 669 } 670#endif 671 nofault = (int *) &faultbuf; 672 if (setjmp((label_t *) nofault)) { 673 int i=0; 674 675 nofault = (int *) 0; 676#if DEBUG 677 if (mac68k_esp_debug) { 678 printf("be\n"); 679 } 680#endif 681 /* 682 * Bus error... 683 * So, we first check for an interrupt. If we have 684 * one, go handle it. Next we check for DREQ/. If 685 * we have it, then we restart the transfer. If 686 * neither, then loop until we get one or the other. 687 */ 688 statreg = esc->sc_reg + NCR_STAT * 16; 689 for (;;) { 690 spl2(); /* Give serial a chance... */ 691 splhigh(); /* That's enough... */ 692 693 if (*statreg & 0x80) { 694 goto gotintr; 695 } 696 697 if (esp_have_dreq(esc)) { 698 /* 699 * Get the length from the address 700 * differential. 701 */ 702 addr = (u_int16_t *) mac68k_a2_fromfault; 703 len = esc->sc_dmasize - 704 ((long) addr - (long) *esc->sc_dmaaddr); 705 706 if (esc->sc_datain == 0) { 707 /* 708 * Let the FIFO drain before we read 709 * the transfer count. 710 * Do we need to do this? 711 * Can we do this? 712 */ 713 while (NCR_READ_REG(sc, NCR_FFLAG) 714 & 0x1f); 715 /* 716 * Get the length from the transfer 717 * counters. 718 */ 719 res = NCR_READ_REG(sc, NCR_TCL); 720 res += NCR_READ_REG(sc, NCR_TCM) << 8; 721 /* 722 * If they don't agree, 723 * adjust accordingly. 724 */ 725 while (res > len) { 726 len+=2; addr--; 727 } 728 if (res != len) { 729 panic("esp_quick_dma_go: res %d != len %d\n", 730 res, len); 731 } 732 } 733 break; 734 } 735 736 DELAY(1); 737 if (i++ > 1000000) 738 panic("esp_dma_go: Bus error, but no condition! Argh!"); 739 } 740 goto restart_dmago; 741 } 742 743 len &= ~1; 744 745 statreg = esc->sc_reg + NCR_STAT * 16; 746 pdma = (u_int16_t *) (esc->sc_reg + 0x100); 747 748 /* 749 * These loops are unrolled into assembly for two reasons: 750 * 1) We can make sure that they are as efficient as possible, and 751 * 2) (more importantly) we need the address that we are reading 752 * from or writing to to be in a2. 753 */ 754 cnt32 = len / 32; 755 cnt2 = (len % 32) / 2; 756 if (esc->sc_datain == 0) { 757 /* while (cnt32--) { 16 instances of *pdma = *addr++; } */ 758 /* while (cnt2--) { *pdma = *addr++; } */ 759 __asm __volatile (" 760 movl %1, %%a2 761 movl %2, %%a3 762 movw %3, %%d2 763 cmpw #0, %%d2 764 beq 2f 765 subql #1, %%d2 766 1: movw %%a2@+,%%a3@; movw %%a2@+,%%a3@ 767 movw %%a2@+,%%a3@; movw %%a2@+,%%a3@ 768 movw %%a2@+,%%a3@; movw %%a2@+,%%a3@ 769 movw %%a2@+,%%a3@; movw %%a2@+,%%a3@ 770 movw %%a2@+,%%a3@; movw %%a2@+,%%a3@ 771 movw %%a2@+,%%a3@; movw %%a2@+,%%a3@ 772 movw %%a2@+,%%a3@; movw %%a2@+,%%a3@ 773 movw %%a2@+,%%a3@; movw %%a2@+,%%a3@ 774 movw #8704,%%sr 775 movw #9728,%%sr 776 dbra %%d2, 1b 777 2: movw %4, %%d2 778 cmpw #0, %%d2 779 beq 4f 780 subql #1, %%d2 781 3: movw %%a2@+,%%a3@ 782 dbra %%d2, 3b 783 4: movl %%a2, %0" 784 : "=g" (addr) 785 : "0" (addr), "g" (pdma), "g" (cnt32), "g" (cnt2) 786 : "a2", "a3", "d2"); 787 if (esc->sc_pad) { 788 unsigned char *c; 789 c = (unsigned char *) addr; 790 /* Wait for DREQ */ 791 while (!esp_have_dreq(esc)) { 792 if (*statreg & 0x80) { 793 nofault = (int *) 0; 794 goto gotintr; 795 } 796 } 797 *(unsigned char *)pdma = *c; 798 } 799 } else { 800 /* while (cnt32--) { 16 instances of *addr++ = *pdma; } */ 801 /* while (cnt2--) { *addr++ = *pdma; } */ 802 __asm __volatile (" 803 movl %1, %%a2 804 movl %2, %%a3 805 movw %3, %%d2 806 cmpw #0, %%d2 807 beq 6f 808 subql #1, %%d2 809 5: movw %%a3@,%%a2@+; movw %%a3@,%%a2@+ 810 movw %%a3@,%%a2@+; movw %%a3@,%%a2@+ 811 movw %%a3@,%%a2@+; movw %%a3@,%%a2@+ 812 movw %%a3@,%%a2@+; movw %%a3@,%%a2@+ 813 movw %%a3@,%%a2@+; movw %%a3@,%%a2@+ 814 movw %%a3@,%%a2@+; movw %%a3@,%%a2@+ 815 movw %%a3@,%%a2@+; movw %%a3@,%%a2@+ 816 movw %%a3@,%%a2@+; movw %%a3@,%%a2@+ 817 movw #8704,%%sr 818 movw #9728,%%sr 819 dbra %%d2, 5b 820 6: movw %4, %%d2 821 cmpw #0, %%d2 822 beq 8f 823 subql #1, %%d2 824 7: movw %%a3@,%%a2@+ 825 dbra %%d2, 7b 826 8: movl %%a2, %0" 827 : "=g" (addr) 828 : "0" (addr), "g" (pdma), "g" (cnt32), "g" (cnt2) 829 : "a2", "a3", "d2"); 830 if (esc->sc_pad) { 831 unsigned char *c; 832 c = (unsigned char *) addr; 833 /* Wait for DREQ */ 834 while (!esp_have_dreq(esc)) { 835 if (*statreg & 0x80) { 836 nofault = (int *) 0; 837 goto gotintr; 838 } 839 } 840 *c = *(unsigned char *)pdma; 841 } 842 } 843 844 nofault = (int *) 0; 845 846 /* 847 * If we have not received an interrupt yet, we should shortly, 848 * and we can't prevent it, so return and wait for it. 849 */ 850 if ((*statreg & 0x80) == 0) { 851#if DEBUG 852 if (mac68k_esp_debug) { 853 printf("g.\n"); 854 } 855#endif 856 if (espspl != -1) splx(espspl); espspl = -1; 857 return; 858 } 859 860gotintr: 861#if DEBUG 862 if (mac68k_esp_debug) { 863 printf("g!\n"); 864 } 865#endif 866 ncr53c9x_intr(sc); 867 if (espspl != -1) splx(espspl); espspl = -1; 868} 869 870void 871esp_intr(sc) 872 void *sc; 873{ 874 struct esp_softc *esc = (struct esp_softc *)sc; 875 876 if (esc->sc_reg[NCR_STAT * 16] & 0x80) { 877 ncr53c9x_intr((struct ncr53c9x_softc *) esp0); 878 } 879} 880 881void 882esp_dualbus_intr(sc) 883 void *sc; 884{ 885 if (esp0 && (esp0->sc_reg[NCR_STAT * 16] & 0x80)) { 886 ncr53c9x_intr((struct ncr53c9x_softc *) esp0); 887 } 888 889 if (esp1 && (esp1->sc_reg[NCR_STAT * 16] & 0x80)) { 890 ncr53c9x_intr((struct ncr53c9x_softc *) esp1); 891 } 892} 893