Home | History | Annotate | Line # | Download | only in mca
edc_mca.c revision 1.22
      1 /*	$NetBSD: edc_mca.c,v 1.22 2003/10/25 18:37:03 christos Exp $	*/
      2 
      3 /*
      4  * Copyright (c) 2001 The NetBSD Foundation, Inc.
      5  *
      6  * This code is derived from software contributed to The NetBSD Foundation
      7  * by Jaromir Dolecek.
      8  *
      9  * Redistribution and use in source and binary forms, with or without
     10  * modification, are permitted provided that the following conditions
     11  * are met:
     12  * 1. Redistributions of source code must retain the above copyright
     13  *    notice, this list of conditions and the following disclaimer.
     14  * 2. Redistributions in binary form must reproduce the above copyright
     15  *    notice, this list of conditions and the following disclaimer in the
     16  *    documentation and/or other materials provided with the distribution.
     17  * 3. All advertising materials mentioning features or use of this software
     18  *    must display the following acknowledgement:
     19  *        This product includes software developed by the NetBSD
     20  *        Foundation, Inc. and its contributors.
     21  * 4. The name of the author may not be used to endorse or promote products
     22  *    derived from this software without specific prior written permission.
     23  *
     24  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
     25  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
     26  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
     27  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
     28  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
     29  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     30  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     31  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     32  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
     33  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     34  */
     35 
     36 /*
     37  * Driver for MCA ESDI controllers and disks conforming to IBM DASD
     38  * spec.
     39  *
     40  * The driver was written with DASD Storage Interface Specification
     41  * for MCA rev. 2.2 in hands, thanks to Scott Telford <st (at) epcc.ed.ac.uk>.
     42  *
     43  * TODO:
     44  * - improve error recovery
     45  *   Issue soft reset on error or timeout?
     46  * - test with > 1 disk (this is supported by some controllers)
     47  * - test with > 1 ESDI controller in machine; shared interrupts
     48  *   necessary for this to work should be supported - edc_intr() specifically
     49  *   checks if the interrupt is for this controller
     50  */
     51 
     52 #include <sys/cdefs.h>
     53 __KERNEL_RCSID(0, "$NetBSD: edc_mca.c,v 1.22 2003/10/25 18:37:03 christos Exp $");
     54 
     55 #include "rnd.h"
     56 
     57 #include <sys/param.h>
     58 #include <sys/systm.h>
     59 #include <sys/errno.h>
     60 #include <sys/device.h>
     61 #include <sys/malloc.h>
     62 #include <sys/endian.h>
     63 #include <sys/disklabel.h>
     64 #include <sys/disk.h>
     65 #include <sys/syslog.h>
     66 #include <sys/proc.h>
     67 #include <sys/vnode.h>
     68 #include <sys/kernel.h>
     69 #include <sys/kthread.h>
     70 #if NRND > 0
     71 #include <sys/rnd.h>
     72 #endif
     73 
     74 #include <machine/bus.h>
     75 #include <machine/intr.h>
     76 
     77 #include <dev/mca/mcareg.h>
     78 #include <dev/mca/mcavar.h>
     79 #include <dev/mca/mcadevs.h>
     80 
     81 #include <dev/mca/edcreg.h>
     82 #include <dev/mca/edvar.h>
     83 #include <dev/mca/edcvar.h>
     84 
     85 #define EDC_ATTN_MAXTRIES	10000	/* How many times check for unbusy */
     86 #define EDC_MAX_CMD_RES_LEN	8
     87 
     88 struct edc_mca_softc {
     89 	struct device sc_dev;
     90 
     91 	bus_space_tag_t	sc_iot;
     92 	bus_space_handle_t sc_ioh;
     93 
     94 	/* DMA related stuff */
     95 	bus_dma_tag_t sc_dmat;		/* DMA tag as passed by parent */
     96 	bus_dmamap_t  sc_dmamap_xfer;	/* transfer dma map */
     97 
     98 	void	*sc_ih;				/* interrupt handle */
     99 
    100 	int	sc_flags;
    101 #define	DASD_QUIET	0x01		/* don't dump cmd error info */
    102 
    103 #define DASD_MAXDEVS	8
    104 	struct ed_softc *sc_ed[DASD_MAXDEVS];
    105 	int sc_maxdevs;			/* max number of disks attached to this
    106 					 * controller */
    107 
    108 	/* I/O results variables */
    109 	volatile int sc_stat;
    110 #define	STAT_START	0
    111 #define	STAT_ERROR	1
    112 #define	STAT_DONE	2
    113 	volatile int sc_resblk;		/* residual block count */
    114 
    115 	/* CMD status block - only set & used in edc_intr() */
    116 	u_int16_t status_block[EDC_MAX_CMD_RES_LEN];
    117 };
    118 
    119 int	edc_mca_probe	__P((struct device *, struct cfdata *, void *));
    120 void	edc_mca_attach	__P((struct device *, struct device *, void *));
    121 
    122 CFATTACH_DECL(edc_mca, sizeof(struct edc_mca_softc),
    123     edc_mca_probe, edc_mca_attach, NULL, NULL);
    124 
    125 static int	edc_intr __P((void *));
    126 static void	edc_dump_status_block __P((struct edc_mca_softc *,
    127 		    u_int16_t *, int));
    128 static int	edc_do_attn __P((struct edc_mca_softc *, int, int, int));
    129 static void	edc_cmd_wait __P((struct edc_mca_softc *, int, int));
    130 static void	edcworker __P((void *));
    131 static void	edc_spawn_worker __P((void *));
    132 
    133 int
    134 edc_mca_probe(parent, match, aux)
    135 	struct device *parent;
    136 	struct cfdata *match;
    137 	void *aux;
    138 {
    139 	struct mca_attach_args *ma = aux;
    140 
    141 	switch (ma->ma_id) {
    142 	case MCA_PRODUCT_IBM_ESDIC:
    143 	case MCA_PRODUCT_IBM_ESDIC_IG:
    144 		return (1);
    145 	default:
    146 		return (0);
    147 	}
    148 }
    149 
    150 void
    151 edc_mca_attach(parent, self, aux)
    152 	struct device *parent, *self;
    153 	void *aux;
    154 {
    155 	struct edc_mca_softc *sc = (void *) self;
    156 	struct mca_attach_args *ma = aux;
    157 	struct ed_attach_args eda;
    158 	int pos2, pos3, pos4;
    159 	int irq, drq, iobase;
    160 	const char *typestr;
    161 	int devno, error;
    162 
    163 	pos2 = mca_conf_read(ma->ma_mc, ma->ma_slot, 2);
    164 	pos3 = mca_conf_read(ma->ma_mc, ma->ma_slot, 3);
    165 	pos4 = mca_conf_read(ma->ma_mc, ma->ma_slot, 4);
    166 
    167 	/*
    168 	 * POS register 2: (adf pos0)
    169 	 *
    170 	 * 7 6 5 4 3 2 1 0
    171 	 *   \ \____/  \ \__ enable: 0=adapter disabled, 1=adapter enabled
    172 	 *    \     \   \___ Primary/Alternate Port Adresses:
    173 	 *     \     \		0=0x3510-3517 1=0x3518-0x351f
    174 	 *      \     \_____ DMA Arbitration Level: 0101=5 0110=6 0111=7
    175 	 *       \              0000=0 0001=1 0011=3 0100=4
    176 	 *        \_________ Fairness On/Off: 1=On 0=Off
    177 	 *
    178 	 * POS register 3: (adf pos1)
    179 	 *
    180 	 * 7 6 5 4 3 2 1 0
    181 	 * 0 0 \_/
    182 	 *       \__________ DMA Burst Pacing Interval: 10=24ms 11=31ms
    183 	 *                     01=16ms 00=Burst Disabled
    184 	 *
    185 	 * POS register 4: (adf pos2)
    186 	 *
    187 	 * 7 6 5 4 3 2 1 0
    188 	 *           \_/ \__ DMA Pacing Control: 1=Disabled 0=Enabled
    189 	 *             \____ Time to Release: 1X=6ms 01=3ms 00=Immediate
    190 	 *
    191 	 * IRQ is fixed to 14 (0x0e).
    192 	 */
    193 
    194 	switch (ma->ma_id) {
    195 	case MCA_PRODUCT_IBM_ESDIC:
    196 		typestr = "IBM ESDI Fixed Disk Controller";
    197 		break;
    198 	case MCA_PRODUCT_IBM_ESDIC_IG:
    199 		typestr = "IBM Integ. ESDI Fixed Disk & Controller";
    200 		break;
    201 	default:
    202 		typestr = NULL;
    203 		break;
    204 	}
    205 
    206 	irq = ESDIC_IRQ;
    207 	iobase = (pos2 & IO_IS_ALT) ? ESDIC_IOALT : ESDIC_IOPRM;
    208 	drq = (pos2 & DRQ_MASK) >> 2;
    209 
    210 	printf(" slot %d irq %d drq %d: %s\n", ma->ma_slot+1,
    211 		irq, drq, typestr);
    212 
    213 #ifdef DIAGNOSTIC
    214 	/*
    215 	 * It's not strictly necessary to check this, machine configuration
    216 	 * utility uses only valid adresses.
    217 	 */
    218 	if (drq == 2 || drq >= 8) {
    219 		printf("%s: invalid DMA Arbitration Level %d\n",
    220 			sc->sc_dev.dv_xname, drq);
    221 		return;
    222 	}
    223 #endif
    224 
    225 	printf("%s: Fairness %s, Release %s, ",
    226 		sc->sc_dev.dv_xname,
    227 		(pos2 & FAIRNESS_ENABLE) ? "On" : "Off",
    228 		(pos4 & RELEASE_1) ? "6ms"
    229 				: ((pos4 & RELEASE_2) ? "3ms" : "Immediate")
    230 		);
    231 	if ((pos4 & PACING_CTRL_DISABLE) == 0) {
    232 		static const char * const pacint[] =
    233 			{ "disabled", "16ms", "24ms", "31ms"};
    234 		printf("DMA burst pacing interval %s\n",
    235 			pacint[(pos3 & PACING_INT_MASK) >> 4]);
    236 	} else
    237 		printf("DMA pacing control disabled\n");
    238 
    239 	sc->sc_iot = ma->ma_iot;
    240 
    241 	if (bus_space_map(sc->sc_iot, iobase,
    242 	    ESDIC_REG_NPORTS, 0, &sc->sc_ioh)) {
    243 		printf("%s: couldn't map registers\n",
    244 		    sc->sc_dev.dv_xname);
    245 		return;
    246 	}
    247 
    248 	sc->sc_ih = mca_intr_establish(ma->ma_mc, irq, IPL_BIO, edc_intr, sc);
    249 	if (sc->sc_ih == NULL) {
    250 		printf("%s: couldn't establish interrupt handler\n",
    251 			sc->sc_dev.dv_xname);
    252 		return;
    253 	}
    254 
    255 	/* Create a MCA DMA map, used for data transfer */
    256 	sc->sc_dmat = ma->ma_dmat;
    257 	if ((error = mca_dmamap_create(sc->sc_dmat, MAXPHYS,
    258 	    BUS_DMA_NOWAIT | BUS_DMA_ALLOCNOW | MCABUS_DMA_16BIT,
    259 	    &sc->sc_dmamap_xfer, drq)) != 0){
    260 		printf("%s: couldn't create DMA map - error %d\n",
    261 			sc->sc_dev.dv_xname, error);
    262 		return;
    263 	}
    264 
    265 	/*
    266 	 * Integrated ESDI controller supports only one disk, other
    267 	 * controllers support two disks.
    268 	 */
    269 	if (ma->ma_id == MCA_PRODUCT_IBM_ESDIC_IG)
    270 		sc->sc_maxdevs = 1;
    271 	else
    272 		sc->sc_maxdevs = 2;
    273 
    274 	/*
    275 	 * Reset controller and attach individual disks. ed attach routine
    276 	 * uses polling so that this works with interrupts disabled.
    277 	 */
    278 
    279 	/* Do a reset to ensure sane state after warm boot. */
    280 	if (bus_space_read_1(sc->sc_iot, sc->sc_ioh, BSR) & BSR_BUSY) {
    281 		/* hard reset */
    282 		printf("%s: controller busy, performing hardware reset ...\n",
    283 			sc->sc_dev.dv_xname);
    284 		bus_space_write_1(sc->sc_iot, sc->sc_ioh, BCR,
    285 			BCR_INT_ENABLE|BCR_RESET);
    286 	} else {
    287 		/* "SOFT" reset */
    288 		edc_do_attn(sc, ATN_RESET_ATTACHMENT, DASD_DEVNO_CONTROLLER,0);
    289 	}
    290 
    291 	/*
    292 	 * Since interrupts are disabled, it's necessary
    293 	 * to detect the interrupt request and call edc_intr()
    294 	 * explicitly. See also edc_run_cmd().
    295 	 */
    296 	while(bus_space_read_1(sc->sc_iot, sc->sc_ioh, BSR) & BSR_BUSY) {
    297 		if (bus_space_read_1(sc->sc_iot, sc->sc_ioh, BSR) & BSR_INTR)
    298 			edc_intr(sc);
    299 
    300 		delay(100);
    301 	}
    302 
    303 	/* be quiet during probes */
    304 	sc->sc_flags |= DASD_QUIET;
    305 
    306 	/* check for attached disks */
    307 	for(devno=0; devno < sc->sc_maxdevs; devno++) {
    308 		eda.edc_drive = devno;
    309 		sc->sc_ed[devno] =
    310 			(void *) config_found_sm(self, &eda, NULL, NULL);
    311 
    312 		/* If initialization did not succeed, NULL the pointer. */
    313 		if (sc->sc_ed[devno]
    314 		    && (sc->sc_ed[devno]->sc_flags & EDF_INIT) == 0)
    315 			sc->sc_ed[devno] = NULL;
    316 	}
    317 
    318 	/* enable full error dumps again */
    319 	sc->sc_flags &= ~DASD_QUIET;
    320 
    321 	/*
    322 	 * Check if there are any disks attached. If not, disestablish
    323 	 * the interrupt.
    324 	 */
    325 	for(devno=0; devno < sc->sc_maxdevs; devno++) {
    326 		if (sc->sc_ed[devno])
    327 			break;
    328 	}
    329 
    330 	if (devno == sc->sc_maxdevs) {
    331 		printf("%s: disabling controller (no drives attached)\n",
    332 			sc->sc_dev.dv_xname);
    333 		mca_intr_disestablish(ma->ma_mc, sc->sc_ih);
    334 		return;
    335 	}
    336 
    337 	/*
    338 	 * Run the worker thread.
    339 	 */
    340 	config_pending_incr();
    341 	kthread_create(edc_spawn_worker, (void *) sc);
    342 }
    343 
    344 void
    345 edc_add_disk(sc, ed)
    346 	struct edc_mca_softc *sc;
    347 	struct ed_softc *ed;
    348 {
    349 	sc->sc_ed[ed->sc_devno] = ed;
    350 }
    351 
    352 static int
    353 edc_intr(arg)
    354 	void *arg;
    355 {
    356 	struct edc_mca_softc *sc = arg;
    357 	u_int8_t isr, intr_id;
    358 	u_int16_t sifr;
    359 	int cmd=-1, devno;
    360 
    361 	/*
    362 	 * Check if the interrupt was for us.
    363 	 */
    364 	if ((bus_space_read_1(sc->sc_iot, sc->sc_ioh, BSR) & BSR_INTR) == 0)
    365 		return (0);
    366 
    367 	/*
    368 	 * Read ISR to find out interrupt type. This also clears the interrupt
    369 	 * condition and BSR_INTR flag. Accordings to docs interrupt ID of 0, 2
    370 	 * and 4 are reserved and not used.
    371 	 */
    372 	isr = bus_space_read_1(sc->sc_iot, sc->sc_ioh, ISR);
    373 	intr_id = isr & ISR_INTR_ID_MASK;
    374 
    375 #ifdef EDC_DEBUG
    376 	if (intr_id == 0 || intr_id == 2 || intr_id == 4) {
    377 		printf("%s: bogus interrupt id %d\n", sc->sc_dev.dv_xname,
    378 			(int) intr_id);
    379 		return (0);
    380 	}
    381 #endif
    382 
    383 	/* Get number of device whose intr this was */
    384 	devno = (isr & 0xe0) >> 5;
    385 
    386 	/*
    387 	 * Get Status block. Higher byte always says how long the status
    388 	 * block is, rest is device number and command code.
    389 	 * Check the status block length against our supported maximum length
    390 	 * and fetch the data.
    391 	 */
    392 	if (bus_space_read_1(sc->sc_iot, sc->sc_ioh,BSR) & BSR_SIFR_FULL) {
    393 		size_t len;
    394 		int i;
    395 
    396 		sifr = le16toh(bus_space_read_2(sc->sc_iot, sc->sc_ioh, SIFR));
    397 		len = (sifr & 0xff00) >> 8;
    398 #ifdef DEBUG
    399 		if (len > EDC_MAX_CMD_RES_LEN)
    400 			panic("%s: maximum Status Length exceeded: %d > %d",
    401 				sc->sc_dev.dv_xname,
    402 				len, EDC_MAX_CMD_RES_LEN);
    403 #endif
    404 
    405 		/* Get command code */
    406 		cmd = sifr & SIFR_CMD_MASK;
    407 
    408 		/* Read whole status block */
    409 		sc->status_block[0] = sifr;
    410 		for(i=1; i < len; i++) {
    411 			while((bus_space_read_1(sc->sc_iot, sc->sc_ioh, BSR)
    412 				& BSR_SIFR_FULL) == 0)
    413 				;
    414 
    415 			sc->status_block[i] = le16toh(
    416 				bus_space_read_2(sc->sc_iot, sc->sc_ioh, SIFR));
    417 		}
    418 		/* zero out rest */
    419 		if (i < EDC_MAX_CMD_RES_LEN) {
    420 			memset(&sc->status_block[i], 0,
    421 				(EDC_MAX_CMD_RES_LEN-i)*sizeof(u_int16_t));
    422 		}
    423 	}
    424 
    425 	switch (intr_id) {
    426 	case ISR_DATA_TRANSFER_RDY:
    427 		/*
    428 		 * Ready to do DMA. The DMA controller has already been
    429 		 * setup, now just kick disk controller to do the transfer.
    430 		 */
    431 		bus_space_write_1(sc->sc_iot, sc->sc_ioh, BCR,
    432 			BCR_INT_ENABLE|BCR_DMA_ENABLE);
    433 		break;
    434 
    435 	case ISR_COMPLETED:
    436 	case ISR_COMPLETED_WITH_ECC:
    437 	case ISR_COMPLETED_RETRIES:
    438 	case ISR_COMPLETED_WARNING:
    439 		/*
    440 		 * Copy device config data if appropriate. sc->sc_ed[]
    441 		 * entry might be NULL during probe.
    442 		 */
    443 		if (cmd == CMD_GET_DEV_CONF && sc->sc_ed[devno]) {
    444 			memcpy(sc->sc_ed[devno]->sense_data, sc->status_block,
    445 				sizeof(sc->sc_ed[devno]->sense_data));
    446 		}
    447 
    448 		sc->sc_stat = STAT_DONE;
    449 		break;
    450 
    451 	case ISR_RESET_COMPLETED:
    452 	case ISR_ABORT_COMPLETED:
    453 		/* nothing to do */
    454 		break;
    455 
    456 	case ISR_ATTN_ERROR:
    457 		/*
    458 		 * Basically, this means driver bug or something seriously
    459 		 * hosed. panic rather than extending the lossage.
    460 		 * No status block available, so no further info.
    461 		 */
    462 		panic("%s: dev %d: attention error",
    463 			sc->sc_dev.dv_xname,
    464 			devno);
    465 		/* NOTREACHED */
    466 		break;
    467 
    468 	default:
    469 		if ((sc->sc_flags & DASD_QUIET) == 0)
    470 			edc_dump_status_block(sc, sc->status_block, intr_id);
    471 
    472 		sc->sc_stat = STAT_ERROR;
    473 		break;
    474 	}
    475 
    476 	/*
    477 	 * Unless the interrupt is for Data Transfer Ready or
    478 	 * Attention Error, finish by assertion EOI. This makes
    479 	 * attachment aware the interrupt is processed and system
    480 	 * is ready to accept another one.
    481 	 */
    482 	if (intr_id != ISR_DATA_TRANSFER_RDY && intr_id != ISR_ATTN_ERROR)
    483 		edc_do_attn(sc, ATN_END_INT, devno, intr_id);
    484 
    485 	/* If Read or Write Data, wakeup worker thread to finish it */
    486 	if (intr_id != ISR_DATA_TRANSFER_RDY) {
    487 	    	if (cmd == CMD_READ_DATA || cmd == CMD_WRITE_DATA)
    488 			sc->sc_resblk = sc->status_block[SB_RESBLKCNT_IDX];
    489 		wakeup_one(sc);
    490 	}
    491 
    492 	return (1);
    493 }
    494 
    495 /*
    496  * This follows the exact order for Attention Request as
    497  * written in DASD Storage Interface Specification MC (Rev 2.2).
    498  */
    499 static int
    500 edc_do_attn(sc, attn_type, devno, intr_id)
    501 	struct edc_mca_softc *sc;
    502 	int attn_type, devno, intr_id;
    503 {
    504 	int tries;
    505 
    506 	/* 1. Disable interrupts in BCR. */
    507 	bus_space_write_1(sc->sc_iot, sc->sc_ioh, BCR, 0);
    508 
    509 	/*
    510 	 * 2. Assure NOT BUSY and NO INTERRUPT PENDING, unless acknowledging
    511 	 *    a RESET COMPLETED interrupt.
    512 	 */
    513 	if (intr_id != ISR_RESET_COMPLETED) {
    514 #ifdef EDC_DEBUG
    515 		if (attn_type == ATN_CMD_REQ
    516 		    && (bus_space_read_1(sc->sc_iot, sc->sc_ioh, BSR)
    517 			    & BSR_INT_PENDING))
    518 			panic("%s: edc int pending", sc->sc_dev.dv_xname);
    519 #endif
    520 
    521 		for(tries=1; tries < EDC_ATTN_MAXTRIES; tries++) {
    522 			if ((bus_space_read_1(sc->sc_iot, sc->sc_ioh, BSR)
    523 			     & BSR_BUSY) == 0)
    524 				break;
    525 		}
    526 
    527 		if (tries == EDC_ATTN_MAXTRIES) {
    528 			printf("%s: edc_do_attn: timeout waiting for attachment to become available\n",
    529 					sc->sc_ed[devno]->sc_dev.dv_xname);
    530 			return (EIO);
    531 		}
    532 	}
    533 
    534 	/*
    535 	 * 3. Write proper DEVICE NUMBER and Attention number to ATN.
    536 	 */
    537 	bus_space_write_1(sc->sc_iot, sc->sc_ioh, ATN, attn_type | (devno<<5));
    538 
    539 	/*
    540 	 * 4. Enable interrupts via BCR.
    541 	 */
    542 	bus_space_write_1(sc->sc_iot, sc->sc_ioh, BCR, BCR_INT_ENABLE);
    543 
    544 	return (0);
    545 }
    546 
    547 /*
    548  * Wait until command is processed, timeout after 'secs' seconds.
    549  * We use mono_time, since we don't need actual RTC, just time
    550  * interval.
    551  */
    552 static void
    553 edc_cmd_wait(sc, secs, poll)
    554 	struct edc_mca_softc *sc;
    555 	int secs, poll;
    556 {
    557 	int val;
    558 
    559 	if (!poll) {
    560 		int s;
    561 
    562 		/* Not polling, can sleep. Sleep until we are awakened,
    563 		 * but maximum secs seconds.
    564 		 */
    565 		s = splbio();
    566 		if (sc->sc_stat != STAT_DONE)
    567 			(void) tsleep(sc, PRIBIO, "edcwcmd", secs * hz);
    568 		splx(s);
    569 	}
    570 
    571 	/* Wait until the command is completely finished */
    572 	while((val = bus_space_read_1(sc->sc_iot, sc->sc_ioh, BSR))
    573 	    & BSR_CMD_INPROGRESS) {
    574 		if (poll && (val & BSR_INTR))
    575 			edc_intr(sc);
    576 	}
    577 }
    578 
    579 /*
    580  * Command controller to execute specified command on a device.
    581  */
    582 int
    583 edc_run_cmd(sc, cmd, devno, cmd_args, cmd_len, poll)
    584 	struct edc_mca_softc *sc;
    585 	int cmd;
    586 	int devno;
    587 	u_int16_t cmd_args[];
    588 	int cmd_len, poll;
    589 {
    590 	int i, error, tries;
    591 	u_int16_t cmd0;
    592 
    593 	sc->sc_stat = STAT_START;
    594 
    595 	/* Do Attention Request for Command Request. */
    596 	if ((error = edc_do_attn(sc, ATN_CMD_REQ, devno, 0)))
    597 		return (error);
    598 
    599 	/*
    600 	 * Construct the command. The bits are like this:
    601 	 *
    602 	 * 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0
    603 	 *  \_/   0  0       1 0 \__/   \_____/
    604 	 *    \    \__________/     \         \_ Command Code (see CMD_*)
    605 	 *     \              \      \__ Device: 0 common, 7 controller
    606 	 *      \              \__ Options: reserved, bit 10=cache bypass bit
    607 	 *       \_ Type: 00=2B, 01=4B, 10 and 11 reserved
    608 	 *
    609 	 * We always use device 0 or 1, so difference is made only by Command
    610 	 * Code, Command Options and command length.
    611 	 */
    612 	cmd0 = ((cmd_len == 4) ? (CIFR_LONG_CMD) : 0)
    613 		| (devno <<  5)
    614 		| (cmd_args[0] << 8) | cmd;
    615 	cmd_args[0] = cmd0;
    616 
    617 	/*
    618 	 * Write word of CMD to the CIFR. This sets "Command
    619 	 * Interface Register Full (CMD IN)" in BSR. Once the attachment
    620 	 * detects it, it reads the word and clears CMD IN. This all should
    621 	 * be quite fast, so don't sleep in !poll case neither.
    622 	 */
    623 	for(i=0; i < cmd_len; i++) {
    624 		bus_space_write_2(sc->sc_iot, sc->sc_ioh, CIFR,
    625 			htole16(cmd_args[i]));
    626 
    627 		/* Wait until CMD IN is cleared. */
    628 		tries = 0;
    629 		for(; (bus_space_read_1(sc->sc_iot, sc->sc_ioh, BSR)
    630 		    & BSR_CIFR_FULL) && tries < 10000 ; tries++)
    631 			delay(poll ? 1000 : 1);
    632 			;
    633 
    634 		if (tries == 10000
    635 		    && bus_space_read_1(sc->sc_iot, sc->sc_ioh, BSR)
    636 		       & BSR_CIFR_FULL) {
    637 			printf("%s: device too slow to accept command %d\n",
    638 				sc->sc_dev.dv_xname, cmd);
    639 			return (EIO);
    640 		}
    641 	}
    642 
    643 	/* Wait for command to complete, but maximum 15 seconds. */
    644 	edc_cmd_wait(sc, 15, poll);
    645 
    646 	return ((sc->sc_stat != STAT_DONE) ? EIO : 0);
    647 }
    648 
    649 #ifdef EDC_DEBUG
    650 static const char * const edc_commands[] = {
    651 	"Invalid Command",
    652 	"Read Data",
    653 	"Write Data",
    654 	"Read Verify",
    655 	"Write with Verify",
    656 	"Seek",
    657 	"Park Head",
    658 	"Get Command Complete Status",
    659 	"Get Device Status",
    660 	"Get Device Configuration",
    661 	"Get POS Information",
    662 	"Translate RBA",
    663 	"Write Attachment Buffer",
    664 	"Read Attachment Buffer",
    665 	"Run Diagnostic Test",
    666 	"Get Diagnostic Status Block",
    667 	"Get MFG Header",
    668 	"Format Unit",
    669 	"Format Prepare",
    670 	"Set MAX RBA",
    671 	"Set Power Saving Mode",
    672 	"Power Conservation Command",
    673 };
    674 
    675 static const char * const edc_cmd_status[256] = {
    676 	"Reserved",
    677 	"Command completed successfully",
    678 	"Reserved",
    679 	"Command completed successfully with ECC applied",
    680 	"Reserved",
    681 	"Command completed successfully with retries",
    682 	"Format Command partially completed",	/* Status available */
    683 	"Command completed successfully with ECC and retries",
    684 	"Command completed with Warning", 	/* Command Error is available */
    685 	"Aborted",
    686 	"Reset completed",
    687 	"Data Transfer Ready",		/* No Status Block available */
    688 	"Command terminated with failure",	/* Device Error is available */
    689 	"DMA Error",			/* Retry entire command as recovery */
    690 	"Command Block Error",
    691 	"Attention Error (Illegal Attention Code)",
    692 	/* 0x14 - 0xff reserved */
    693 };
    694 
    695 static const char * const edc_cmd_error[256] = {
    696 	"No Error",
    697 	"Invalid parameter in the command block",
    698 	"Reserved",
    699 	"Command not supported",
    700 	"Command Aborted per request",
    701 	"Reserved",
    702 	"Command rejected",	/* Attachment diagnostic failure */
    703 	"Format Rejected",	/* Prepare Format command is required */
    704 	"Format Error (Primary Map is not readable)",
    705 	"Format Error (Secondary map is not readable)",
    706 	"Format Error (Diagnostic Failure)",
    707 	"Format Warning (Secondary Map Overflow)",
    708 	"Reserved"
    709 	"Format Error (Host Checksum Error)",
    710 	"Reserved",
    711 	"Format Warning (Push table overflow)",
    712 	"Format Warning (More pushes than allowed)",
    713 	"Reserved",
    714 	"Format Warning (Error during verifying)",
    715 	"Invalid device number for the command",
    716 	/* 0x14-0xff reserved */
    717 };
    718 
    719 static const char * const edc_dev_errors[] = {
    720 	"No Error",
    721 	"Seek Fault",	/* Device report */
    722 	"Interface Fault (Parity, Attn, or Cmd Complete Error)",
    723 	"Block not found (ID not found)",
    724 	"Block not found (AM not found)",
    725 	"Data ECC Error (hard error)",
    726 	"ID CRC Error",
    727 	"RBA Out of Range",
    728 	"Reserved",
    729 	"Defective Block",
    730 	"Reserved",
    731 	"Selection Error",
    732 	"Reserved",
    733 	"Write Fault",
    734 	"No index or sector pulse",
    735 	"Device Not Ready",
    736 	"Seek Error",	/* Attachment report */
    737 	"Bad Format",
    738 	"Volume Overflow",
    739 	"No Data AM Found",
    740 	"Block not found (No ID AM or ID CRC error occurred)",
    741 	"Reserved",
    742 	"Reserved",
    743 	"No ID found on track (ID search)",
    744 	/* 0x19 - 0xff reserved */
    745 };
    746 #endif /* EDC_DEBUG */
    747 
    748 static void
    749 edc_dump_status_block(sc, status_block, intr_id)
    750 	struct edc_mca_softc *sc;
    751 	u_int16_t *status_block;
    752 	int intr_id;
    753 {
    754 #ifdef EDC_DEBUG
    755 	printf("%s: Command: %s, Status: %s (intr %d)\n",
    756 		sc->sc_dev.dv_xname,
    757 		edc_commands[status_block[0] & 0x1f],
    758 		edc_cmd_status[SB_GET_CMD_STATUS(status_block)],
    759 		intr_id
    760 		);
    761 #else
    762 	printf("%s: Command: %d, Status: %d (intr %d)\n",
    763 		sc->sc_dev.dv_xname,
    764 		status_block[0] & 0x1f,
    765 		SB_GET_CMD_STATUS(status_block),
    766 		intr_id
    767 		);
    768 #endif
    769 	printf("%s: # left blocks: %u, last processed RBA: %u\n",
    770 		sc->sc_dev.dv_xname,
    771 		status_block[SB_RESBLKCNT_IDX],
    772 		(status_block[5] << 16) | status_block[4]);
    773 
    774 	if (intr_id == ISR_COMPLETED_WARNING) {
    775 #ifdef EDC_DEBUG
    776 		printf("%s: Command Error Code: %s\n",
    777 			sc->sc_dev.dv_xname,
    778 			edc_cmd_error[status_block[1] & 0xff]);
    779 #else
    780 		printf("%s: Command Error Code: %d\n",
    781 			sc->sc_dev.dv_xname,
    782 			status_block[1] & 0xff);
    783 #endif
    784 	}
    785 
    786 	if (intr_id == ISR_CMD_FAILED) {
    787 #ifdef EDC_DEBUG
    788 		char buf[100];
    789 
    790 		printf("%s: Device Error Code: %s\n",
    791 			sc->sc_dev.dv_xname,
    792 			edc_dev_errors[status_block[2] & 0xff]);
    793 		bitmask_snprintf((status_block[2] & 0xff00) >> 8,
    794 			"\20"
    795 			"\01SeekOrCmdComplete"
    796 			"\02Track0Flag"
    797 			"\03WriteFault"
    798 			"\04Selected"
    799 			"\05Ready"
    800 			"\06Reserved0"
    801 			"\07STANDBY"
    802 			"\010Reserved0",
    803 			buf, sizeof(buf));
    804 		printf("%s: Device Status: %s\n",
    805 			sc->sc_dev.dv_xname, buf);
    806 #else
    807 		printf("%s: Device Error Code: %d, Device Status: %d\n",
    808 			sc->sc_dev.dv_xname,
    809 			status_block[2] & 0xff,
    810 			(status_block[2] & 0xff00) >> 8);
    811 #endif
    812 	}
    813 }
    814 
    815 static void
    816 edc_spawn_worker(arg)
    817 	void *arg;
    818 {
    819 	struct edc_mca_softc *sc = (struct edc_mca_softc *) arg;
    820 	int error;
    821 	struct proc *wrk;
    822 
    823 	/* Now, everything is ready, start a kthread */
    824 	if ((error = kthread_create1(edcworker, sc, &wrk,
    825 			"%s", sc->sc_dev.dv_xname))) {
    826 		printf("%s: cannot spawn worker thread: errno=%d\n",
    827 			sc->sc_dev.dv_xname, error);
    828 		panic("edc_spawn_worker");
    829 	}
    830 }
    831 
    832 /*
    833  * Main worker thread function.
    834  */
    835 void
    836 edcworker(arg)
    837 	void *arg;
    838 {
    839 	struct edc_mca_softc *sc = (struct edc_mca_softc *) arg;
    840 	struct ed_softc *ed;
    841 	struct buf *bp;
    842 	int i, error;
    843 
    844 	config_pending_decr();
    845 
    846 	for(;;) {
    847 		/* Wait until awakened */
    848 		(void) tsleep(sc, PRIBIO, "edcidle", 0);
    849 
    850 		for(i=0; i<sc->sc_maxdevs; ) {
    851 			if ((ed = sc->sc_ed[i]) == NULL) {
    852 				i++;
    853 				continue;
    854 			}
    855 
    856 			/* Is there a buf for us ? */
    857 			simple_lock(&ed->sc_q_lock);
    858 			if ((bp = BUFQ_GET(&ed->sc_q)) == NULL) {
    859 				simple_unlock(&ed->sc_q_lock);
    860 				i++;
    861 				continue;
    862 			}
    863 			simple_unlock(&ed->sc_q_lock);
    864 
    865 			/* Instrumentation. */
    866 			disk_busy(&ed->sc_dk);
    867 
    868 			error = edc_bio(sc, ed, bp->b_data, bp->b_bcount,
    869 				bp->b_rawblkno, (bp->b_flags & B_READ), 0);
    870 
    871 			if (error) {
    872 				bp->b_error = error;
    873 				bp->b_flags |= B_ERROR;
    874 			} else {
    875 				/* Set resid, most commonly to zero. */
    876 				bp->b_resid = sc->sc_resblk * DEV_BSIZE;
    877 			}
    878 
    879 			disk_unbusy(&ed->sc_dk, (bp->b_bcount - bp->b_resid),
    880 			    (bp->b_flags & B_READ));
    881 #if NRND > 0
    882 			rnd_add_uint32(&ed->rnd_source, bp->b_blkno);
    883 #endif
    884 			biodone(bp);
    885 		}
    886 	}
    887 }
    888 
    889 int
    890 edc_bio(struct edc_mca_softc *sc, struct ed_softc *ed, void *data,
    891 	size_t bcount, daddr_t rawblkno, int isread, int poll)
    892 {
    893 	u_int16_t cmd_args[4];
    894 	int error=0, fl;
    895 	u_int16_t track;
    896 	u_int16_t cyl;
    897 	u_int8_t head;
    898 	u_int8_t sector;
    899 
    900 	mca_disk_busy();
    901 
    902 	/* set WAIT and R/W flag appropriately for the DMA transfer */
    903 	fl = ((poll) ? BUS_DMA_NOWAIT : BUS_DMA_WAITOK)
    904 		| ((isread) ? BUS_DMA_READ : BUS_DMA_WRITE);
    905 
    906 	/* Load the buffer for DMA transfer. */
    907 	if ((error = bus_dmamap_load(sc->sc_dmat, sc->sc_dmamap_xfer, data,
    908 	    bcount, NULL, BUS_DMA_STREAMING|fl))) {
    909 		printf("%s: ed_bio: unable to load DMA buffer - error %d\n",
    910 			ed->sc_dev.dv_xname, error);
    911 		goto out;
    912 	}
    913 
    914 	bus_dmamap_sync(sc->sc_dmat, sc->sc_dmamap_xfer, 0,
    915 		bcount, (isread) ? BUS_DMASYNC_PREREAD : BUS_DMASYNC_PREWRITE);
    916 
    917 	track = rawblkno / ed->sectors;
    918 	head = track % ed->heads;
    919 	cyl = track / ed->heads;
    920 	sector = rawblkno % ed->sectors;
    921 
    922 	/* Read or Write Data command */
    923 	cmd_args[0] = 2;	/* Options 0000010 */
    924 	cmd_args[1] = bcount / DEV_BSIZE;
    925 	cmd_args[2] = ((cyl & 0x1f) << 11) | (head << 5) | sector;
    926 	cmd_args[3] = ((cyl & 0x3E0) >> 5);
    927 	error = edc_run_cmd(sc,
    928 			(isread) ? CMD_READ_DATA : CMD_WRITE_DATA,
    929 			ed->sc_devno, cmd_args, 4, poll);
    930 
    931 	/* Sync the DMA memory */
    932 	if (!error)  {
    933 		bus_dmamap_sync(sc->sc_dmat, sc->sc_dmamap_xfer, 0, bcount,
    934 			(isread)? BUS_DMASYNC_POSTREAD : BUS_DMASYNC_POSTWRITE);
    935 	}
    936 
    937 	/* We are done, unload buffer from DMA map */
    938 	bus_dmamap_unload(sc->sc_dmat, sc->sc_dmamap_xfer);
    939 
    940     out:
    941 	mca_disk_unbusy();
    942 
    943 	return (error);
    944 }
    945