xref: /netbsd-src/sys/dev/ic/sunscpal.c (revision c7fb772b85b2b5d4cfb282f868f454b4701534fd)
1 /*	$NetBSD: sunscpal.c,v 1.29 2021/08/07 16:19:12 thorpej Exp $	*/
2 
3 /*
4  * Copyright (c) 2001 Matthew Fredette
5  * Copyright (c) 1995 David Jones, Gordon W. Ross
6  * Copyright (c) 1994 Jarle Greipsland
7  * All rights reserved.
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. The name of the authors may not be used to endorse or promote products
18  *    derived from this software without specific prior written permission.
19  * 4. All advertising materials mentioning features or use of this software
20  *    must display the following acknowledgement:
21  *      This product includes software developed by
22  *      David Jones and Gordon Ross
23  *
24  * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``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 AUTHORS 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  * This is a machine-independent driver for the Sun "sc"
38  * SCSI Bus Controller (SBC).
39  *
40  * This code should work with any memory-mapped card,
41  * and can be shared by multiple adapters that address
42  * the card with different register offset spacings.
43  * (This can happen on the atari, for example.)
44  *
45  * Credits, history:
46  *
47  * Matthew Fredette completely copied revision 1.38 of
48  * ncr5380sbc.c, and then heavily modified it to match
49  * the Sun sc PAL.  The remaining credits are for
50  * ncr5380sbc.c:
51  *
52  * David Jones is the author of most of the code that now
53  * appears in this file, and was the architect of the
54  * current overall structure (MI/MD code separation, etc.)
55  *
56  * Gordon Ross integrated the message phase code, added lots of
57  * comments about what happens when and why (re. SCSI spec.),
58  * debugged some reentrance problems, and added several new
59  * "hooks" needed for the Sun3 "si" adapters.
60  *
61  * The message in/out code was taken nearly verbatim from
62  * the aic6360 driver by Jarle Greipsland.
63  *
64  * Several other NCR5380 drivers were used for reference
65  * while developing this driver, including work by:
66  *   The Alice Group (mac68k port) namely:
67  *       Allen K. Briggs, Chris P. Caputo, Michael L. Finch,
68  *       Bradley A. Grantham, and Lawrence A. Kesteloot
69  *   Michael L. Hitch (amiga drivers: sci.c)
70  *   Leo Weppelman (atari driver: ncr5380.c)
71  * There are others too.  Thanks, everyone.
72  *
73  * Transliteration to bus_space() performed 9/17/98 by
74  * John Ruschmeyer (jruschme@exit109.com) for i386 'nca' driver.
75  * Thank you all.
76  */
77 
78 #include <sys/cdefs.h>
79 __KERNEL_RCSID(0, "$NetBSD: sunscpal.c,v 1.29 2021/08/07 16:19:12 thorpej Exp $");
80 
81 #include "opt_ddb.h"
82 
83 #include <sys/param.h>
84 #include <sys/systm.h>
85 #include <sys/kernel.h>
86 #include <sys/errno.h>
87 #include <sys/malloc.h>
88 #include <sys/device.h>
89 #include <sys/buf.h>
90 #include <sys/proc.h>
91 
92 #include <dev/scsipi/scsi_all.h>
93 #include <dev/scsipi/scsipi_all.h>
94 #include <dev/scsipi/scsipi_debug.h>
95 #include <dev/scsipi/scsi_message.h>
96 #include <dev/scsipi/scsiconf.h>
97 
98 #ifdef DDB
99 #include <ddb/db_output.h>
100 #endif
101 
102 #include <dev/ic/sunscpalreg.h>
103 #include <dev/ic/sunscpalvar.h>
104 
105 static void	sunscpal_reset_scsibus(struct sunscpal_softc *);
106 static void	sunscpal_sched(struct sunscpal_softc *);
107 static void	sunscpal_done(struct sunscpal_softc *);
108 
109 static int	sunscpal_select(struct sunscpal_softc *, struct sunscpal_req *);
110 static void	sunscpal_reselect(struct sunscpal_softc *);
111 
112 static int	sunscpal_msg_in(struct sunscpal_softc *);
113 static int	sunscpal_msg_out(struct sunscpal_softc *);
114 static int	sunscpal_data_xfer(struct sunscpal_softc *, int);
115 static int	sunscpal_command(struct sunscpal_softc *);
116 static int	sunscpal_status(struct sunscpal_softc *);
117 static void	sunscpal_machine(struct sunscpal_softc *);
118 
119 void	sunscpal_abort(struct sunscpal_softc *);
120 void	sunscpal_cmd_timeout(void *);
121 /*
122  * Action flags returned by the info_transfer functions:
123  * (These determine what happens next.)
124  */
125 #define ACT_CONTINUE	0x00	/* No flags: expect another phase */
126 #define ACT_DISCONNECT	0x01	/* Target is disconnecting */
127 #define ACT_CMD_DONE	0x02	/* Need to call scsipi_done() */
128 #define ACT_RESET_BUS	0x04	/* Need bus reset (cmd timeout) */
129 #define ACT_WAIT_DMA	0x10	/* Wait for DMA to complete */
130 
131 /*****************************************************************
132  * Debugging stuff
133  *****************************************************************/
134 
135 #ifndef DDB
136 /* This is used only in recoverable places. */
137 #ifndef Debugger
138 #define Debugger() printf("Debug: sunscpal.c:%d\n", __LINE__)
139 #endif
140 #endif
141 
142 #ifdef	SUNSCPAL_DEBUG
143 
144 #define	SUNSCPAL_DBG_BREAK	1
145 #define	SUNSCPAL_DBG_CMDS	2
146 #define	SUNSCPAL_DBG_DMA	4
147 int sunscpal_debug = 0;
148 #define	SUNSCPAL_BREAK() \
149 	do { if (sunscpal_debug & SUNSCPAL_DBG_BREAK) Debugger(); } while (0)
150 static void sunscpal_show_scsi_cmd(struct scsipi_xfer *);
151 #ifdef DDB
152 void	sunscpal_clear_trace(void);
153 void	sunscpal_show_trace(void);
154 void	sunscpal_show_req(struct sunscpal_req *);
155 void	sunscpal_show_state(void);
156 #endif	/* DDB */
157 #else	/* SUNSCPAL_DEBUG */
158 
159 #define	SUNSCPAL_BREAK() 		/* nada */
160 #define sunscpal_show_scsi_cmd(xs) /* nada */
161 
162 #endif	/* SUNSCPAL_DEBUG */
163 
164 static const char *
165 phase_names[8] = {
166 	"DATA_OUT",
167 	"DATA_IN",
168 	"COMMAND",
169 	"STATUS",
170 	"UNSPEC1",
171 	"UNSPEC2",
172 	"MSG_OUT",
173 	"MSG_IN",
174 };
175 
176 #ifdef SUNSCPAL_USE_BUS_DMA
177 static void sunscpal_dma_alloc(struct sunscpal_softc *);
178 static void sunscpal_dma_free(struct sunscpal_softc *);
179 static void sunscpal_dma_setup(struct sunscpal_softc *);
180 #else
181 #define sunscpal_dma_alloc(sc) (*sc->sc_dma_alloc)(sc)
182 #define sunscpal_dma_free(sc) (*sc->sc_dma_free)(sc)
183 #define sunscpal_dma_setup(sc) (*sc->sc_dma_setup)(sc)
184 #endif
185 static void sunscpal_minphys(struct buf *);
186 
187 /*****************************************************************
188  * Actual chip control
189  *****************************************************************/
190 
191 /*
192  * XXX: These timeouts might need to be tuned...
193  */
194 
195 /* This one is used when waiting for a phase change. (X100uS.) */
196 int sunscpal_wait_phase_timo = 1000 * 10 * 300;	/* 5 min. */
197 
198 /* These are used in the following inline functions. */
199 int sunscpal_wait_req_timo = 1000 * 50;	/* X2 = 100 mS. */
200 int sunscpal_wait_nrq_timo = 1000 * 25;	/* X2 =  50 mS. */
201 
202 static inline int sunscpal_wait_req(struct sunscpal_softc *);
203 static inline int sunscpal_wait_not_req(struct sunscpal_softc *);
204 static inline void sunscpal_sched_msgout(struct sunscpal_softc *, int);
205 
206 /* Return zero on success. */
sunscpal_wait_req(struct sunscpal_softc * sc)207 static inline int sunscpal_wait_req(struct sunscpal_softc *sc)
208 {
209 	int timo = sunscpal_wait_req_timo;
210 
211 	for (;;) {
212 		if (SUNSCPAL_READ_2(sc, sunscpal_icr) & SUNSCPAL_ICR_REQUEST) {
213 			timo = 0;	/* return 0 */
214 			break;
215 		}
216 		if (--timo < 0)
217 			break;	/* return -1 */
218 		delay(2);
219 	}
220 	return timo;
221 }
222 
223 /* Return zero on success. */
sunscpal_wait_not_req(struct sunscpal_softc * sc)224 static inline int sunscpal_wait_not_req(struct sunscpal_softc *sc)
225 {
226 	int timo = sunscpal_wait_nrq_timo;
227 
228 	for (;;) {
229 		if ((SUNSCPAL_READ_2(sc, sunscpal_icr) &
230 		    SUNSCPAL_ICR_REQUEST) == 0) {
231 			timo = 0;	/* return 0 */
232 			break;
233 		}
234 		if (--timo < 0)
235 			break;	/* return -1 */
236 		delay(2);
237 	}
238 	return timo;
239 }
240 
241 /*
242  * These functions control DMA functions in the chipset independent of
243  * the host DMA implementation.
244  */
245 static void sunscpal_dma_start(struct sunscpal_softc *);
246 static void sunscpal_dma_poll(struct sunscpal_softc *);
247 static void sunscpal_dma_stop(struct sunscpal_softc *);
248 
249 static void
sunscpal_dma_start(struct sunscpal_softc * sc)250 sunscpal_dma_start(struct sunscpal_softc *sc)
251 {
252 	struct sunscpal_req *sr = sc->sc_current;
253 	int xlen;
254 	uint16_t icr;
255 
256 	xlen = sc->sc_reqlen;
257 
258 	/* Let'er rip! */
259 	icr = SUNSCPAL_READ_2(sc, sunscpal_icr);
260 	icr |= SUNSCPAL_ICR_DMA_ENABLE |
261 	    ((xlen & 1) ? 0 : SUNSCPAL_ICR_WORD_MODE) |
262 	    ((sr->sr_flags & SR_IMMED) ? 0 : SUNSCPAL_ICR_INTERRUPT_ENABLE);
263 	SUNSCPAL_WRITE_2(sc, sunscpal_icr, icr);
264 
265 	sc->sc_state |= SUNSCPAL_DOINGDMA;
266 
267 #ifdef	SUNSCPAL_DEBUG
268 	if (sunscpal_debug & SUNSCPAL_DBG_DMA) {
269 		printf("%s: started, flags=0x%x\n",
270 		    __func__, sc->sc_state);
271 	}
272 #endif
273 }
274 
275 #define	ICR_MASK (SUNSCPAL_ICR_PARITY_ERROR | SUNSCPAL_ICR_BUS_ERROR | SUNSCPAL_ICR_INTERRUPT_REQUEST)
276 #define	POLL_TIMO	50000	/* X100 = 5 sec. */
277 
278 /*
279  * Poll (spin-wait) for DMA completion.
280  * Called right after xx_dma_start(), and
281  * xx_dma_stop() will be called next.
282  */
283 static void
sunscpal_dma_poll(struct sunscpal_softc * sc)284 sunscpal_dma_poll(struct sunscpal_softc *sc)
285 {
286 	struct sunscpal_req *sr = sc->sc_current;
287 	int tmo;
288 
289 	/* Make sure DMA started successfully. */
290 	if (sc->sc_state & SUNSCPAL_ABORTING)
291 		return;
292 
293 	/* Wait for any "DMA complete" or error bits. */
294 	tmo = POLL_TIMO;
295 	for (;;) {
296 		if (SUNSCPAL_READ_2(sc, sunscpal_icr) & ICR_MASK)
297 			break;
298 		if (--tmo <= 0) {
299 			printf("sc: DMA timeout (while polling)\n");
300 			/* Indicate timeout as MI code would. */
301 			sr->sr_flags |= SR_OVERDUE;
302 			break;
303 		}
304 		delay(100);
305 	}
306 	SUNSCPAL_TRACE("sunscpal_dma_poll: waited %d\n", POLL_TIMO - tmo);
307 
308 #ifdef	SUNSCPAL_DEBUG
309 	if (sunscpal_debug & SUNSCPAL_DBG_DMA) {
310 		char buffer[64];
311 		snprintb(buffer, sizeof(buffer),
312 		    SUNSCPAL_READ_2(sc, sunscpal_icr), SUNSCPAL_ICR_BITS);
313 		printf("%s: done, icr=%s\n", __func__, buffer);
314 	}
315 #endif
316 }
317 
318 static void
sunscpal_dma_stop(struct sunscpal_softc * sc)319 sunscpal_dma_stop(struct sunscpal_softc *sc)
320 {
321 	struct sunscpal_req *sr = sc->sc_current;
322 	struct scsipi_xfer *xs = sr->sr_xs;
323 	int resid, ntrans;
324 	uint16_t icr;
325 
326 	if ((sc->sc_state & SUNSCPAL_DOINGDMA) == 0) {
327 #ifdef	DEBUG
328 		printf("%s: DMA not running\n", __func__);
329 #endif
330 		return;
331 	}
332 	sc->sc_state &= ~SUNSCPAL_DOINGDMA;
333 
334 	/* First, halt the DMA engine. */
335 	icr = SUNSCPAL_READ_2(sc, sunscpal_icr);
336 	icr &= ~(SUNSCPAL_ICR_DMA_ENABLE | SUNSCPAL_ICR_WORD_MODE |
337 	    SUNSCPAL_ICR_INTERRUPT_ENABLE);
338 	SUNSCPAL_WRITE_2(sc, sunscpal_icr, icr);
339 
340 #ifdef	SUNSCPAL_USE_BUS_DMA
341 	/*
342 	 * XXX - this function is supposed to be independent of
343 	 * the host's DMA implementation.
344 	 */
345  {
346 	 sunscpal_dma_handle_t dh = sr->sr_dma_hand;
347 
348 	 /* sync the DMA map: */
349 	 bus_dmamap_sync(sc->sunscpal_dmat, dh->dh_dmamap, 0, dh->dh_maplen,
350 	     ((xs->xs_control & XS_CTL_DATA_OUT) == 0 ?
351 	    BUS_DMASYNC_POSTREAD : BUS_DMASYNC_POSTWRITE));
352  }
353 #endif /* SUNSCPAL_USE_BUS_DMA */
354 
355 
356 	if (icr & (SUNSCPAL_ICR_BUS_ERROR)) {
357 		char buffer[64];
358 		snprintb(buffer, sizeof(buffer), SUNSCPAL_ICR_BITS, icr);
359 		printf("sc: DMA error, icr=%s, reset\n", buffer);
360 		sr->sr_xs->error = XS_DRIVER_STUFFUP;
361 		sc->sc_state |= SUNSCPAL_ABORTING;
362 		goto out;
363 	}
364 
365 	/* Note that timeout may have set the error flag. */
366 	if (sc->sc_state & SUNSCPAL_ABORTING)
367 		goto out;
368 
369 	/* XXX: Wait for DMA to actually finish? */
370 
371 	/*
372 	 * Now try to figure out how much actually transferred
373 	 */
374 
375 	resid = SUNSCPAL_DMA_COUNT_FLIP(SUNSCPAL_READ_2(sc,
376 	    sunscpal_dma_count));
377 	ntrans = sc->sc_reqlen - resid;
378 
379 #ifdef	SUNSCPAL_DEBUG
380 	if (sunscpal_debug & SUNSCPAL_DBG_DMA) {
381 		printf("%s: resid=0x%x ntrans=0x%x\n",
382 		    __func__, resid, ntrans);
383 	}
384 #endif
385 
386 	if (ntrans < sc->sc_min_dma_len) {
387 		printf("sc: DMA count: 0x%x\n", resid);
388 		sc->sc_state |= SUNSCPAL_ABORTING;
389 		goto out;
390 	}
391 	if (ntrans > sc->sc_datalen)
392 		panic("%s: excess transfer", __func__);
393 
394 	/* Adjust data pointer */
395 	sc->sc_dataptr += ntrans;
396 	sc->sc_datalen -= ntrans;
397 
398 	/*
399 	 * After a read, we may need to clean-up
400 	 * "Left-over bytes" (yuck!)
401 	 */
402 	if (((xs->xs_control & XS_CTL_DATA_OUT) == 0) &&
403 	    ((icr & SUNSCPAL_ICR_ODD_LENGTH) != 0)) {
404 #ifdef DEBUG
405 		printf("sc: Got Left-over bytes!\n");
406 #endif
407 		*(sc->sc_dataptr++) = SUNSCPAL_READ_1(sc, sunscpal_data);
408 		sc->sc_datalen--;
409 	}
410 
411  out:
412 	SUNSCPAL_WRITE_2(sc, sunscpal_dma_count, SUNSCPAL_DMA_COUNT_FLIP(0));
413 
414 }
415 
416 /* Ask the target for a MSG_OUT phase. */
417 static inline void
sunscpal_sched_msgout(struct sunscpal_softc * sc,int msg_code)418 sunscpal_sched_msgout(struct sunscpal_softc *sc, int msg_code)
419 {
420 	/*
421 	 * This controller does not allow you to assert ATN, which
422 	 * will eventually leave us with no option other than to reset
423 	 * the bus.  We keep this function as a placeholder, though,
424 	 * and this printf will eventually go away or get #ifdef'ed:
425 	 */
426 	printf("%s: trying to schedule 0x%0x\n", __func__, msg_code);
427 	sc->sc_msgpriq |= msg_code;
428 }
429 
430 int
sunscpal_pio_out(struct sunscpal_softc * sc,int phase,int count,uint8_t * data)431 sunscpal_pio_out(struct sunscpal_softc *sc, int phase, int count, uint8_t *data)
432 {
433 	int resid;
434 
435 	resid = count;
436 	while (resid > 0) {
437 		if (!SUNSCPAL_BUSY(sc)) {
438 			SUNSCPAL_TRACE("pio_out: lost BSY, resid=%d\n", resid);
439 			break;
440 		}
441 		if (sunscpal_wait_req(sc)) {
442 			SUNSCPAL_TRACE("pio_out: no REQ, resid=%d\n", resid);
443 			break;
444 		}
445 		if (SUNSCPAL_BUS_PHASE(SUNSCPAL_READ_2(sc, sunscpal_icr)) !=
446 		    phase)
447 			break;
448 
449 		/* Put the data on the bus. */
450 		if (data) {
451 			SUNSCPAL_BYTE_WRITE(sc, phase, *data++);
452 		} else {
453 			SUNSCPAL_BYTE_WRITE(sc, phase, 0);
454 		}
455 
456 		--resid;
457 	}
458 
459 	return count - resid;
460 }
461 
462 
463 int
sunscpal_pio_in(struct sunscpal_softc * sc,int phase,int count,uint8_t * data)464 sunscpal_pio_in(struct sunscpal_softc *sc, int phase, int count, uint8_t *data)
465 {
466 	int resid;
467 
468 	resid = count;
469 	while (resid > 0) {
470 		if (!SUNSCPAL_BUSY(sc)) {
471 			SUNSCPAL_TRACE("pio_in: lost BSY, resid=%d\n", resid);
472 			break;
473 		}
474 		if (sunscpal_wait_req(sc)) {
475 			SUNSCPAL_TRACE("pio_in: no REQ, resid=%d\n", resid);
476 			break;
477 		}
478 		/* A phase change is not valid until AFTER REQ rises! */
479 		if (SUNSCPAL_BUS_PHASE(SUNSCPAL_READ_2(sc, sunscpal_icr)) !=
480 		    phase)
481 			break;
482 
483 		/* Read the data bus. */
484 		if (data)
485 			*data++ = SUNSCPAL_BYTE_READ(sc, phase);
486 		else
487 			(void)SUNSCPAL_BYTE_READ(sc, phase);
488 
489 		--resid;
490 	}
491 
492 	return count - resid;
493 }
494 
495 
496 void
sunscpal_init(struct sunscpal_softc * sc)497 sunscpal_init(struct sunscpal_softc *sc)
498 {
499 	int i, j;
500 
501 #ifdef	SUNSCPAL_DEBUG
502 	sunscpal_debug_sc = sc;
503 #endif
504 
505 	for (i = 0; i < SUNSCPAL_OPENINGS; i++)
506 		sc->sc_ring[i].sr_xs = NULL;
507 	for (i = 0; i < 8; i++)
508 		for (j = 0; j < 8; j++)
509 			sc->sc_matrix[i][j] = NULL;
510 
511 	sc->sc_prevphase = SUNSCPAL_PHASE_INVALID;
512 	sc->sc_state = SUNSCPAL_IDLE;
513 
514 	SUNSCPAL_WRITE_2(sc, sunscpal_icr, 0);
515 	SUNSCPAL_WRITE_2(sc, sunscpal_dma_addr_h, 0);
516 	SUNSCPAL_WRITE_2(sc, sunscpal_dma_addr_l, 0);
517 	SUNSCPAL_WRITE_2(sc, sunscpal_dma_count, SUNSCPAL_DMA_COUNT_FLIP(0));
518 
519 	SUNSCPAL_CLR_INTR(sc);
520 
521 	/* Another hack (Er.. hook!) for anything that needs it: */
522 	if (sc->sc_intr_on) {
523 		SUNSCPAL_TRACE("init: intr ON\n", 0);
524 		sc->sc_intr_on(sc);
525 	}
526 }
527 
528 
529 static void
sunscpal_reset_scsibus(struct sunscpal_softc * sc)530 sunscpal_reset_scsibus(struct sunscpal_softc *sc)
531 {
532 
533 	SUNSCPAL_TRACE("reset_scsibus, cur=0x%x\n", (long)sc->sc_current);
534 
535 	SUNSCPAL_WRITE_2(sc, sunscpal_icr, SUNSCPAL_ICR_RESET);
536 	delay(500);
537 	SUNSCPAL_WRITE_2(sc, sunscpal_icr, 0);
538 
539 	SUNSCPAL_CLR_INTR(sc);
540 	/* XXX - Need long delay here! */
541 	delay(100000);
542 
543 	/* XXX - Need to cancel disconnected requests. */
544 }
545 
546 
547 /*
548  * Interrupt handler for the SCSI Bus Controller (SBC)
549  * This may also called for a DMA timeout (at splbio).
550  */
551 int
sunscpal_intr(void * arg)552 sunscpal_intr(void *arg)
553 {
554 	struct sunscpal_softc *sc = arg;
555 	int claimed = 0;
556 
557 	/*
558 	 * Do not touch SBC regs here unless sc_current == NULL
559 	 * or it will complain about "register conflict" errors.
560 	 * Instead, just let sunscpal_machine() deal with it.
561 	 */
562 	SUNSCPAL_TRACE("intr: top, state=%d\n", sc->sc_state);
563 
564 	if (sc->sc_state == SUNSCPAL_IDLE) {
565 		/*
566 		 * Might be reselect.  sunscpal_reselect() will check,
567 		 * and set up the connection if so.  This will verify
568 		 * that sc_current == NULL at the beginning...
569 		 */
570 
571 		/* Another hack (Er.. hook!) for anything that needs it: */
572 		if (sc->sc_intr_off) {
573 			SUNSCPAL_TRACE("intr: for reselect, intr off\n", 0);
574 		    sc->sc_intr_off(sc);
575 		}
576 
577 		sunscpal_reselect(sc);
578 	}
579 
580 	/*
581 	 * The remaining documented interrupt causes are a DMA complete
582 	 * condition.
583 	 *
584 	 * The procedure is to let sunscpal_machine() figure out what
585 	 * to do next.
586 	 */
587 	if (sc->sc_state & SUNSCPAL_WORKING) {
588 		SUNSCPAL_TRACE("intr: call machine, cur=0x%x\n",
589 		    (long)sc->sc_current);
590 		/* This will usually free-up the nexus. */
591 		sunscpal_machine(sc);
592 		SUNSCPAL_TRACE("intr: machine done, cur=0x%x\n",
593 		    (long)sc->sc_current);
594 		claimed = 1;
595 	}
596 
597 	/* Maybe we can run some commands now... */
598 	if (sc->sc_state == SUNSCPAL_IDLE) {
599 		SUNSCPAL_TRACE("intr: call sched, cur=0x%x\n",
600 		    (long)sc->sc_current);
601 		sunscpal_sched(sc);
602 		SUNSCPAL_TRACE("intr: sched done, cur=0x%x\n",
603 		    (long)sc->sc_current);
604 	}
605 
606 	return claimed;
607 }
608 
609 
610 /*
611  * Abort the current command (i.e. due to timeout)
612  */
613 void
sunscpal_abort(struct sunscpal_softc * sc)614 sunscpal_abort(struct sunscpal_softc *sc)
615 {
616 
617 	/*
618 	 * Finish it now.  If DMA is in progress, we
619 	 * can not call sunscpal_sched_msgout() because
620 	 * that hits the SBC (avoid DMA conflict).
621 	 */
622 
623 	/* Another hack (Er.. hook!) for anything that needs it: */
624 	if (sc->sc_intr_off) {
625 		SUNSCPAL_TRACE("abort: intr off\n", 0);
626 		sc->sc_intr_off(sc);
627 	}
628 
629 	sc->sc_state |= SUNSCPAL_ABORTING;
630 	if ((sc->sc_state & SUNSCPAL_DOINGDMA) == 0) {
631 		sunscpal_sched_msgout(sc, SEND_ABORT);
632 	}
633 	SUNSCPAL_TRACE("abort: call machine, cur=0x%x\n",
634 	    (long)sc->sc_current);
635 	sunscpal_machine(sc);
636 	SUNSCPAL_TRACE("abort: machine done, cur=0x%x\n",
637 	    (long)sc->sc_current);
638 
639 	/* Another hack (Er.. hook!) for anything that needs it: */
640 	if (sc->sc_intr_on) {
641 		SUNSCPAL_TRACE("abort: intr ON\n", 0);
642 		sc->sc_intr_on(sc);
643 	}
644 }
645 
646 /*
647  * Timeout handler, scheduled for each SCSI command.
648  */
649 void
sunscpal_cmd_timeout(void * arg)650 sunscpal_cmd_timeout(void *arg)
651 {
652 	struct sunscpal_req *sr = arg;
653 	struct scsipi_xfer *xs;
654 	struct scsipi_periph *periph;
655 	struct sunscpal_softc *sc;
656 	int s;
657 
658 	s = splbio();
659 
660 	/* Get all our variables... */
661 	xs = sr->sr_xs;
662 	if (xs == NULL) {
663 		printf("%s: no scsipi_xfer\n", __func__);
664 		goto out;
665 	}
666 	periph = xs->xs_periph;
667 	sc = device_private(periph->periph_channel->chan_adapter->adapt_dev);
668 
669 	printf("%s: cmd timeout, targ=%d, lun=%d\n",
670 	    device_xname(sc->sc_dev),
671 	    sr->sr_target, sr->sr_lun);
672 
673 	/*
674 	 * Mark the overdue job as failed, and arrange for
675 	 * sunscpal_machine to terminate it.  If the victim
676 	 * is the current job, call sunscpal_machine() now.
677 	 * Otherwise arrange for sunscpal_sched() to do it.
678 	 */
679 	sr->sr_flags |= SR_OVERDUE;
680 	if (sc->sc_current == sr) {
681 		SUNSCPAL_TRACE("cmd_tmo: call abort, sr=0x%x\n", (long)sr);
682 		sunscpal_abort(sc);
683 	} else {
684 		/*
685 		 * The driver may be idle, or busy with another job.
686 		 * Arrange for sunscpal_sched() to do the deed.
687 		 */
688 		SUNSCPAL_TRACE("cmd_tmo: clear matrix, t/l=0x%02x\n",
689 		    (sr->sr_target << 4) | sr->sr_lun);
690 		sc->sc_matrix[sr->sr_target][sr->sr_lun] = NULL;
691 	}
692 
693 	/*
694 	 * We may have aborted the current job, or may have
695 	 * already been idle. In either case, we should now
696 	 * be idle, so try to start another job.
697 	 */
698 	if (sc->sc_state == SUNSCPAL_IDLE) {
699 		SUNSCPAL_TRACE("cmd_tmo: call sched, cur=0x%x\n",
700 		    (long)sc->sc_current);
701 		sunscpal_sched(sc);
702 		SUNSCPAL_TRACE("cmd_tmo: sched done, cur=0x%x\n",
703 		    (long)sc->sc_current);
704 	}
705 
706  out:
707 	splx(s);
708 }
709 
710 
711 /*****************************************************************
712  * Interface to higher level
713  *****************************************************************/
714 
715 
716 /*
717  * Enter a new SCSI command into the "issue" queue, and
718  * if there is work to do, start it going.
719  *
720  * WARNING:  This can be called recursively!
721  * (see comment in sunscpal_done)
722  */
723 void
sunscpal_scsipi_request(struct scsipi_channel * chan,scsipi_adapter_req_t req,void * arg)724 sunscpal_scsipi_request(struct scsipi_channel *chan, scsipi_adapter_req_t req,
725     void *arg)
726 {
727 	struct scsipi_xfer *xs;
728 	struct sunscpal_softc *sc;
729 	struct sunscpal_req *sr;
730 	int s, i, flags;
731 
732 	sc = device_private(chan->chan_adapter->adapt_dev);
733 
734 	switch (req) {
735 	case ADAPTER_REQ_RUN_XFER:
736 		xs = arg;
737 		flags = xs->xs_control;
738 
739 		if (flags & XS_CTL_DATA_UIO)
740 			panic("sunscpal: scsi data uio requested");
741 
742 		s = splbio();
743 
744 		if (flags & XS_CTL_POLL) {
745 			/* Terminate any current command. */
746 			sr = sc->sc_current;
747 			if (sr != NULL) {
748 				printf("%s: polled request aborting %d/%d\n",
749 				    device_xname(sc->sc_dev), sr->sr_target,
750 				    sr->sr_lun);
751 				sunscpal_abort(sc);
752 			}
753 			if (sc->sc_state != SUNSCPAL_IDLE) {
754 				panic("%s: polled request, abort failed",
755 				    __func__);
756 			}
757 		}
758 
759 		/*
760 		 * Find lowest empty slot in ring buffer.
761 		 * XXX: What about "fairness" and cmd order?
762 		 */
763 		for (i = 0; i < SUNSCPAL_OPENINGS; i++)
764 			if (sc->sc_ring[i].sr_xs == NULL)
765 				goto new;
766 
767 		xs->error = XS_RESOURCE_SHORTAGE;
768 		SUNSCPAL_TRACE("scsipi_cmd: no openings, rv=%d\n", rv);
769 		goto out;
770 
771  new:
772 		/* Create queue entry */
773 		sr = &sc->sc_ring[i];
774 		sr->sr_xs = xs;
775 		sr->sr_target = xs->xs_periph->periph_target;
776 		sr->sr_lun = xs->xs_periph->periph_lun;
777 		sr->sr_dma_hand = NULL;
778 		sr->sr_dataptr = xs->data;
779 		sr->sr_datalen = xs->datalen;
780 		sr->sr_flags = (flags & XS_CTL_POLL) ? SR_IMMED : 0;
781 		sr->sr_status = -1;	/* no value */
782 		sc->sc_ncmds++;
783 
784 		SUNSCPAL_TRACE("scsipi_cmd: new sr=0x%x\n", (long)sr);
785 
786 		if (flags & XS_CTL_POLL) {
787 			/* Force this new command to be next. */
788 			sc->sc_rr = i;
789 		}
790 
791 		/*
792 		 * If we were idle, run some commands...
793 		 */
794 		if (sc->sc_state == SUNSCPAL_IDLE) {
795 			SUNSCPAL_TRACE("scsipi_cmd: call sched, cur=0x%x\n",
796 			    (long)sc->sc_current);
797 			sunscpal_sched(sc);
798 			SUNSCPAL_TRACE("scsipi_cmd: sched done, cur=0x%x\n",
799 			    (long)sc->sc_current);
800 		}
801 
802 		if (flags & XS_CTL_POLL) {
803 			/* Make sure sunscpal_sched() finished it. */
804 			if ((xs->xs_status & XS_STS_DONE) == 0)
805 				panic("%s: poll didn't finish", __func__);
806 		}
807 
808  out:
809 		splx(s);
810 		return;
811 
812 	case ADAPTER_REQ_GROW_RESOURCES:
813 		/* XXX Not supported. */
814 		return;
815 
816 	case ADAPTER_REQ_SET_XFER_MODE:
817 	    {
818 		/*
819 		 * We don't support Sync, Wide, or Tagged Queueing.
820 		 * Just callback now, to report this.
821 		 */
822 		struct scsipi_xfer_mode *xm = arg;
823 
824 		xm->xm_mode = 0;
825 		xm->xm_period = 0;
826 		xm->xm_offset = 0;
827 		scsipi_async_event(chan, ASYNC_EVENT_XFER_MODE, xm);
828 		return;
829 	    }
830 	}
831 }
832 
833 
834 /*
835  * POST PROCESSING OF SCSI_CMD (usually current)
836  * Called by sunscpal_sched(), sunscpal_machine()
837  */
838 static void
sunscpal_done(struct sunscpal_softc * sc)839 sunscpal_done(struct sunscpal_softc *sc)
840 {
841 	struct	sunscpal_req *sr;
842 	struct	scsipi_xfer *xs;
843 
844 #ifdef	DIAGNOSTIC
845 	if (sc->sc_state == SUNSCPAL_IDLE)
846 		panic("%s: state=idle", __func__);
847 	if (sc->sc_current == NULL)
848 		panic("%s: current=0", __func__);
849 #endif
850 
851 	sr = sc->sc_current;
852 	xs = sr->sr_xs;
853 
854 	SUNSCPAL_TRACE("done: top, cur=0x%x\n", (long)sc->sc_current);
855 
856 	/*
857 	 * Clean up DMA resources for this command.
858 	 */
859 	if (sr->sr_dma_hand) {
860 		SUNSCPAL_TRACE("done: dma_free, dh=0x%x\n",
861 		    (long)sr->sr_dma_hand);
862 		sunscpal_dma_free(sc);
863 	}
864 #ifdef	DIAGNOSTIC
865 	if (sr->sr_dma_hand)
866 		panic("%s: DMA free did not", __func__);
867 #endif
868 
869 	if (sc->sc_state & SUNSCPAL_ABORTING) {
870 		SUNSCPAL_TRACE("done: aborting, error=%d\n", xs->error);
871 		if (xs->error == XS_NOERROR)
872 			xs->error = XS_TIMEOUT;
873 	}
874 
875 	SUNSCPAL_TRACE("done: check error=%d\n", (long)xs->error);
876 
877 	/* If error is already set, ignore sr_status value. */
878 	if (xs->error != XS_NOERROR)
879 		goto finish;
880 
881 	SUNSCPAL_TRACE("done: check status=%d\n", sr->sr_status);
882 
883 	xs->status = sr->sr_status;
884 	switch (sr->sr_status) {
885 	case SCSI_OK:	/* 0 */
886 		break;
887 
888 	case SCSI_CHECK:
889 	case SCSI_BUSY:
890 		xs->error = XS_BUSY;
891 		break;
892 
893 	case -1:
894 		/* This is our "impossible" initial value. */
895 		/* fallthrough */
896 	default:
897 		printf("%s: target %d, bad status=%d\n",
898 		    device_xname(sc->sc_dev), sr->sr_target, sr->sr_status);
899 		xs->error = XS_DRIVER_STUFFUP;
900 		break;
901 	}
902 
903  finish:
904 
905 	SUNSCPAL_TRACE("done: finish, error=%d\n", xs->error);
906 
907 	/*
908 	 * Dequeue the finished command, but don't clear sc_state until
909 	 * after the call to scsipi_done(), because that may call back to
910 	 * sunscpal_scsi_cmd() - unwanted recursion!
911 	 *
912 	 * Keeping sc->sc_state != idle terminates the recursion.
913 	 */
914 #ifdef	DIAGNOSTIC
915 	if ((sc->sc_state & SUNSCPAL_WORKING) == 0)
916 		panic("%s: bad state", __func__);
917 #endif
918 
919 	/* Clear our pointers to the request. */
920 	sc->sc_current = NULL;
921 	sc->sc_matrix[sr->sr_target][sr->sr_lun] = NULL;
922 	callout_stop(&sr->sr_xs->xs_callout);
923 
924 	/* Make the request free. */
925 	sr->sr_xs = NULL;
926 	sc->sc_ncmds--;
927 
928 	/* Tell common SCSI code it is done. */
929 	scsipi_done(xs);
930 
931 	sc->sc_state = SUNSCPAL_IDLE;
932 	/* Now sunscpal_sched() may be called again. */
933 }
934 
935 
936 /*
937  * Schedule a SCSI operation.  This routine should return
938  * only after it achieves one of the following conditions:
939  *  	Busy (sc->sc_state != SUNSCPAL_IDLE)
940  *  	No more work can be started.
941  */
942 static void
sunscpal_sched(struct sunscpal_softc * sc)943 sunscpal_sched(struct sunscpal_softc *sc)
944 {
945 	struct sunscpal_req	*sr;
946 	struct scsipi_xfer *xs;
947 	int	target = 0, lun = 0;
948 	int	error, i;
949 
950 	/* Another hack (Er.. hook!) for anything that needs it: */
951 	if (sc->sc_intr_off) {
952 		SUNSCPAL_TRACE("sched: top, intr off\n", 0);
953 		sc->sc_intr_off(sc);
954 	}
955 
956  next_job:
957 	/*
958 	 * Grab the next job from queue.  Must be idle.
959 	 */
960 #ifdef	DIAGNOSTIC
961 	if (sc->sc_state != SUNSCPAL_IDLE)
962 		panic("%s: not idle", __func__);
963 	if (sc->sc_current)
964 		panic("%s: current set", __func__);
965 #endif
966 
967 	/*
968 	 * Always start the search where we last looked.
969 	 */
970 	i = sc->sc_rr;
971 	sr = NULL;
972 	do {
973 		if (sc->sc_ring[i].sr_xs) {
974 			target = sc->sc_ring[i].sr_target;
975 			lun = sc->sc_ring[i].sr_lun;
976 			if (sc->sc_matrix[target][lun] == NULL) {
977 				/*
978 				 * Do not mark the  target/LUN busy yet,
979 				 * because reselect may cause some other
980 				 * job to become the current one, so we
981 				 * might not actually start this job.
982 				 * Instead, set sc_matrix later on.
983 				 */
984 				sc->sc_rr = i;
985 				sr = &sc->sc_ring[i];
986 				break;
987 			}
988 		}
989 		i++;
990 		if (i == SUNSCPAL_OPENINGS)
991 			i = 0;
992 	} while (i != sc->sc_rr);
993 
994 	if (sr == NULL) {
995 		SUNSCPAL_TRACE("sched: no work, cur=0x%x\n",
996 		    (long)sc->sc_current);
997 
998 		/* Another hack (Er.. hook!) for anything that needs it: */
999 		if (sc->sc_intr_on) {
1000 			SUNSCPAL_TRACE("sched: ret, intr ON\n", 0);
1001 			sc->sc_intr_on(sc);
1002 		}
1003 
1004 		return;		/* No more work to do. */
1005 	}
1006 
1007 	SUNSCPAL_TRACE("sched: select for t/l=0x%02x\n",
1008 	    (sr->sr_target << 4) | sr->sr_lun);
1009 
1010 	sc->sc_state = SUNSCPAL_WORKING;
1011 	error = sunscpal_select(sc, sr);
1012 	if (sc->sc_current) {
1013 		/* Lost the race!  reselected out from under us! */
1014 		/* Work with the reselected job. */
1015 		if (sr->sr_flags & SR_IMMED) {
1016 			printf("%s: reselected while polling (abort)\n",
1017 			    device_xname(sc->sc_dev));
1018 			/* Abort the reselected job. */
1019 			sc->sc_state |= SUNSCPAL_ABORTING;
1020 			sc->sc_msgpriq |= SEND_ABORT;
1021 		}
1022 		sr = sc->sc_current;
1023 		xs = sr->sr_xs;
1024 		SUNSCPAL_TRACE("sched: reselect, new sr=0x%x\n", (long)sr);
1025 		goto have_nexus;
1026 	}
1027 
1028 	/* Normal selection result.  Target/LUN is now busy. */
1029 	sc->sc_matrix[target][lun] = sr;
1030 	sc->sc_current = sr;	/* connected */
1031 	xs = sr->sr_xs;
1032 
1033 	/*
1034 	 * Initialize pointers, etc. for this job
1035 	 */
1036 	sc->sc_dataptr  = sr->sr_dataptr;
1037 	sc->sc_datalen  = sr->sr_datalen;
1038 	sc->sc_prevphase = SUNSCPAL_PHASE_INVALID;
1039 	sc->sc_msgpriq = SEND_IDENTIFY;
1040 	sc->sc_msgoutq = 0;
1041 	sc->sc_msgout  = 0;
1042 
1043 	SUNSCPAL_TRACE("sched: select rv=%d\n", error);
1044 
1045 	switch (error) {
1046 	case XS_NOERROR:
1047 		break;
1048 
1049 	case XS_BUSY:
1050 		/* XXX - Reset and try again. */
1051 		printf("%s: select found SCSI bus busy, resetting...\n",
1052 		    device_xname(sc->sc_dev));
1053 		sunscpal_reset_scsibus(sc);
1054 		/* fallthrough */
1055 	case XS_SELTIMEOUT:
1056 	default:
1057 		xs->error = error;	/* from select */
1058 		SUNSCPAL_TRACE("sched: call done, sr=0x%x\n", (long)sr);
1059 		sunscpal_done(sc);
1060 
1061 		/* Paranoia: clear everything. */
1062 		sc->sc_dataptr = NULL;
1063 		sc->sc_datalen = 0;
1064 		sc->sc_prevphase = SUNSCPAL_PHASE_INVALID;
1065 		sc->sc_msgpriq = 0;
1066 		sc->sc_msgoutq = 0;
1067 		sc->sc_msgout  = 0;
1068 
1069 		goto next_job;
1070 	}
1071 
1072 	/*
1073 	 * Selection was successful.  Normally, this means
1074 	 * we are starting a new command.  However, this
1075 	 * might be the termination of an overdue job.
1076 	 */
1077 	if (sr->sr_flags & SR_OVERDUE) {
1078 		SUNSCPAL_TRACE("sched: overdue, sr=0x%x\n", (long)sr);
1079 		sc->sc_state |= SUNSCPAL_ABORTING;
1080 		sc->sc_msgpriq |= SEND_ABORT;
1081 		goto have_nexus;
1082 	}
1083 
1084 	/*
1085 	 * OK, we are starting a new command.
1086 	 * Initialize and allocate resources for the new command.
1087 	 * Device reset is special (only uses MSG_OUT phase).
1088 	 * Normal commands start in MSG_OUT phase where we will
1089 	 * send and IDENDIFY message, and then expect CMD phase.
1090 	 */
1091 #ifdef	SUNSCPAL_DEBUG
1092 	if (sunscpal_debug & SUNSCPAL_DBG_CMDS) {
1093 		printf("%s: begin, target=%d, LUN=%d\n", __func__,
1094 		    xs->xs_periph->periph_target, xs->xs_periph->periph_lun);
1095 		sunscpal_show_scsi_cmd(xs);
1096 	}
1097 #endif
1098 	if (xs->xs_control & XS_CTL_RESET) {
1099 		SUNSCPAL_TRACE("sched: cmd=reset, sr=0x%x\n", (long)sr);
1100 		/* Not an error, so do not set SUNSCPAL_ABORTING */
1101 		sc->sc_msgpriq |= SEND_DEV_RESET;
1102 		goto have_nexus;
1103 	}
1104 
1105 #ifdef	DIAGNOSTIC
1106 	if ((xs->xs_control & (XS_CTL_DATA_IN | XS_CTL_DATA_OUT)) == 0) {
1107 		if (sc->sc_dataptr) {
1108 			printf("%s: ptr but no data in/out flags?\n",
1109 			    device_xname(sc->sc_dev));
1110 			SUNSCPAL_BREAK();
1111 			sc->sc_dataptr = NULL;
1112 		}
1113 	}
1114 #endif
1115 
1116 	/* Allocate DMA space (maybe) */
1117 	if (sc->sc_dataptr && (sc->sc_flags & SUNSCPAL_DISABLE_DMA) == 0 &&
1118 		(sc->sc_datalen >= sc->sc_min_dma_len))
1119 	{
1120 		SUNSCPAL_TRACE("sched: dma_alloc, len=%d\n", sc->sc_datalen);
1121 		sunscpal_dma_alloc(sc);
1122 	}
1123 
1124 	/*
1125 	 * Initialization hook called just after select,
1126 	 * at the beginning of COMMAND phase.
1127 	 * (but AFTER the DMA allocation is done)
1128 	 *
1129 	 * We need to set up the DMA engine BEFORE the target puts
1130 	 * the SCSI bus into any DATA phase.
1131 	 */
1132 	if (sr->sr_dma_hand) {
1133 		SUNSCPAL_TRACE("sched: dma_setup, dh=0x%x\n",
1134 		    (long) sr->sr_dma_hand);
1135 	    sunscpal_dma_setup(sc);
1136 	}
1137 
1138 	/*
1139 	 * Schedule a timeout for the job we are starting.
1140 	 */
1141 	if ((sr->sr_flags & SR_IMMED) == 0) {
1142 		i = mstohz(xs->timeout);
1143 		SUNSCPAL_TRACE("sched: set timeout=%d\n", i);
1144 		callout_reset(&sr->sr_xs->xs_callout, i,
1145 		    sunscpal_cmd_timeout, sr);
1146 	}
1147 
1148  have_nexus:
1149 
1150 	SUNSCPAL_TRACE("sched: call machine, cur=0x%x\n",
1151 	    (long)sc->sc_current);
1152 	sunscpal_machine(sc);
1153 	SUNSCPAL_TRACE("sched: machine done, cur=0x%x\n",
1154 	    (long)sc->sc_current);
1155 
1156 	/*
1157 	 * What state did sunscpal_machine() leave us in?
1158 	 * Hopefully it sometimes completes a job...
1159 	 */
1160 	if (sc->sc_state == SUNSCPAL_IDLE)
1161 		goto next_job;
1162 
1163 	return; 	/* Have work in progress. */
1164 }
1165 
1166 
1167 /*
1168  *  Reselect handler: checks for reselection, and if we are being
1169  *	reselected, it sets up sc->sc_current.
1170  *
1171  *  We are reselected when:
1172  *	SEL is TRUE
1173  *	IO  is TRUE
1174  *	BSY is FALSE
1175  */
1176 void
sunscpal_reselect(struct sunscpal_softc * sc)1177 sunscpal_reselect(struct sunscpal_softc *sc)
1178 {
1179 
1180 	/*
1181 	 * This controller does not implement disconnect/reselect, so
1182 	 * we really don't have anything to do here.  We keep this
1183 	 * function as a placeholder, though.
1184 	 */
1185 }
1186 
1187 /*
1188  *  Select target: xs is the transfer that we are selecting for.
1189  *  sc->sc_current should be NULL.
1190  *
1191  *  Returns:
1192  *	sc->sc_current != NULL  ==> we were reselected (race!)
1193  *	XS_NOERROR		==> selection worked
1194  *	XS_BUSY 		==> lost arbitration
1195  *	XS_SELTIMEOUT   	==> no response to selection
1196  */
1197 static int
sunscpal_select(struct sunscpal_softc * sc,struct sunscpal_req * sr)1198 sunscpal_select(struct sunscpal_softc *sc, struct sunscpal_req *sr)
1199 {
1200 	int timo, target_mask;
1201 	u_short	mode;
1202 
1203 	/* Check for reselect */
1204 	sunscpal_reselect(sc);
1205 	if (sc->sc_current) {
1206 		SUNSCPAL_TRACE("select: reselect, cur=0x%x\n",
1207 		    (long)sc->sc_current);
1208 		return XS_BUSY;	/* reselected */
1209 	}
1210 
1211 	/*
1212 	 * Select the target.
1213 	 */
1214 	target_mask = (1 << sr->sr_target);
1215 	SUNSCPAL_WRITE_1(sc, sunscpal_data, target_mask);
1216 	SUNSCPAL_WRITE_2(sc, sunscpal_icr, SUNSCPAL_ICR_SELECT);
1217 
1218 	/*
1219 	 * Wait for the target to assert BSY.
1220 	 * SCSI spec. says wait for 250 mS.
1221 	 */
1222 	for (timo = 25000;;) {
1223 		if (SUNSCPAL_READ_2(sc, sunscpal_icr) & SUNSCPAL_ICR_BUSY)
1224 			goto success;
1225 		if (--timo <= 0)
1226 			break;
1227 		delay(10);
1228 	}
1229 
1230 	SUNSCPAL_WRITE_1(sc, sunscpal_data, 0);
1231 	SUNSCPAL_WRITE_2(sc, sunscpal_icr, 0);
1232 
1233 	SUNSCPAL_TRACE("select: device down, rc=%d\n", XS_SELTIMEOUT);
1234 	return XS_SELTIMEOUT;
1235 
1236  success:
1237 
1238 	/*
1239 	 * The target is now driving BSY, so we can stop
1240 	 * driving SEL and the data bus.  We do set up
1241 	 * whether or not this target needs parity.
1242 	 */
1243 	mode = 0;
1244 	if ((sc->sc_parity_disable & target_mask) == 0)
1245 		mode |= SUNSCPAL_ICR_PARITY_ENABLE;
1246 	SUNSCPAL_WRITE_2(sc, sunscpal_icr, mode);
1247 
1248 	return XS_NOERROR;
1249 }
1250 
1251 /*****************************************************************
1252  * Functions to handle each info. transfer phase:
1253  *****************************************************************/
1254 
1255 /*
1256  * The message system:
1257  *
1258  * This is a revamped message system that now should easier accommodate
1259  * new messages, if necessary.
1260  *
1261  * Currently we accept these messages:
1262  * IDENTIFY (when reselecting)
1263  * COMMAND COMPLETE # (expect bus free after messages marked #)
1264  * NOOP
1265  * MESSAGE REJECT
1266  * SYNCHRONOUS DATA TRANSFER REQUEST
1267  * SAVE DATA POINTER
1268  * RESTORE POINTERS
1269  * DISCONNECT #
1270  *
1271  * We may send these messages in prioritized order:
1272  * BUS DEVICE RESET #		if XS_CTL_RESET & xs->xs_control (or in
1273  *				weird sits.)
1274  * MESSAGE PARITY ERROR		par. err. during MSGI
1275  * MESSAGE REJECT		If we get a message we don't know how to handle
1276  * ABORT #			send on errors
1277  * INITIATOR DETECTED ERROR	also on errors (SCSI2) (during info xfer)
1278  * IDENTIFY			At the start of each transfer
1279  * SYNCHRONOUS DATA TRANSFER REQUEST	if appropriate
1280  * NOOP				if nothing else fits the bill ...
1281  */
1282 
1283 /*
1284  * Precondition:
1285  * The SCSI bus is already in the MSGI phase and there is a message byte
1286  * on the bus, along with an asserted REQ signal.
1287  *
1288  * Our return value determines whether our caller, sunscpal_machine()
1289  * will expect to see another REQ (and possibly phase change).
1290  */
1291 static int
sunscpal_msg_in(struct sunscpal_softc * sc)1292 sunscpal_msg_in(struct sunscpal_softc *sc)
1293 {
1294 	struct sunscpal_req *sr = sc->sc_current;
1295 	struct scsipi_xfer *xs = sr->sr_xs;
1296 	int n, phase;
1297 	int act_flags;
1298 
1299 	act_flags = ACT_CONTINUE;
1300 
1301 	if (sc->sc_prevphase == SUNSCPAL_PHASE_MSG_IN) {
1302 		/* This is a continuation of the previous message. */
1303 		n = sc->sc_imp - sc->sc_imess;
1304 		SUNSCPAL_TRACE("msg_in: continuation, n=%d\n", n);
1305 		goto nextbyte;
1306 	}
1307 
1308 	/* This is a new MESSAGE IN phase.  Clean up our state. */
1309 	sc->sc_state &= ~SUNSCPAL_DROP_MSGIN;
1310 
1311  nextmsg:
1312 	n = 0;
1313 	sc->sc_imp = &sc->sc_imess[n];
1314 
1315  nextbyte:
1316 	/*
1317 	 * Read a whole message, but don't ack the last byte.  If we reject the
1318 	 * message, we have to assert ATN during the message transfer phase
1319 	 * itself.
1320 	 */
1321 	for (;;) {
1322 		/*
1323 		 * Read a message byte.
1324 		 * First, check BSY, REQ, phase...
1325 		 */
1326 		if (!SUNSCPAL_BUSY(sc)) {
1327 			SUNSCPAL_TRACE("msg_in: lost BSY, n=%d\n", n);
1328 			/* XXX - Assume the command completed? */
1329 			act_flags |= (ACT_DISCONNECT | ACT_CMD_DONE);
1330 			return act_flags;
1331 		}
1332 		if (sunscpal_wait_req(sc)) {
1333 			SUNSCPAL_TRACE("msg_in: BSY but no REQ, n=%d\n", n);
1334 			/* Just let sunscpal_machine() handle it... */
1335 			return act_flags;
1336 		}
1337 		phase = SUNSCPAL_BUS_PHASE(SUNSCPAL_READ_2(sc, sunscpal_icr));
1338 		if (phase != SUNSCPAL_PHASE_MSG_IN) {
1339 			/*
1340 			 * Target left MESSAGE IN, probably because it
1341 			 * a) noticed our ATN signal, or
1342 			 * b) ran out of messages.
1343 			 */
1344 			return act_flags;
1345 		}
1346 		/* Still in MESSAGE IN phase, and REQ is asserted. */
1347 		if ((SUNSCPAL_READ_2(sc, sunscpal_icr) &
1348 		    SUNSCPAL_ICR_PARITY_ERROR) != 0) {
1349 			sunscpal_sched_msgout(sc, SEND_PARITY_ERROR);
1350 			sc->sc_state |= SUNSCPAL_DROP_MSGIN;
1351 		}
1352 
1353 		/* Gather incoming message bytes if needed. */
1354 		if ((sc->sc_state & SUNSCPAL_DROP_MSGIN) == 0) {
1355 			if (n >= SUNSCPAL_MAX_MSG_LEN) {
1356 				sunscpal_sched_msgout(sc, SEND_REJECT);
1357 				sc->sc_state |= SUNSCPAL_DROP_MSGIN;
1358 			} else {
1359 				*sc->sc_imp++ =
1360 				    SUNSCPAL_READ_1(sc, sunscpal_cmd_stat);
1361 				n++;
1362 				/*
1363 				 * This testing is suboptimal, but most
1364 				 * messages will be of the one byte variety, so
1365 				 * it should not affect performance
1366 				 * significantly.
1367 				 */
1368 				if (n == 1 && MSG_IS1BYTE(sc->sc_imess[0]))
1369 					goto have_msg;
1370 				if (n == 2 && MSG_IS2BYTE(sc->sc_imess[0]))
1371 					goto have_msg;
1372 				if (n >= 3 && MSG_ISEXTENDED(sc->sc_imess[0]) &&
1373 					n == sc->sc_imess[1] + 2)
1374 					goto have_msg;
1375 			}
1376 		}
1377 
1378 		/*
1379 		 * If we reach this spot we're either:
1380 		 * a) in the middle of a multi-byte message, or
1381 		 * b) dropping bytes.
1382 		 */
1383 
1384 		if (act_flags != ACT_CONTINUE)
1385 			return act_flags;
1386 
1387 		/* back to nextbyte */
1388 	}
1389 
1390  have_msg:
1391 	/* We now have a complete message.  Parse it. */
1392 
1393 	switch (sc->sc_imess[0]) {
1394 	case MSG_CMDCOMPLETE:
1395 		SUNSCPAL_TRACE("msg_in: CMDCOMPLETE\n", 0);
1396 		/* Target is about to disconnect. */
1397 		act_flags |= (ACT_DISCONNECT | ACT_CMD_DONE);
1398 		break;
1399 
1400 	case MSG_PARITY_ERROR:
1401 		SUNSCPAL_TRACE("msg_in: PARITY_ERROR\n", 0);
1402 		/* Resend the last message. */
1403 		sunscpal_sched_msgout(sc, sc->sc_msgout);
1404 		break;
1405 
1406 	case MSG_MESSAGE_REJECT:
1407 		/* The target rejects the last message we sent. */
1408 		SUNSCPAL_TRACE("msg_in: got reject for 0x%x\n", sc->sc_msgout);
1409 		switch (sc->sc_msgout) {
1410 		case SEND_IDENTIFY:
1411 			/* Really old target controller? */
1412 			/* XXX ... */
1413 			break;
1414 		case SEND_INIT_DET_ERR:
1415 			goto abort;
1416 		}
1417 		break;
1418 
1419 	case MSG_NOOP:
1420 		SUNSCPAL_TRACE("msg_in: NOOP\n", 0);
1421 		break;
1422 
1423 	case MSG_DISCONNECT:
1424 		SUNSCPAL_TRACE("msg_in: DISCONNECT\n", 0);
1425 		/* Target is about to disconnect. */
1426 		act_flags |= ACT_DISCONNECT;
1427 		if ((xs->xs_periph->periph_quirks & PQUIRK_AUTOSAVE) == 0)
1428 			break;
1429 		/*FALLTHROUGH*/
1430 
1431 	case MSG_SAVEDATAPOINTER:
1432 		SUNSCPAL_TRACE("msg_in: SAVE_PTRS\n", 0);
1433 		sr->sr_dataptr = sc->sc_dataptr;
1434 		sr->sr_datalen = sc->sc_datalen;
1435 		break;
1436 
1437 	case MSG_RESTOREPOINTERS:
1438 		SUNSCPAL_TRACE("msg_in: RESTORE_PTRS\n", 0);
1439 		sc->sc_dataptr = sr->sr_dataptr;
1440 		sc->sc_datalen = sr->sr_datalen;
1441 		break;
1442 
1443 	case MSG_EXTENDED:
1444 		switch (sc->sc_imess[2]) {
1445 		case MSG_EXT_SDTR:
1446 		case MSG_EXT_WDTR:
1447 			/* This controller can not do synchronous mode. */
1448 			goto reject;
1449 		default:
1450 			printf("%s: unrecognized MESSAGE EXTENDED; "
1451 			    "sending REJECT\n",
1452 			    device_xname(sc->sc_dev));
1453 			SUNSCPAL_BREAK();
1454 			goto reject;
1455 		}
1456 		break;
1457 
1458 	default:
1459 		SUNSCPAL_TRACE("msg_in: eh? imsg=0x%x\n", sc->sc_imess[0]);
1460 		printf("%s: unrecognized MESSAGE; sending REJECT\n",
1461 		    device_xname(sc->sc_dev));
1462 		SUNSCPAL_BREAK();
1463 		/* FALLTHROUGH */
1464 	reject:
1465 		sunscpal_sched_msgout(sc, SEND_REJECT);
1466 		break;
1467 
1468 	abort:
1469 		sc->sc_state |= SUNSCPAL_ABORTING;
1470 		sunscpal_sched_msgout(sc, SEND_ABORT);
1471 		break;
1472 	}
1473 
1474 	/* Go get the next message, if any. */
1475 	if (act_flags == ACT_CONTINUE)
1476 		goto nextmsg;
1477 
1478 	return act_flags;
1479 }
1480 
1481 
1482 /*
1483  * The message out (and in) stuff is a bit complicated:
1484  * If the target requests another message (sequence) without
1485  * having changed phase in between it really asks for a
1486  * retransmit, probably due to parity error(s).
1487  * The following messages can be sent:
1488  * IDENTIFY	   @ These 4 stem from SCSI command activity
1489  * SDTR		   @
1490  * WDTR		   @
1491  * DEV_RESET	   @
1492  * REJECT if MSGI doesn't make sense
1493  * PARITY_ERROR if parity error while in MSGI
1494  * INIT_DET_ERR if parity error while not in MSGI
1495  * ABORT if INIT_DET_ERR rejected
1496  * NOOP if asked for a message and there's nothing to send
1497  *
1498  * Note that we call this one with (sc_current == NULL)
1499  * when sending ABORT for unwanted reselections.
1500  */
1501 static int
sunscpal_msg_out(struct sunscpal_softc * sc)1502 sunscpal_msg_out(struct sunscpal_softc *sc)
1503 {
1504 	/*
1505 	 * This controller does not allow you to assert ATN, which
1506 	 * means we will never get the opportunity to send messages to
1507 	 * the target (the bus will never enter this MSG_OUT phase).
1508 	 * This will eventually leave us with no option other than to
1509 	 * reset the bus.  We keep this function as a placeholder,
1510 	 * though, and this printf will eventually go away or get
1511 	 * #ifdef'ed:
1512 	 */
1513 	printf("%s: bus is in MSG_OUT phase?\n", __func__);
1514 	return ACT_CONTINUE | ACT_RESET_BUS;
1515 }
1516 
1517 /*
1518  * Handle command phase.
1519  */
1520 static int
sunscpal_command(struct sunscpal_softc * sc)1521 sunscpal_command(struct sunscpal_softc *sc)
1522 {
1523 	struct sunscpal_req *sr = sc->sc_current;
1524 	struct scsipi_xfer *xs = sr->sr_xs;
1525 	int len;
1526 
1527 	/* Assume command can be sent in one go. */
1528 	/* XXX: Do this using DMA, and get a phase change intr? */
1529 	len = sunscpal_pio_out(sc, SUNSCPAL_PHASE_COMMAND, xs->cmdlen,
1530 	    (uint8_t *)xs->cmd);
1531 
1532 	if (len != xs->cmdlen) {
1533 #ifdef	SUNSCPAL_DEBUG
1534 		printf("%s: short transfer: wanted %d got %d.\n",
1535 		    __func__, xs->cmdlen, len);
1536 		sunscpal_show_scsi_cmd(xs);
1537 		SUNSCPAL_BREAK();
1538 #endif
1539 		if (len < 6) {
1540 			xs->error = XS_DRIVER_STUFFUP;
1541 			sc->sc_state |= SUNSCPAL_ABORTING;
1542 			sunscpal_sched_msgout(sc, SEND_ABORT);
1543 		}
1544 
1545 	}
1546 
1547 	return ACT_CONTINUE;
1548 }
1549 
1550 
1551 /*
1552  * Handle either data_in or data_out
1553  */
1554 static int
sunscpal_data_xfer(struct sunscpal_softc * sc,int phase)1555 sunscpal_data_xfer(struct sunscpal_softc *sc, int phase)
1556 {
1557 	struct sunscpal_req *sr = sc->sc_current;
1558 	struct scsipi_xfer *xs = sr->sr_xs;
1559 	int expected_phase;
1560 	int len;
1561 
1562 	/*
1563 	 * When aborting a command, disallow any data phase.
1564 	 */
1565 	if (sc->sc_state & SUNSCPAL_ABORTING) {
1566 		printf("%s: aborting, bus phase=%s (reset)\n",
1567 		    device_xname(sc->sc_dev), phase_names[(phase >> 8) & 7]);
1568 		return ACT_RESET_BUS;	/* XXX */
1569 	}
1570 
1571 	/* Validate expected phase (data_in or data_out) */
1572 	expected_phase = (xs->xs_control & XS_CTL_DATA_OUT) ?
1573 	    SUNSCPAL_PHASE_DATA_OUT : SUNSCPAL_PHASE_DATA_IN;
1574 	if (phase != expected_phase) {
1575 		printf("%s: data phase error\n", device_xname(sc->sc_dev));
1576 		goto abort;
1577 	}
1578 
1579 	/* Make sure we have some data to move. */
1580 	if (sc->sc_datalen <= 0) {
1581 		/* Device needs padding. */
1582 		if (phase == SUNSCPAL_PHASE_DATA_IN)
1583 			sunscpal_pio_in(sc, phase, 4096, NULL);
1584 		else
1585 			sunscpal_pio_out(sc, phase, 4096, NULL);
1586 		/* Make sure that caused a phase change. */
1587 		if (SUNSCPAL_BUS_PHASE(SUNSCPAL_READ_2(sc, sunscpal_icr)) ==
1588 		    phase) {
1589 			/* More than 4k is just too much! */
1590 			printf("%s: too much data padding\n",
1591 			    device_xname(sc->sc_dev));
1592 			goto abort;
1593 		}
1594 		return ACT_CONTINUE;
1595 	}
1596 
1597 	/*
1598 	 * Attempt DMA only if dma_alloc gave us a DMA handle AND
1599 	 * there is enough left to transfer so DMA is worth while.
1600 	 */
1601 	if (sr->sr_dma_hand && (sc->sc_datalen >= sc->sc_min_dma_len)) {
1602 		/*
1603 		 * OK, really start DMA.  Note, the MD start function
1604 		 * is responsible for setting the TCMD register, etc.
1605 		 * (Acknowledge the phase change there, not here.)
1606 		 */
1607 		SUNSCPAL_TRACE("data_xfer: dma_start, dh=0x%x\n",
1608 		    (long)sr->sr_dma_hand);
1609 		sunscpal_dma_start(sc);
1610 		return ACT_WAIT_DMA;
1611 	}
1612 
1613 	/*
1614 	 * Doing PIO for data transfer.  (Possibly "Pseudo DMA")
1615 	 * XXX:  Do PDMA functions need to set tcmd later?
1616 	 */
1617 	SUNSCPAL_TRACE("data_xfer: doing PIO, len=%d\n", sc->sc_datalen);
1618 	if (phase == SUNSCPAL_PHASE_DATA_OUT) {
1619 		len = sunscpal_pio_out(sc, phase,
1620 		    sc->sc_datalen, sc->sc_dataptr);
1621 	} else {
1622 		len = sunscpal_pio_in(sc, phase,
1623 		    sc->sc_datalen, sc->sc_dataptr);
1624 	}
1625 	sc->sc_dataptr += len;
1626 	sc->sc_datalen -= len;
1627 
1628 	SUNSCPAL_TRACE("data_xfer: did PIO, resid=%d\n", sc->sc_datalen);
1629 	return ACT_CONTINUE;
1630 
1631  abort:
1632 	sc->sc_state |= SUNSCPAL_ABORTING;
1633 	sunscpal_sched_msgout(sc, SEND_ABORT);
1634 	return ACT_CONTINUE;
1635 }
1636 
1637 
1638 static int
sunscpal_status(struct sunscpal_softc * sc)1639 sunscpal_status(struct sunscpal_softc *sc)
1640 {
1641 	int len;
1642 	uint8_t status;
1643 	struct sunscpal_req *sr = sc->sc_current;
1644 
1645 	len = sunscpal_pio_in(sc, SUNSCPAL_PHASE_STATUS, 1, &status);
1646 	if (len) {
1647 		sr->sr_status = status;
1648 	} else {
1649 		printf("%s: none?\n", __func__);
1650 	}
1651 
1652 	return ACT_CONTINUE;
1653 }
1654 
1655 
1656 /*
1657  * This is the big state machine that follows SCSI phase changes.
1658  * This is somewhat like a co-routine.  It will do a SCSI command,
1659  * and exit if the command is complete, or if it must wait, i.e.
1660  * for DMA to complete or for reselect to resume the job.
1661  *
1662  * The bus must be selected, and we need to know which command is
1663  * being undertaken.
1664  */
1665 static void
sunscpal_machine(struct sunscpal_softc * sc)1666 sunscpal_machine(struct sunscpal_softc *sc)
1667 {
1668 	struct sunscpal_req *sr;
1669 	struct scsipi_xfer *xs;
1670 	int act_flags, phase, timo;
1671 
1672 #ifdef	DIAGNOSTIC
1673 	if (sc->sc_state == SUNSCPAL_IDLE)
1674 		panic("%s: state=idle", __func__);
1675 	if (sc->sc_current == NULL)
1676 		panic("%s: no current cmd", __func__);
1677 #endif
1678 
1679 	sr = sc->sc_current;
1680 	xs = sr->sr_xs;
1681 	act_flags = ACT_CONTINUE;
1682 
1683 	/*
1684 	 * This will be called by sunscpal_intr() when DMA is
1685 	 * complete.  Must stop DMA before touching the PAL or
1686 	 * there will be "register conflict" errors.
1687 	 */
1688 	if ((sc->sc_state & SUNSCPAL_DOINGDMA) != 0) {
1689 		/* Pick-up where where we left off... */
1690 		goto dma_done;
1691 	}
1692 
1693  next_phase:
1694 
1695 	if (!SUNSCPAL_BUSY(sc)) {
1696 		/* Unexpected disconnect */
1697 		printf("%s: unexpected disconnect.\n", __func__);
1698 		xs->error = XS_DRIVER_STUFFUP;
1699 		act_flags |= (ACT_DISCONNECT | ACT_CMD_DONE);
1700 		goto do_actions;
1701 	}
1702 
1703 	/*
1704 	 * Wait for REQ before reading the phase.
1705 	 * Need to wait longer than usual here, because
1706 	 * some devices are just plain slow...
1707 	 */
1708 	timo = sunscpal_wait_phase_timo;
1709 	for (;;) {
1710 		if (SUNSCPAL_READ_2(sc, sunscpal_icr) & SUNSCPAL_ICR_REQUEST)
1711 			break;
1712 		if (--timo <= 0) {
1713 			if (sc->sc_state & SUNSCPAL_ABORTING) {
1714 				printf("%s: no REQ while aborting, reset\n",
1715 				    device_xname(sc->sc_dev));
1716 				act_flags |= ACT_RESET_BUS;
1717 				goto do_actions;
1718 			}
1719 			printf("%s: no REQ for next phase, abort\n",
1720 			    device_xname(sc->sc_dev));
1721 			sc->sc_state |= SUNSCPAL_ABORTING;
1722 			sunscpal_sched_msgout(sc, SEND_ABORT);
1723 			goto next_phase;
1724 		}
1725 		delay(100);
1726 	}
1727 
1728 	phase = SUNSCPAL_BUS_PHASE(SUNSCPAL_READ_2(sc, sunscpal_icr));
1729 	SUNSCPAL_TRACE("machine: phase=%s\n",
1730 	    (long)phase_names[(phase >> 8) & 7]);
1731 
1732 	/*
1733 	 * We assume that the device knows what it's doing,
1734 	 * so any phase is good.
1735 	 */
1736 
1737 	switch (phase) {
1738 
1739 	case SUNSCPAL_PHASE_DATA_OUT:
1740 	case SUNSCPAL_PHASE_DATA_IN:
1741 		act_flags = sunscpal_data_xfer(sc, phase);
1742 		break;
1743 
1744 	case SUNSCPAL_PHASE_COMMAND:
1745 		act_flags = sunscpal_command(sc);
1746 		break;
1747 
1748 	case SUNSCPAL_PHASE_STATUS:
1749 		act_flags = sunscpal_status(sc);
1750 		break;
1751 
1752 	case SUNSCPAL_PHASE_MSG_OUT:
1753 		act_flags = sunscpal_msg_out(sc);
1754 		break;
1755 
1756 	case SUNSCPAL_PHASE_MSG_IN:
1757 		act_flags = sunscpal_msg_in(sc);
1758 		break;
1759 
1760 	default:
1761 		printf("%s: Unexpected phase 0x%x\n", __func__, phase);
1762 		sc->sc_state |= SUNSCPAL_ABORTING;
1763 		sunscpal_sched_msgout(sc, SEND_ABORT);
1764 		goto next_phase;
1765 
1766 	} /* switch */
1767 	sc->sc_prevphase = phase;
1768 
1769  do_actions:
1770 
1771 	if (act_flags & ACT_WAIT_DMA) {
1772 		act_flags &= ~ACT_WAIT_DMA;
1773 		/* Wait for DMA to complete (polling, or interrupt). */
1774 		if ((sr->sr_flags & SR_IMMED) == 0) {
1775 			SUNSCPAL_TRACE("machine: wait for DMA intr.\n", 0);
1776 			return; 	/* will resume at dma_done */
1777 		}
1778 		/* Busy-wait for it to finish. */
1779 		SUNSCPAL_TRACE("machine: dma_poll, dh=0x%x\n",
1780 		    (long)sr->sr_dma_hand);
1781 		sunscpal_dma_poll(sc);
1782  dma_done:
1783 		/* Return here after interrupt. */
1784 		if (sr->sr_flags & SR_OVERDUE)
1785 			sc->sc_state |= SUNSCPAL_ABORTING;
1786 		SUNSCPAL_TRACE("machine: dma_stop, dh=0x%x\n",
1787 		    (long)sr->sr_dma_hand);
1788 		sunscpal_dma_stop(sc);
1789 		SUNSCPAL_CLR_INTR(sc);	/* XXX */
1790 		/*
1791 		 * While DMA is running we can not touch the SBC,
1792 		 * so various places just set SUNSCPAL_ABORTING and
1793 		 * expect us the "kick it" when DMA is done.
1794 		 */
1795 		if (sc->sc_state & SUNSCPAL_ABORTING) {
1796 			sunscpal_sched_msgout(sc, SEND_ABORT);
1797 		}
1798 	}
1799 
1800 	/*
1801 	 * Check for parity error.
1802 	 * XXX - better place to check?
1803 	 */
1804 	if (SUNSCPAL_READ_2(sc, sunscpal_icr) & SUNSCPAL_ICR_PARITY_ERROR) {
1805 		printf("%s: parity error!\n", device_xname(sc->sc_dev));
1806 		/* XXX: sc->sc_state |= SUNSCPAL_ABORTING; */
1807 		sunscpal_sched_msgout(sc, SEND_PARITY_ERROR);
1808 	}
1809 
1810 	if (act_flags == ACT_CONTINUE)
1811 		goto next_phase;
1812 	/* All other actions "break" from the loop. */
1813 
1814 	SUNSCPAL_TRACE("machine: act_flags=0x%x\n", act_flags);
1815 
1816 	if (act_flags & ACT_RESET_BUS) {
1817 		act_flags |= ACT_CMD_DONE;
1818 		/*
1819 		 * Reset the SCSI bus, usually due to a timeout.
1820 		 * The error code XS_TIMEOUT allows retries.
1821 		 */
1822 		sc->sc_state |= SUNSCPAL_ABORTING;
1823 		printf("%s: reset SCSI bus for TID=%d LUN=%d\n",
1824 		    device_xname(sc->sc_dev), sr->sr_target, sr->sr_lun);
1825 		sunscpal_reset_scsibus(sc);
1826 	}
1827 
1828 	if (act_flags & ACT_CMD_DONE) {
1829 		act_flags |= ACT_DISCONNECT;
1830 		/* Need to call scsipi_done() */
1831 		/* XXX: from the aic6360 driver, but why? */
1832 		if (sc->sc_datalen < 0) {
1833 			printf("%s: %d extra bytes from %d:%d\n",
1834 			    device_xname(sc->sc_dev), -sc->sc_datalen,
1835 			    sr->sr_target, sr->sr_lun);
1836 			sc->sc_datalen = 0;
1837 		}
1838 		xs->resid = sc->sc_datalen;
1839 		/* Note: this will clear sc_current */
1840 		SUNSCPAL_TRACE("machine: call done, cur=0x%x\n", (long)sr);
1841 		sunscpal_done(sc);
1842 	}
1843 
1844 	if (act_flags & ACT_DISCONNECT) {
1845 		/*
1846 		 * The device has dropped BSY (or will soon).
1847 		 * We have to wait here for BSY to drop, otherwise
1848 		 * the next command may decide we need a bus reset.
1849 		 */
1850 		timo = sunscpal_wait_req_timo;	/* XXX */
1851 		for (;;) {
1852 			if (!SUNSCPAL_BUSY(sc))
1853 				goto busfree;
1854 			if (--timo <= 0)
1855 				break;
1856 			delay(2);
1857 		}
1858 		/* Device is sitting on the bus! */
1859 		printf("%s: Target %d LUN %d stuck busy, resetting...\n",
1860 		    device_xname(sc->sc_dev), sr->sr_target, sr->sr_lun);
1861 		sunscpal_reset_scsibus(sc);
1862  busfree:
1863 		SUNSCPAL_TRACE("machine: discon, waited %d\n",
1864 			sunscpal_wait_req_timo - timo);
1865 
1866 		SUNSCPAL_WRITE_2(sc, sunscpal_icr, 0);
1867 
1868 		if ((act_flags & ACT_CMD_DONE) == 0) {
1869 			SUNSCPAL_TRACE("machine: discon, cur=0x%x\n", (long)sr);
1870 		}
1871 
1872 		/*
1873 		 * We may be here due to a disconnect message,
1874 		 * in which case we did NOT call sunscpal_done,
1875 		 * and we need to clear sc_current.
1876 		 */
1877 		sc->sc_state = SUNSCPAL_IDLE;
1878 		sc->sc_current = NULL;
1879 
1880 		/* Paranoia: clear everything. */
1881 		sc->sc_dataptr = NULL;
1882 		sc->sc_datalen = 0;
1883 		sc->sc_prevphase = SUNSCPAL_PHASE_INVALID;
1884 		sc->sc_msgpriq = 0;
1885 		sc->sc_msgoutq = 0;
1886 		sc->sc_msgout  = 0;
1887 
1888 		/* Our caller will re-enable interrupts. */
1889 	}
1890 }
1891 
1892 
1893 #ifdef	SUNSCPAL_DEBUG
1894 
1895 static void
sunscpal_show_scsi_cmd(struct scsipi_xfer * xs)1896 sunscpal_show_scsi_cmd(struct scsipi_xfer *xs)
1897 {
1898 	uint8_t *b = (uint8_t *)xs->cmd;
1899 	int i = 0;
1900 
1901 	scsipi_printaddr(xs->xs_periph);
1902 	if ((xs->xs_control & XS_CTL_RESET) == 0) {
1903 		printf("-");
1904 		while (i < xs->cmdlen) {
1905 			if (i != 0)
1906 				printf(",");
1907 			printf("%x", b[i++]);
1908 		}
1909 		printf("-\n");
1910 	} else {
1911 		printf("-RESET-\n");
1912 	}
1913 }
1914 
1915 
1916 int sunscpal_traceidx = 0;
1917 
1918 #define	TRACE_MAX	1024
1919 struct trace_ent {
1920 	char *msg;
1921 	long  val;
1922 } sunscpal_tracebuf[TRACE_MAX];
1923 
1924 void
sunscpal_trace(char * msg,long val)1925 sunscpal_trace(char *msg, long val)
1926 {
1927 	struct trace_ent *tr;
1928 	int s;
1929 
1930 	s = splbio();
1931 
1932 	tr = &sunscpal_tracebuf[sunscpal_traceidx];
1933 
1934 	sunscpal_traceidx++;
1935 	if (sunscpal_traceidx >= TRACE_MAX)
1936 		sunscpal_traceidx = 0;
1937 
1938 	tr->msg = msg;
1939 	tr->val = val;
1940 
1941 	splx(s);
1942 }
1943 
1944 #ifdef	DDB
1945 void
sunscpal_clear_trace(void)1946 sunscpal_clear_trace(void)
1947 {
1948 
1949 	sunscpal_traceidx = 0;
1950 	memset((void *)sunscpal_tracebuf, 0, sizeof(sunscpal_tracebuf));
1951 }
1952 
1953 void
sunscpal_show_trace(void)1954 sunscpal_show_trace(void)
1955 {
1956 	struct trace_ent *tr;
1957 	int idx;
1958 
1959 	idx = sunscpal_traceidx;
1960 	do {
1961 		tr = &sunscpal_tracebuf[idx];
1962 		idx++;
1963 		if (idx >= TRACE_MAX)
1964 			idx = 0;
1965 		if (tr->msg)
1966 			db_printf(tr->msg, tr->val);
1967 	} while (idx != sunscpal_traceidx);
1968 }
1969 
1970 void
sunscpal_show_req(struct sunscpal_req * sr)1971 sunscpal_show_req(struct sunscpal_req *sr)
1972 {
1973 	struct scsipi_xfer *xs = sr->sr_xs;
1974 
1975 	db_printf("TID=%d ",	sr->sr_target);
1976 	db_printf("LUN=%d ",	sr->sr_lun);
1977 	db_printf("dh=%p ",	sr->sr_dma_hand);
1978 	db_printf("dptr=%p ",	sr->sr_dataptr);
1979 	db_printf("dlen=0x%x ",	sr->sr_datalen);
1980 	db_printf("flags=%d ",	sr->sr_flags);
1981 	db_printf("stat=%d ",	sr->sr_status);
1982 
1983 	if (xs == NULL) {
1984 		db_printf("(xs=NULL)\n");
1985 		return;
1986 	}
1987 	db_printf("\n");
1988 #ifdef	SCSIDEBUG
1989 	show_scsipi_xs(xs);
1990 #else
1991 	db_printf("xs=%p\n", xs);
1992 #endif
1993 }
1994 
1995 void
sunscpal_show_state(void)1996 sunscpal_show_state(void)
1997 {
1998 	struct sunscpal_softc *sc;
1999 	struct sunscpal_req *sr;
2000 	int i, j, k;
2001 
2002 	sc = sunscpal_debug_sc;
2003 
2004 	if (sc == NULL) {
2005 		db_printf("sunscpal_debug_sc == NULL\n");
2006 		return;
2007 	}
2008 
2009 	db_printf("sc_ncmds=%d\n",  	sc->sc_ncmds);
2010 	k = -1;	/* which is current? */
2011 	for (i = 0; i < SUNSCPAL_OPENINGS; i++) {
2012 		sr = &sc->sc_ring[i];
2013 		if (sr->sr_xs) {
2014 			if (sr == sc->sc_current)
2015 				k = i;
2016 			db_printf("req %d: (sr=%p)", i, sr);
2017 			sunscpal_show_req(sr);
2018 		}
2019 	}
2020 	db_printf("sc_rr=%d, current=%d\n", sc->sc_rr, k);
2021 
2022 	db_printf("Active request matrix:\n");
2023 	for(i = 0; i < 8; i++) {		/* targets */
2024 		for (j = 0; j < 8; j++) {	/* LUN */
2025 			sr = sc->sc_matrix[i][j];
2026 			if (sr) {
2027 				db_printf("TID=%d LUN=%d sr=%p\n", i, j, sr);
2028 			}
2029 		}
2030 	}
2031 
2032 	db_printf("sc_state=0x%x\n",	sc->sc_state);
2033 	db_printf("sc_current=%p\n",	sc->sc_current);
2034 	db_printf("sc_dataptr=%p\n",	sc->sc_dataptr);
2035 	db_printf("sc_datalen=0x%x\n",	sc->sc_datalen);
2036 
2037 	db_printf("sc_prevphase=%d\n",	sc->sc_prevphase);
2038 	db_printf("sc_msgpriq=0x%x\n",	sc->sc_msgpriq);
2039 }
2040 #endif	/* DDB */
2041 #endif	/* SUNSCPAL_DEBUG */
2042 
2043 void
sunscpal_attach(struct sunscpal_softc * sc,int options)2044 sunscpal_attach(struct sunscpal_softc *sc, int options)
2045 {
2046 
2047 	/*
2048 	 * Handle our options.
2049 	 */
2050 	aprint_normal(": options=0x%x\n", options);
2051 	sc->sc_parity_disable = (options & SUNSCPAL_OPT_NO_PARITY_CHK);
2052 	if (options & SUNSCPAL_OPT_DISABLE_DMA)
2053 		sc->sc_flags |= SUNSCPAL_DISABLE_DMA;
2054 
2055 	/*
2056 	 * Fill in the adapter.
2057 	 */
2058 	memset(&sc->sc_adapter, 0, sizeof(sc->sc_adapter));
2059 	sc->sc_adapter.adapt_dev = sc->sc_dev;
2060 	sc->sc_adapter.adapt_nchannels = 1;
2061 	sc->sc_adapter.adapt_openings = SUNSCPAL_OPENINGS;
2062 	sc->sc_adapter.adapt_max_periph = 1;
2063 	sc->sc_adapter.adapt_request = sunscpal_scsipi_request;
2064 	sc->sc_adapter.adapt_minphys = sunscpal_minphys;
2065 	if (options & SUNSCPAL_OPT_FORCE_POLLING)
2066 		sc->sc_adapter.adapt_flags |= SCSIPI_ADAPT_POLL_ONLY;
2067 
2068 	sc->sc_channel.chan_adapter = &sc->sc_adapter;
2069 	sc->sc_channel.chan_bustype = &scsi_bustype;
2070 	sc->sc_channel.chan_channel = 0;
2071 	sc->sc_channel.chan_ntargets = 8;
2072 	sc->sc_channel.chan_nluns = 8;
2073 	sc->sc_channel.chan_id = 7;
2074 
2075 	/*
2076 	 * Add reference to adapter so that we drop the reference after
2077 	 * config_found() to make sure the adapter is disabled.
2078 	 */
2079 	if (scsipi_adapter_addref(&sc->sc_adapter) != 0) {
2080 		aprint_error_dev(sc->sc_dev, "unable to enable controller\n");
2081 		return;
2082 	}
2083 
2084 	sunscpal_init(sc);	/* Init chip and driver */
2085 	sunscpal_reset_scsibus(sc);
2086 
2087 	/*
2088 	 * Ask the adapter what subunits are present
2089 	 */
2090 	(void)config_found(sc->sc_dev, &sc->sc_channel, scsiprint, CFARGS_NONE);
2091 	scsipi_adapter_delref(&sc->sc_adapter);
2092 }
2093 
2094 int
sunscpal_detach(struct sunscpal_softc * sc,int flags)2095 sunscpal_detach(struct sunscpal_softc *sc, int flags)
2096 {
2097 
2098 	return EOPNOTSUPP;
2099 }
2100 
2101 static void
sunscpal_minphys(struct buf * bp)2102 sunscpal_minphys(struct buf *bp)
2103 {
2104 
2105 	if (bp->b_bcount > SUNSCPAL_MAX_DMA_LEN) {
2106 #ifdef	SUNSCPAL_DEBUG
2107 		if (sunscpal_debug & SUNSCPAL_DBG_DMA) {
2108 			printf("%s: len = 0x%lx.\n", __func__, bp->b_bcount);
2109 			Debugger();
2110 		}
2111 #endif
2112 		bp->b_bcount = SUNSCPAL_MAX_DMA_LEN;
2113 	}
2114 	return minphys(bp);
2115 }
2116 
2117 #ifdef SUNSCPAL_USE_BUS_DMA
2118 
2119 /*
2120  * Allocate a DMA handle and put it in sr->sr_dma_hand.  Prepare
2121  * for DMA transfer.
2122  */
2123 static void
sunscpal_dma_alloc(struct sunscpal_softc * sc)2124 sunscpal_dma_alloc(struct sunscpal_softc *sc)
2125 {
2126 	struct sunscpal_req *sr = sc->sc_current;
2127 	sunscpal_dma_handle_t dh;
2128 	int i, xlen;
2129 	u_long addr;
2130 
2131 #ifdef	DIAGNOSTIC
2132 	if (sr->sr_dma_hand != NULL)
2133 		panic("%s: already have DMA handle", __func__);
2134 #endif
2135 
2136 	addr = (u_long)sc->sc_dataptr;
2137 	xlen = sc->sc_datalen;
2138 
2139 	/* If the DMA start addr is misaligned then do PIO */
2140 	if ((addr & 1) || (xlen & 1)) {
2141 		printf("%s: misaligned.\n", __func__);
2142 		return;
2143 	}
2144 
2145 	/* Make sure our caller checked sc_min_dma_len. */
2146 	if (xlen < sc->sc_min_dma_len)
2147 		panic("%s: xlen=0x%x", __func__, xlen);
2148 
2149 	/*
2150 	 * Never attempt single transfers of more than 63k, because
2151 	 * our count register is only 16 bits.
2152 	 * This should never happen since already bounded by minphys().
2153 	 * XXX - Should just segment these...
2154 	 */
2155 	if (xlen > SUNSCPAL_MAX_DMA_LEN) {
2156 		printf("%s: excessive xlen=0x%x\n", __func__, xlen);
2157 		Debugger();
2158 		sc->sc_datalen = xlen = SUNSCPAL_MAX_DMA_LEN;
2159 	}
2160 
2161 	/* Find free DMA handle.  Guaranteed to find one since we have
2162 	   as many DMA handles as the driver has processes. */
2163 	for (i = 0; i < SUNSCPAL_OPENINGS; i++) {
2164 		if ((sc->sc_dma_handles[i].dh_flags & SUNSCDH_BUSY) == 0)
2165 			goto found;
2166 	}
2167 	panic("%s: no free DMA handles.", device_xname(sc->sc_dev));
2168  found:
2169 
2170 	dh = &sc->sc_dma_handles[i];
2171 	dh->dh_flags = SUNSCDH_BUSY;
2172 	dh->dh_mapaddr = (uint8_t *)addr;
2173 	dh->dh_maplen  = xlen;
2174 	dh->dh_dvma = 0;
2175 
2176 	/* Load the DMA map. */
2177 	if (bus_dmamap_load(sc->sunscpal_dmat, dh->dh_dmamap,
2178 	    dh->dh_mapaddr, dh->dh_maplen, NULL, BUS_DMA_NOWAIT) != 0) {
2179 		/* Can't load map */
2180 		printf("%s: can't DMA %p/0x%x\n", __func__,
2181 		    dh->dh_mapaddr, dh->dh_maplen);
2182 		dh->dh_flags = 0;
2183 		return;
2184 	}
2185 
2186 	/* success */
2187 	sr->sr_dma_hand = dh;
2188 }
2189 
2190 static void
sunscpal_dma_free(struct sunscpal_softc * sc)2191 sunscpal_dma_free(struct sunscpal_softc *sc)
2192 {
2193 	struct sunscpal_req *sr = sc->sc_current;
2194 	sunscpal_dma_handle_t dh = sr->sr_dma_hand;
2195 
2196 #ifdef	DIAGNOSTIC
2197 	if (dh == NULL)
2198 		panic("%s: no DMA handle", __func__);
2199 #endif
2200 
2201 	if (sc->sc_state & SUNSCPAL_DOINGDMA)
2202 		panic("%s: free while in progress", __func__);
2203 
2204 	if (dh->dh_flags & SUNSCDH_BUSY) {
2205 		/* XXX - Should separate allocation and mapping. */
2206 		/* Give back the DVMA space. */
2207 		bus_dmamap_unload(sc->sunscpal_dmat, dh->dh_dmamap);
2208 		dh->dh_flags = 0;
2209 	}
2210 	sr->sr_dma_hand = NULL;
2211 }
2212 
2213 /*
2214  * This function is called during the SELECT phase that
2215  * precedes a COMMAND phase, in case we need to setup the
2216  * DMA engine before the bus enters a DATA phase.
2217  *
2218  * On the sc version, setup the start address and the count.
2219  */
2220 static void
sunscpal_dma_setup(struct sunscpal_softc * sc)2221 sunscpal_dma_setup(struct sunscpal_softc *sc)
2222 {
2223 	struct sunscpal_req *sr = sc->sc_current;
2224 	struct scsipi_xfer *xs = sr->sr_xs;
2225 	sunscpal_dma_handle_t dh = sr->sr_dma_hand;
2226 	long data_pa;
2227 	int xlen;
2228 
2229 	/*
2230 	 * Get the DVMA mapping for this segment.
2231 	 * XXX - Should separate allocation and mapin.
2232 	 */
2233 	data_pa = dh->dh_dvma;
2234 	data_pa += (sc->sc_dataptr - dh->dh_mapaddr);
2235 	if (data_pa & 1)
2236 		panic("%s: bad pa=0x%lx", __func__, data_pa);
2237 	xlen = sc->sc_datalen;
2238 	if (xlen & 1)
2239 		panic("%s: bad xlen=0x%x", __func__, xlen);
2240 	sc->sc_reqlen = xlen; 	/* XXX: or less? */
2241 
2242 #ifdef	SUNSCPAL_DEBUG
2243 	if (sunscpal_debug & SUNSCPAL_DBG_DMA) {
2244 		printf("%s: dh=%p, pa=0x%lx, xlen=0x%x\n",
2245 		    __func__, dh, data_pa, xlen);
2246 	}
2247 #endif
2248 
2249 	/* sync the DMA map: */
2250 	bus_dmamap_sync(sc->sunscpal_dmat, dh->dh_dmamap, 0, dh->dh_maplen,
2251 	    ((xs->xs_control & XS_CTL_DATA_OUT) == 0 ?
2252 	    BUS_DMASYNC_PREREAD : BUS_DMASYNC_PREWRITE));
2253 
2254 	/* Load the start address and the count. */
2255 	SUNSCPAL_WRITE_2(sc, sunscpal_dma_addr_h, (data_pa >> 16) & 0xFFFF);
2256 	SUNSCPAL_WRITE_2(sc, sunscpal_dma_addr_l, (data_pa >> 0) & 0xFFFF);
2257 	SUNSCPAL_WRITE_2(sc, sunscpal_dma_count, SUNSCPAL_DMA_COUNT_FLIP(xlen));
2258 }
2259 
2260 #endif /* SUNSCPAL_USE_BUS_DMA */
2261