1/*	$NetBSD: sbic.c,v 1.69 2010/12/20 00:25:26 matt Exp $ */
2
3/*
4 * Copyright (c) 1990 The Regents of the University of California.
5 * All rights reserved.
6 *
7 * This code is derived from software contributed to Berkeley by
8 * Van Jacobson of Lawrence Berkeley Laboratory.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 *    notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 *    notice, this list of conditions and the following disclaimer in the
17 *    documentation and/or other materials provided with the distribution.
18 * 3. Neither the name of the University nor the names of its contributors
19 *    may be used to endorse or promote products derived from this software
20 *    without specific prior written permission.
21 *
22 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
23 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
24 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
25 * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
26 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
27 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
28 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
29 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
31 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32 * SUCH DAMAGE.
33 *
34 *	@(#)scsi.c	7.5 (Berkeley) 5/4/91
35 */
36
37/*
38 * Copyright (c) 1994 Christian E. Hopps
39 *
40 * This code is derived from software contributed to Berkeley by
41 * Van Jacobson of Lawrence Berkeley Laboratory.
42 *
43 * Redistribution and use in source and binary forms, with or without
44 * modification, are permitted provided that the following conditions
45 * are met:
46 * 1. Redistributions of source code must retain the above copyright
47 *    notice, this list of conditions and the following disclaimer.
48 * 2. Redistributions in binary form must reproduce the above copyright
49 *    notice, this list of conditions and the following disclaimer in the
50 *    documentation and/or other materials provided with the distribution.
51 * 3. All advertising materials mentioning features or use of this software
52 *    must display the following acknowledgement:
53 *	This product includes software developed by the University of
54 *	California, Berkeley and its contributors.
55 * 4. Neither the name of the University nor the names of its contributors
56 *    may be used to endorse or promote products derived from this software
57 *    without specific prior written permission.
58 *
59 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
60 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
61 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
62 * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
63 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
64 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
65 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
66 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
67 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
68 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
69 * SUCH DAMAGE.
70 *
71 *	@(#)scsi.c	7.5 (Berkeley) 5/4/91
72 */
73
74/*
75 * AMIGA AMD 33C93 scsi adaptor driver
76 */
77
78#include "opt_ddb.h"
79#ifdef __m68k__
80#include "opt_m68k_arch.h"
81#endif
82
83#include <sys/cdefs.h>
84__KERNEL_RCSID(0, "$NetBSD: sbic.c,v 1.69 2010/12/20 00:25:26 matt Exp $");
85
86#include <sys/param.h>
87#include <sys/systm.h>
88#include <sys/device.h>
89#include <sys/kernel.h> /* For hz */
90#include <sys/disklabel.h>
91#include <sys/buf.h>
92#include <dev/scsipi/scsi_all.h>
93#include <dev/scsipi/scsipi_all.h>
94#include <dev/scsipi/scsiconf.h>
95#include <machine/cpu.h>
96#include <amiga/amiga/device.h>
97#include <amiga/amiga/custom.h>
98#include <amiga/amiga/isr.h>
99#include <amiga/dev/dmavar.h>
100#include <amiga/dev/sbicreg.h>
101#include <amiga/dev/sbicvar.h>
102
103/* These are for bounce buffers */
104#include <amiga/amiga/cc.h>
105#include <amiga/dev/zbusvar.h>
106
107/* Since I can't find this in any other header files */
108#define SCSI_PHASE(reg)	(reg&0x07)
109
110/*
111 * SCSI delays
112 * In u-seconds, primarily for state changes on the SPC.
113 */
114#define	SBIC_CMD_WAIT	50000	/* wait per step of 'immediate' cmds */
115#define	SBIC_DATA_WAIT	50000	/* wait per data in/out step */
116#define	SBIC_INIT_WAIT	50000	/* wait per step (both) during init */
117
118#define SBIC_WAIT(regs, until, timeo) sbicwait(regs, until, timeo, __LINE__)
119
120int  sbicicmd(struct sbic_softc *, int, int, void *, int, void *, int);
121int  sbicgo(struct sbic_softc *, struct scsipi_xfer *);
122int  sbicdmaok(struct sbic_softc *, struct scsipi_xfer *);
123int  sbicwait(sbic_regmap_t, char, int , int);
124int  sbiccheckdmap(void *, u_long, u_long);
125int  sbicselectbus(struct sbic_softc *, sbic_regmap_t, u_char, u_char, u_char);
126int  sbicxfstart(sbic_regmap_t, int, u_char, int);
127int  sbicxfout(sbic_regmap_t regs, int, void *, int);
128int  sbicfromscsiperiod(struct sbic_softc *, sbic_regmap_t, int);
129int  sbictoscsiperiod(struct sbic_softc *, sbic_regmap_t, int);
130int  sbicpoll(struct sbic_softc *);
131int  sbicnextstate(struct sbic_softc *, u_char, u_char);
132int  sbicmsgin(struct sbic_softc *);
133int  sbicxfin(sbic_regmap_t regs, int, void *);
134int  sbicabort(struct sbic_softc *, sbic_regmap_t, const char *);
135void sbicxfdone(struct sbic_softc *, sbic_regmap_t, int);
136void sbicerror(struct sbic_softc *, sbic_regmap_t, u_char);
137void sbicstart(struct sbic_softc *);
138void sbicreset(struct sbic_softc *);
139void sbic_scsidone(struct sbic_acb *, int);
140void sbic_sched(struct sbic_softc *);
141void sbic_save_ptrs(struct sbic_softc *, sbic_regmap_t,int,int);
142void sbic_load_ptrs(struct sbic_softc *, sbic_regmap_t,int,int);
143#ifdef DEBUG
144void sbicdumpstate(void);
145void sbic_dump_acb(struct sbic_acb *);
146#endif
147
148/*
149 * Synch xfer parameters, and timing conversions
150 */
151int sbic_min_period = SBIC_SYN_MIN_PERIOD;  /* in cycles = f(ICLK,FSn) */
152int sbic_max_offset = SBIC_SYN_MAX_OFFSET;  /* pure number */
153
154int sbic_cmd_wait = SBIC_CMD_WAIT;
155int sbic_data_wait = SBIC_DATA_WAIT;
156int sbic_init_wait = SBIC_INIT_WAIT;
157
158/*
159 * was broken before.. now if you want this you get it for all drives
160 * on sbic controllers.
161 */
162u_char sbic_inhibit_sync[8];
163int sbic_enable_reselect = 1;
164int sbic_clock_override = 0;
165int sbic_no_dma = 0;
166int sbic_parallel_operations = 1;
167
168#ifdef DEBUG
169sbic_regmap_t debug_sbic_regs;
170int	sbicdma_ops = 0;	/* total DMA operations */
171int	sbicdma_bounces = 0;	/* number operations using bounce buffer */
172int	sbicdma_hits = 0;	/* number of DMA chains that were contiguous */
173int	sbicdma_misses = 0;	/* number of DMA chains that were not contiguous */
174int     sbicdma_saves = 0;
175#define QPRINTF(a) if (sbic_debug > 1) printf a
176int	sbic_debug = 0;
177int	sync_debug = 0;
178int	sbic_dma_debug = 0;
179int	reselect_debug = 0;
180int	data_pointer_debug = 0;
181u_char	debug_asr, debug_csr, routine;
182void sbictimeout(struct sbic_softc *dev);
183
184#define CSR_TRACE_SIZE 32
185#if CSR_TRACE_SIZE
186#define CSR_TRACE(w,c,a,x) do { \
187	int s_csr_trace = splbio(); \
188	csr_trace[csr_traceptr].whr = (w); csr_trace[csr_traceptr].csr = (c); \
189	csr_trace[csr_traceptr].asr = (a); csr_trace[csr_traceptr].xtn = (x); \
190	dma_cachectl((void *)&csr_trace[csr_traceptr], sizeof(csr_trace[0])); \
191	csr_traceptr = (csr_traceptr + 1) & (CSR_TRACE_SIZE - 1); \
192/*	dma_cachectl((void *)&csr_traceptr, sizeof(csr_traceptr));*/ \
193	splx(s_csr_trace); \
194} while (0)
195int csr_traceptr;
196int csr_tracesize = CSR_TRACE_SIZE;
197struct {
198	u_char whr;
199	u_char csr;
200	u_char asr;
201	u_char xtn;
202} csr_trace[CSR_TRACE_SIZE];
203#else
204#define CSR_TRACE(w,c,a,x)
205#endif
206
207#define SBIC_TRACE_SIZE 0
208#if SBIC_TRACE_SIZE
209#define SBIC_TRACE(dev) do { \
210	int s = splbio(); \
211	sbic_trace[sbic_traceptr].sp = &s; \
212	sbic_trace[sbic_traceptr].line = __LINE__; \
213	sbic_trace[sbic_traceptr].sr = s; \
214	sbic_trace[sbic_traceptr].csr = csr_traceptr; \
215	dma_cachectl(&sbic_trace[sbic_traceptr], sizeof(sbic_trace[0])); \
216	sbic_traceptr = (sbic_traceptr + 1) & (SBIC_TRACE_SIZE - 1); \
217	dma_cachectl(&sbic_traceptr, sizeof(sbic_traceptr)); \
218	if (dev) dma_cachectl(dev, sizeof(*dev)); \
219	splx(s); \
220} while (0)
221int sbic_traceptr;
222int sbic_tracesize = SBIC_TRACE_SIZE;
223struct {
224	void *sp;
225	u_short line;
226	u_short sr;
227	int csr;
228} sbic_trace[SBIC_TRACE_SIZE];
229#else
230#define SBIC_TRACE(dev)
231#endif
232
233#else	/* DEBUG */
234#define QPRINTF(a)
235#define CSR_TRACE(w,c,a,x)
236#define SBIC_TRACE(dev)
237#endif	/* DEBUG */
238
239/*
240 * default minphys routine for sbic based controllers
241 */
242void
243sbic_minphys(struct buf *bp)
244{
245
246	/*
247	 * No max transfer at this level.
248	 */
249	minphys(bp);
250}
251
252/*
253 * Save DMA pointers.  Take into account partial transfer. Shut down DMA.
254 */
255void
256sbic_save_ptrs(struct sbic_softc *dev, sbic_regmap_t regs, int target, int lun)
257{
258	int count, asr, s;
259	struct sbic_acb* acb;
260
261	SBIC_TRACE(dev);
262	if( !dev->sc_cur ) return;
263	if( !(dev->sc_flags & SBICF_INDMA) ) return; /* DMA not active */
264
265	s = splbio();
266
267	acb = dev->sc_nexus;
268	count = -1;
269	do {
270		GET_SBIC_asr(regs, asr);
271		if( asr & SBIC_ASR_DBR ) {
272			printf("sbic_save_ptrs: asr %02x canceled!\n", asr);
273			splx(s);
274			SBIC_TRACE(dev);
275			return;
276		}
277	} while( asr & (SBIC_ASR_BSY|SBIC_ASR_CIP) );
278
279	/* Save important state */
280	/* must be done before dmastop */
281	acb->sc_dmacmd = dev->sc_dmacmd;
282	SBIC_TC_GET(regs, count);
283
284	/* Shut down DMA ====CAREFUL==== */
285	dev->sc_dmastop(dev);
286	dev->sc_flags &= ~SBICF_INDMA;
287	SBIC_TC_PUT(regs, 0);
288
289#ifdef DEBUG
290	if(!count && sbic_debug) printf("%dcount0",target);
291	if(data_pointer_debug == -1)
292		printf("SBIC saving target %d data pointers from (%p,%x)%xASR:%02x",
293		       target, dev->sc_cur->dc_addr, dev->sc_cur->dc_count,
294		       acb->sc_dmacmd, asr);
295#endif
296
297	/* Fixup partial xfers */
298	acb->sc_kv.dc_addr += (dev->sc_tcnt - count);
299	acb->sc_kv.dc_count -= (dev->sc_tcnt - count);
300	acb->sc_pa.dc_addr += (dev->sc_tcnt - count);
301	acb->sc_pa.dc_count -= ((dev->sc_tcnt - count)>>1);
302
303	acb->sc_tcnt = dev->sc_tcnt = count;
304#ifdef DEBUG
305	if(data_pointer_debug)
306		printf(" at (%p,%x):%x\n",
307		       dev->sc_cur->dc_addr, dev->sc_cur->dc_count,count);
308	sbicdma_saves++;
309#endif
310	splx(s);
311	SBIC_TRACE(dev);
312}
313
314
315/*
316 * DOES NOT RESTART DMA!!!
317 */
318void
319sbic_load_ptrs(struct sbic_softc *dev, sbic_regmap_t regs, int target, int lun)
320{
321	int s, count;
322	char* vaddr, * paddr;
323	struct sbic_acb *acb;
324
325	SBIC_TRACE(dev);
326	acb = dev->sc_nexus;
327	if( !acb->sc_kv.dc_count ) {
328		/* No data to xfer */
329		SBIC_TRACE(dev);
330		return;
331	}
332
333	s = splbio();
334
335	dev->sc_last = dev->sc_cur = &acb->sc_pa;
336	dev->sc_tcnt = acb->sc_tcnt;
337	dev->sc_dmacmd = acb->sc_dmacmd;
338
339#ifdef DEBUG
340	sbicdma_ops++;
341#endif
342	if( !dev->sc_tcnt ) {
343		/* sc_tcnt == 0 implies end of segment */
344
345		/* do kvm to pa mappings */
346		paddr = acb->sc_pa.dc_addr =
347			(char *) kvtop(acb->sc_kv.dc_addr);
348
349		vaddr = acb->sc_kv.dc_addr;
350		count = acb->sc_kv.dc_count;
351		for(count = (PAGE_SIZE - ((int)vaddr & PGOFSET));
352		    count < acb->sc_kv.dc_count
353		    && (char*)kvtop(vaddr + count + 4) == paddr + count + 4;
354		    count += PAGE_SIZE);
355		/* If it's all contiguous... */
356		if(count > acb->sc_kv.dc_count ) {
357			count = acb->sc_kv.dc_count;
358#ifdef DEBUG
359			sbicdma_hits++;
360#endif
361		} else {
362#ifdef DEBUG
363			sbicdma_misses++;
364#endif
365		}
366		acb->sc_tcnt = count;
367		acb->sc_pa.dc_count = count >> 1;
368
369#ifdef DEBUG
370		if(data_pointer_debug)
371			printf("DMA recalc:kv(%p,%x)pa(%p,%lx)\n",
372			       acb->sc_kv.dc_addr,
373			       acb->sc_kv.dc_count,
374			       acb->sc_pa.dc_addr,
375			       acb->sc_tcnt);
376#endif
377	}
378	splx(s);
379#ifdef DEBUG
380	if(data_pointer_debug)
381		printf("SBIC restoring target %d data pointers at (%p,%x)%x\n",
382		       target, dev->sc_cur->dc_addr, dev->sc_cur->dc_count,
383		       dev->sc_dmacmd);
384#endif
385	SBIC_TRACE(dev);
386}
387
388/*
389 * used by specific sbic controller
390 *
391 * it appears that the higher level code does nothing with LUN's
392 * so I will too.  I could plug it in, however so could they
393 * in scsi_scsipi_cmd().
394 */
395void
396sbic_scsipi_request(struct scsipi_channel *chan, scsipi_adapter_req_t req,
397                    void *arg)
398{
399	struct scsipi_xfer *xs;
400	struct scsipi_periph *periph;
401	struct sbic_acb *acb;
402	struct sbic_softc *dev = (void *)chan->chan_adapter->adapt_dev;
403	int flags, s, stat;
404
405	switch (req) {
406	case ADAPTER_REQ_RUN_XFER:
407		xs = arg;
408		periph = xs->xs_periph;
409
410		SBIC_TRACE(dev);
411		flags = xs->xs_control;
412
413		if (flags & XS_CTL_DATA_UIO)
414			panic("sbic: scsi data uio requested");
415
416		if (dev->sc_nexus && flags & XS_CTL_POLL)
417			panic("sbic_scsipi_request: busy");
418
419		s = splbio();
420		acb = dev->free_list.tqh_first;
421		if (acb)
422			TAILQ_REMOVE(&dev->free_list, acb, chain);
423		splx(s);
424
425#ifdef DIAGNOSTIC
426		if (acb == NULL) {
427			scsipi_printaddr(periph);
428			printf("unable to allocate acb\n");
429			panic("sbic_scsipi_request");
430		}
431#endif
432		acb->flags = ACB_ACTIVE;
433		if (flags & XS_CTL_DATA_IN)
434			acb->flags |= ACB_DATAIN;
435		acb->xs = xs;
436		memcpy(&acb->cmd, xs->cmd, xs->cmdlen);
437		acb->clen = xs->cmdlen;
438		acb->sc_kv.dc_addr = xs->data;
439		acb->sc_kv.dc_count = xs->datalen;
440		acb->pa_addr = xs->data ? (char *)kvtop(xs->data) : 0;	/* XXXX check */
441
442		if (flags & XS_CTL_POLL) {
443			s = splbio();
444			/*
445			 * This has major side effects - it locks up the machine
446			 */
447
448			dev->sc_flags |= SBICF_ICMD;
449			do {
450				while(dev->sc_nexus)
451					sbicpoll(dev);
452				dev->sc_nexus = acb;
453				dev->sc_stat[0] = -1;
454				dev->sc_xs = xs;
455				dev->target = periph->periph_target;
456				dev->lun = periph->periph_lun;
457				stat = sbicicmd(dev, dev->target, dev->lun,
458					&acb->cmd, acb->clen,
459					acb->sc_kv.dc_addr, acb->sc_kv.dc_count);
460			} while (dev->sc_nexus != acb);
461			sbic_scsidone(acb, stat);
462
463			splx(s);
464			SBIC_TRACE(dev);
465			return;
466		}
467
468		s = splbio();
469		TAILQ_INSERT_TAIL(&dev->ready_list, acb, chain);
470
471		if (dev->sc_nexus) {
472			splx(s);
473			SBIC_TRACE(dev);
474			return;
475		}
476
477		/*
478		 * nothing is active, try to start it now.
479		 */
480		sbic_sched(dev);
481		splx(s);
482
483		SBIC_TRACE(dev);
484/* TODO:  add sbic_poll to do XS_CTL_POLL operations */
485#if 0
486		if (flags & XS_CTL_POLL)
487			return(COMPLETE);
488#endif
489		return;
490
491	case ADAPTER_REQ_GROW_RESOURCES:
492		return;
493
494	case ADAPTER_REQ_SET_XFER_MODE:
495		return;
496	}
497}
498
499/*
500 * attempt to start the next available command
501 */
502void
503sbic_sched(struct sbic_softc *dev)
504{
505	struct scsipi_xfer *xs;
506	struct scsipi_periph *periph;
507	struct sbic_acb *acb;
508	int flags, /*phase,*/ stat, i;
509
510	SBIC_TRACE(dev);
511	if (dev->sc_nexus)
512		return;			/* a command is current active */
513
514	SBIC_TRACE(dev);
515	for (acb = dev->ready_list.tqh_first; acb; acb = acb->chain.tqe_next) {
516		periph = acb->xs->xs_periph;
517		i = periph->periph_target;
518		if (!(dev->sc_tinfo[i].lubusy & (1 << periph->periph_lun))) {
519			struct sbic_tinfo *ti = &dev->sc_tinfo[i];
520
521			TAILQ_REMOVE(&dev->ready_list, acb, chain);
522			dev->sc_nexus = acb;
523			ti = &dev->sc_tinfo[periph->periph_target];
524			ti->lubusy |= (1 << periph->periph_lun);
525			acb->sc_pa.dc_addr = acb->pa_addr;	/* XXXX check */
526			break;
527		}
528	}
529
530	SBIC_TRACE(dev);
531	if (acb == NULL)
532		return;			/* did not find an available command */
533
534	dev->sc_xs = xs = acb->xs;
535	periph = xs->xs_periph;
536	flags = xs->xs_control;
537
538	if (flags & XS_CTL_RESET)
539		sbicreset(dev);
540
541#ifdef DEBUG
542	if( data_pointer_debug > 1 )
543		printf("sbic_sched(%d,%d)\n", periph->periph_target,
544			periph->periph_lun);
545#endif
546	dev->sc_stat[0] = -1;
547	dev->target = periph->periph_target;
548	dev->lun = periph->periph_lun;
549	if ( flags & XS_CTL_POLL || ( !sbic_parallel_operations
550				   && (sbicdmaok(dev, xs) == 0)))
551		stat = sbicicmd(dev, periph->periph_target,
552			periph->periph_lun, &acb->cmd,
553		    acb->clen, acb->sc_kv.dc_addr, acb->sc_kv.dc_count);
554	else if (sbicgo(dev, xs) == 0 && xs->error != XS_SELTIMEOUT) {
555		SBIC_TRACE(dev);
556		return;
557	} else
558		stat = dev->sc_stat[0];
559
560	sbic_scsidone(acb, stat);
561	SBIC_TRACE(dev);
562}
563
564void
565sbic_scsidone(struct sbic_acb *acb, int stat)
566{
567	struct scsipi_xfer *xs;
568	struct scsipi_periph *periph;
569	struct sbic_softc *dev;
570	int dosched = 0;
571
572	xs = acb->xs;
573	periph = xs->xs_periph;
574	dev = (void *)periph->periph_channel->chan_adapter->adapt_dev;
575	SBIC_TRACE(dev);
576#ifdef DIAGNOSTIC
577	if (acb == NULL || xs == NULL) {
578		printf("sbic_scsidone -- (%d,%d) no scsi_xfer\n",
579		       dev->target, dev->lun);
580#ifdef DDB
581		Debugger();
582#endif
583		return;
584	}
585#endif
586
587	xs->status = stat;
588	xs->resid = 0;		/* XXXX */
589#ifdef DEBUG
590	if( data_pointer_debug > 1 )
591		printf("scsidone: (%d,%d)->(%d,%d)%02x\n",
592		       periph->periph_target, periph->periph_lun,
593		       dev->target,  dev->lun,  stat);
594	if( periph->periph_target ==
595		periph->periph_channel->chan_id)
596		panic("target == hostid");
597#endif
598
599	if (xs->error == XS_NOERROR) {
600		if (stat == SCSI_CHECK || stat == SCSI_BUSY)
601			xs->error = XS_BUSY;
602	}
603
604	/*
605	 * Remove the ACB from whatever queue it's on.  We have to do a bit of
606	 * a hack to figure out which queue it's on.  Note that it is *not*
607	 * necessary to cdr down the ready queue, but we must cdr down the
608	 * nexus queue and see if it's there, so we can mark the unit as no
609	 * longer busy.  This code is sickening, but it works.
610	 */
611	if (acb == dev->sc_nexus) {
612		dev->sc_nexus = NULL;
613		dev->sc_xs = NULL;
614		dev->sc_tinfo[periph->periph_target].lubusy &=
615			~(1<<periph->periph_lun);
616		if (dev->ready_list.tqh_first)
617			dosched = 1;	/* start next command */
618	} else if (dev->ready_list.tqh_last == &acb->chain.tqe_next) {
619		TAILQ_REMOVE(&dev->ready_list, acb, chain);
620	} else {
621		register struct sbic_acb *acb2;
622		for (acb2 = dev->nexus_list.tqh_first; acb2;
623		    acb2 = acb2->chain.tqe_next) {
624			if (acb2 == acb) {
625				TAILQ_REMOVE(&dev->nexus_list, acb, chain);
626				dev->sc_tinfo[periph->periph_target].lubusy
627					&= ~(1<<periph->periph_lun);
628				break;
629			}
630		}
631		if (acb2)
632			;
633		else if (acb->chain.tqe_next) {
634			TAILQ_REMOVE(&dev->ready_list, acb, chain);
635		} else {
636			printf("%s: can't find matching acb\n",
637			    dev->sc_dev.dv_xname);
638#ifdef DDB
639			Debugger();
640#endif
641		}
642	}
643	/* Put it on the free list. */
644	acb->flags = ACB_FREE;
645	TAILQ_INSERT_HEAD(&dev->free_list, acb, chain);
646
647	dev->sc_tinfo[periph->periph_target].cmds++;
648
649	scsipi_done(xs);
650
651	if (dosched)
652		sbic_sched(dev);
653	SBIC_TRACE(dev);
654}
655
656int
657sbicdmaok(struct sbic_softc *dev, struct scsipi_xfer *xs)
658{
659	if (sbic_no_dma || !xs->datalen || xs->datalen & 0x1 ||
660	    (u_int)xs->data & 0x3)
661		return(0);
662	/*
663	 * controller supports dma to any addresses?
664	 */
665	else if ((dev->sc_flags & SBICF_BADDMA) == 0)
666		return(1);
667	/*
668	 * this address is ok for DMA?
669	 */
670	else if (sbiccheckdmap(xs->data, xs->datalen, dev->sc_dmamask) == 0)
671		return(1);
672	/*
673	 * we have a bounce buffer?
674	 */
675	else if (dev->sc_tinfo[xs->xs_periph->periph_target].bounce)
676		return(1);
677	/*
678	 * try to get one
679	 */
680	else if ((dev->sc_tinfo[xs->xs_periph->periph_target].bounce
681		 = (char *)alloc_z2mem(MAXPHYS))) {
682		if (isztwomem(dev->sc_tinfo[xs->xs_periph->periph_target].bounce))
683			printf("alloc ZII target %d bounce pa 0x%x\n",
684			       xs->xs_periph->periph_target,
685			       (unsigned)kvtop(dev->sc_tinfo[xs->xs_periph->periph_target].bounce));
686		else if (dev->sc_tinfo[xs->xs_periph->periph_target].bounce)
687			printf("alloc CHIP target %d bounce pa %p\n",
688			       xs->xs_periph->periph_target,
689			       PREP_DMA_MEM(dev->sc_tinfo[xs->xs_periph->periph_target].bounce));
690		return(1);
691	}
692
693	return(0);
694}
695
696
697int
698sbicwait(sbic_regmap_t regs, char until, int timeo, int line)
699{
700	u_char val;
701	int csr;
702
703	SBIC_TRACE((struct sbic_softc *)0);
704	if (timeo == 0)
705		timeo = 1000000;	/* some large value.. */
706
707	GET_SBIC_asr(regs,val);
708	while ((val & until) == 0) {
709		if (timeo-- == 0) {
710			GET_SBIC_csr(regs, csr);
711			printf("sbicwait TIMEO @%d with asr=x%x csr=x%x\n",
712			    line, val, csr);
713#if defined(DDB) && defined(DEBUG)
714			Debugger();
715#endif
716			return(val); /* Maybe I should abort */
717			break;
718		}
719		DELAY(1);
720		GET_SBIC_asr(regs,val);
721	}
722	SBIC_TRACE((struct sbic_softc *)0);
723	return(val);
724}
725
726int
727sbicabort(struct sbic_softc *dev, sbic_regmap_t regs, const char *where)
728{
729	u_char csr, asr;
730
731	GET_SBIC_asr(regs, asr);
732	GET_SBIC_csr(regs, csr);
733
734	printf ("%s: abort %s: csr = 0x%02x, asr = 0x%02x\n",
735	    dev->sc_dev.dv_xname, where, csr, asr);
736
737
738#if 0
739	/* Clean up running command */
740	if (dev->sc_nexus != NULL) {
741		dev->sc_nexus->xs->error = XS_DRIVER_STUFFUP;
742		sbic_scsidone(dev->sc_nexus, dev->sc_stat[0]);
743	}
744	while (acb = dev->nexus_list.tqh_first) {
745		acb->xs->error = XS_DRIVER_STUFFUP;
746		sbic_scsidone(acb, -1 /*acb->stat[0]*/);
747	}
748#endif
749
750	/* Clean up chip itself */
751	if (dev->sc_flags & SBICF_SELECTED) {
752		while( asr & SBIC_ASR_DBR ) {
753			/* sbic is jammed w/data. need to clear it */
754			/* But we don't know what direction it needs to go */
755			GET_SBIC_data(regs, asr);
756			printf("%s: abort %s: clearing data buffer 0x%02x\n",
757			       dev->sc_dev.dv_xname, where, asr);
758			GET_SBIC_asr(regs, asr);
759			if( asr & SBIC_ASR_DBR ) /* Not the read direction, then */
760				SET_SBIC_data(regs, asr);
761			GET_SBIC_asr(regs, asr);
762		}
763		WAIT_CIP(regs);
764printf("%s: sbicabort - sending ABORT command\n", dev->sc_dev.dv_xname);
765		SET_SBIC_cmd(regs, SBIC_CMD_ABORT);
766		WAIT_CIP(regs);
767
768		GET_SBIC_asr(regs, asr);
769		if (asr & (SBIC_ASR_BSY|SBIC_ASR_LCI)) {
770			/* ok, get more drastic.. */
771
772printf("%s: sbicabort - asr %x, trying to reset\n", dev->sc_dev.dv_xname, asr);
773			sbicreset(dev);
774			dev->sc_flags &= ~SBICF_SELECTED;
775			return -1;
776		}
777printf("%s: sbicabort - sending DISC command\n", dev->sc_dev.dv_xname);
778		SET_SBIC_cmd(regs, SBIC_CMD_DISC);
779
780		do {
781			asr = SBIC_WAIT (regs, SBIC_ASR_INT, 0);
782			GET_SBIC_csr (regs, csr);
783			CSR_TRACE('a',csr,asr,0);
784		} while ((csr != SBIC_CSR_DISC) && (csr != SBIC_CSR_DISC_1)
785		    && (csr != SBIC_CSR_CMD_INVALID));
786
787		/* lets just hope it worked.. */
788		dev->sc_flags &= ~SBICF_SELECTED;
789	}
790	return -1;
791}
792
793
794/*
795 * Initialize driver-private structures
796 */
797
798void
799sbicinit(struct sbic_softc *dev)
800{
801	sbic_regmap_t regs;
802	u_int i;
803	struct sbic_acb *acb;
804	u_int inhibit_sync;
805
806	extern u_long scsi_nosync;
807	extern int shift_nosync;
808
809	regs = dev->sc_sbic;
810
811	if ((dev->sc_flags & SBICF_ALIVE) == 0) {
812		TAILQ_INIT(&dev->ready_list);
813		TAILQ_INIT(&dev->nexus_list);
814		TAILQ_INIT(&dev->free_list);
815		callout_init(&dev->sc_timo_ch, 0);
816		dev->sc_nexus = NULL;
817		dev->sc_xs = NULL;
818		acb = dev->sc_acb;
819		memset(acb, 0, sizeof(dev->sc_acb));
820		for (i = 0; i < sizeof(dev->sc_acb) / sizeof(*acb); i++) {
821			TAILQ_INSERT_TAIL(&dev->free_list, acb, chain);
822			acb++;
823		}
824		memset(dev->sc_tinfo, 0, sizeof(dev->sc_tinfo));
825#ifdef DEBUG
826		/* make sure timeout is really not needed */
827		callout_reset(&dev->sc_timo_ch, 30 * hz,
828		    (void *)sbictimeout, dev);
829#endif
830
831	} else panic("sbic: reinitializing driver!");
832
833	dev->sc_flags |= SBICF_ALIVE;
834	dev->sc_flags &= ~SBICF_SELECTED;
835
836	/* initialize inhibit array */
837	if (scsi_nosync) {
838		inhibit_sync = (scsi_nosync >> shift_nosync) & 0xff;
839		shift_nosync += 8;
840#ifdef DEBUG
841		if (inhibit_sync)
842			printf("%s: Inhibiting synchronous transfer %02x\n",
843				dev->sc_dev.dv_xname, inhibit_sync);
844#endif
845		for (i = 0; i < 8; ++i)
846			if (inhibit_sync & (1 << i))
847				sbic_inhibit_sync[i] = 1;
848	}
849
850	sbicreset(dev);
851}
852
853void
854sbicreset(struct sbic_softc *dev)
855{
856	sbic_regmap_t regs;
857	u_int my_id, s;
858	u_char csr;
859#if 0
860	u_int i;
861	struct sbic_acb *acb;
862#endif
863
864	regs = dev->sc_sbic;
865#if 0
866	if (dev->sc_flags & SBICF_ALIVE) {
867		SET_SBIC_cmd(regs, SBIC_CMD_ABORT);
868		WAIT_CIP(regs);
869	}
870#else
871		SET_SBIC_cmd(regs, SBIC_CMD_ABORT);
872		WAIT_CIP(regs);
873#endif
874	s = splbio();
875	my_id = dev->sc_channel.chan_id & SBIC_ID_MASK;
876
877	/* Enable advanced mode */
878	my_id |= SBIC_ID_EAF /*| SBIC_ID_EHP*/ ;
879	SET_SBIC_myid(regs, my_id);
880
881	/*
882	 * Disable interrupts (in dmainit) then reset the chip
883	 */
884	SET_SBIC_cmd(regs, SBIC_CMD_RESET);
885	DELAY(25);
886	SBIC_WAIT(regs, SBIC_ASR_INT, 0);
887	GET_SBIC_csr(regs, csr);       /* clears interrupt also */
888
889	if (dev->sc_clkfreq < 110)
890		my_id |= SBIC_ID_FS_8_10;
891	else if (dev->sc_clkfreq < 160)
892		my_id |= SBIC_ID_FS_12_15;
893	else if (dev->sc_clkfreq < 210)
894		my_id |= SBIC_ID_FS_16_20;
895
896	SET_SBIC_myid(regs, my_id);
897
898	/*
899	 * Set up various chip parameters
900	 */
901	SET_SBIC_control(regs, SBIC_CTL_EDI | SBIC_CTL_IDI /* | SBIC_CTL_HSP */
902	    | SBIC_MACHINE_DMA_MODE);
903	/*
904	 * don't allow (re)selection (SBIC_RID_ES)
905	 * until we can handle target mode!!
906	 */
907	SET_SBIC_rselid(regs, SBIC_RID_ER);
908	SET_SBIC_syn(regs, 0);     /* asynch for now */
909
910	/*
911	 * anything else was zeroed by reset
912	 */
913	splx(s);
914
915#if 0
916	if ((dev->sc_flags & SBICF_ALIVE) == 0) {
917		TAILQ_INIT(&dev->ready_list);
918		TAILQ_INIT(&dev->nexus_list);
919		TAILQ_INIT(&dev->free_list);
920		dev->sc_nexus = NULL;
921		dev->sc_xs = NULL;
922		acb = dev->sc_acb;
923		memset(acb, 0, sizeof(dev->sc_acb));
924		for (i = 0; i < sizeof(dev->sc_acb) / sizeof(*acb); i++) {
925			TAILQ_INSERT_TAIL(&dev->free_list, acb, chain);
926			acb++;
927		}
928		memset(dev->sc_tinfo, 0, sizeof(dev->sc_tinfo));
929	} else {
930		if (dev->sc_nexus != NULL) {
931			dev->sc_nexus->xs->error = XS_DRIVER_STUFFUP;
932			sbic_scsidone(dev->sc_nexus, dev->sc_stat[0]);
933		}
934		while (acb = dev->nexus_list.tqh_first) {
935			acb->xs->error = XS_DRIVER_STUFFUP;
936			sbic_scsidone(acb, -1 /*acb->stat[0]*/);
937		}
938	}
939
940	dev->sc_flags |= SBICF_ALIVE;
941#endif
942	dev->sc_flags &= ~SBICF_SELECTED;
943}
944
945void
946sbicerror(struct sbic_softc *dev, sbic_regmap_t regs, u_char csr)
947{
948	struct scsipi_xfer *xs;
949
950	xs = dev->sc_xs;
951
952#ifdef DIAGNOSTIC
953	if (xs == NULL)
954		panic("sbicerror");
955#endif
956	if (xs->xs_control & XS_CTL_SILENT)
957		return;
958
959	printf("%s: ", dev->sc_dev.dv_xname);
960	printf("csr == 0x%02x\n", csr);	/* XXX */
961}
962
963/*
964 * select the bus, return when selected or error.
965 */
966int
967sbicselectbus(struct sbic_softc *dev, sbic_regmap_t regs, u_char target,
968              u_char lun, u_char our_addr)
969{
970	u_char asr, csr, id;
971
972	SBIC_TRACE(dev);
973	QPRINTF(("sbicselectbus %d\n", target));
974
975	/*
976	 * if we're already selected, return (XXXX panic maybe?)
977	 */
978	if (dev->sc_flags & SBICF_SELECTED) {
979		SBIC_TRACE(dev);
980		return(1);
981	}
982
983	/*
984	 * issue select
985	 */
986	SBIC_TC_PUT(regs, 0);
987	SET_SBIC_selid(regs, target);
988	SET_SBIC_timeo(regs, SBIC_TIMEOUT(250,dev->sc_clkfreq));
989
990	/*
991	 * set sync or async
992	 */
993	if (dev->sc_sync[target].state == SYNC_DONE)
994		SET_SBIC_syn(regs, SBIC_SYN (dev->sc_sync[target].offset,
995		    dev->sc_sync[target].period));
996	else
997		SET_SBIC_syn(regs, SBIC_SYN (0, sbic_min_period));
998
999	GET_SBIC_asr(regs, asr);
1000	if( asr & (SBIC_ASR_INT|SBIC_ASR_BSY) ) {
1001		/* This means we got ourselves reselected upon */
1002/*		printf("sbicselectbus: INT/BSY asr %02x\n", asr);*/
1003#ifdef DDB
1004/*		Debugger();*/
1005#endif
1006		SBIC_TRACE(dev);
1007		return 1;
1008	}
1009
1010	SET_SBIC_cmd(regs, SBIC_CMD_SEL_ATN);
1011
1012	/*
1013	 * wait for select (merged from separate function may need
1014	 * cleanup)
1015	 */
1016	WAIT_CIP(regs);
1017	do {
1018		asr = SBIC_WAIT(regs, SBIC_ASR_INT | SBIC_ASR_LCI, 0);
1019		if (asr & SBIC_ASR_LCI) {
1020#ifdef DEBUG
1021			if (reselect_debug)
1022				printf("sbicselectbus: late LCI asr %02x\n", asr);
1023#endif
1024			SBIC_TRACE(dev);
1025			return 1;
1026		}
1027		GET_SBIC_csr (regs, csr);
1028		CSR_TRACE('s',csr,asr,target);
1029		QPRINTF(("%02x ", csr));
1030		if( csr == SBIC_CSR_RSLT_NI || csr == SBIC_CSR_RSLT_IFY) {
1031#ifdef DEBUG
1032			if(reselect_debug)
1033				printf("sbicselectbus: reselected asr %02x\n", asr);
1034#endif
1035			/* We need to handle this now so we don't lock up later */
1036			sbicnextstate(dev, csr, asr);
1037			SBIC_TRACE(dev);
1038			return 1;
1039		}
1040		if( csr == SBIC_CSR_SLT || csr == SBIC_CSR_SLT_ATN) {
1041			panic("sbicselectbus: target issued select!");
1042			return 1;
1043		}
1044	} while (csr != (SBIC_CSR_MIS_2|MESG_OUT_PHASE)
1045	    && csr != (SBIC_CSR_MIS_2|CMD_PHASE) && csr != SBIC_CSR_SEL_TIMEO);
1046
1047	/* Enable (or not) reselection */
1048	if(!sbic_enable_reselect && dev->nexus_list.tqh_first == NULL)
1049		SET_SBIC_rselid (regs, 0);
1050	else
1051		SET_SBIC_rselid (regs, SBIC_RID_ER);
1052
1053	if (csr == (SBIC_CSR_MIS_2|CMD_PHASE)) {
1054		dev->sc_flags |= SBICF_SELECTED;	/* device ignored ATN */
1055		GET_SBIC_selid(regs, id);
1056		dev->target = id;
1057		GET_SBIC_tlun(regs,dev->lun);
1058		if( dev->lun & SBIC_TLUN_VALID )
1059			dev->lun &= SBIC_TLUN_MASK;
1060		else
1061			dev->lun = lun;
1062	} else if (csr == (SBIC_CSR_MIS_2|MESG_OUT_PHASE)) {
1063		/*
1064		 * Send identify message
1065		 * (SCSI-2 requires an identify msg (?))
1066		 */
1067		GET_SBIC_selid(regs, id);
1068		dev->target = id;
1069		GET_SBIC_tlun(regs,dev->lun);
1070		if( dev->lun & SBIC_TLUN_VALID )
1071			dev->lun &= SBIC_TLUN_MASK;
1072		else
1073			dev->lun = lun;
1074		/*
1075		 * handle drives that don't want to be asked
1076		 * whether to go sync at all.
1077		 */
1078		if (sbic_inhibit_sync[id]
1079		    && dev->sc_sync[id].state == SYNC_START) {
1080#ifdef DEBUG
1081			if (sync_debug)
1082				printf("Forcing target %d asynchronous.\n", id);
1083#endif
1084			dev->sc_sync[id].offset = 0;
1085			dev->sc_sync[id].period = sbic_min_period;
1086			dev->sc_sync[id].state = SYNC_DONE;
1087		}
1088
1089
1090		if (dev->sc_sync[id].state != SYNC_START){
1091			if( dev->sc_xs->xs_control & XS_CTL_POLL
1092			   || (dev->sc_flags & SBICF_ICMD)
1093			   || !sbic_enable_reselect )
1094				SEND_BYTE (regs, MSG_IDENTIFY | lun);
1095			else
1096				SEND_BYTE (regs, MSG_IDENTIFY_DR | lun);
1097		} else {
1098			/*
1099			 * try to initiate a sync transfer.
1100			 * So compose the sync message we're going
1101			 * to send to the target
1102			 */
1103
1104#ifdef DEBUG
1105			if (sync_debug)
1106				printf("Sending sync request to target %d ... ",
1107				    id);
1108#endif
1109			/*
1110			 * setup scsi message sync message request
1111			 */
1112			dev->sc_msg[0] = MSG_IDENTIFY | lun;
1113			dev->sc_msg[1] = MSG_EXT_MESSAGE;
1114			dev->sc_msg[2] = 3;
1115			dev->sc_msg[3] = MSG_SYNC_REQ;
1116			dev->sc_msg[4] = sbictoscsiperiod(dev, regs,
1117			    sbic_min_period);
1118			dev->sc_msg[5] = sbic_max_offset;
1119
1120			if (sbicxfstart(regs, 6, MESG_OUT_PHASE, sbic_cmd_wait))
1121				sbicxfout(regs, 6, dev->sc_msg, MESG_OUT_PHASE);
1122
1123			dev->sc_sync[id].state = SYNC_SENT;
1124#ifdef DEBUG
1125			if (sync_debug)
1126				printf ("sent\n");
1127#endif
1128		}
1129
1130		asr = SBIC_WAIT (regs, SBIC_ASR_INT, 0);
1131		GET_SBIC_csr (regs, csr);
1132		CSR_TRACE('y',csr,asr,target);
1133		QPRINTF(("[%02x]", csr));
1134#ifdef DEBUG
1135		if (sync_debug && dev->sc_sync[id].state == SYNC_SENT)
1136			printf("csr-result of last msgout: 0x%x\n", csr);
1137#endif
1138
1139		if (csr != SBIC_CSR_SEL_TIMEO)
1140			dev->sc_flags |= SBICF_SELECTED;
1141	}
1142	if (csr == SBIC_CSR_SEL_TIMEO)
1143		dev->sc_xs->error = XS_SELTIMEOUT;
1144
1145	QPRINTF(("\n"));
1146
1147	SBIC_TRACE(dev);
1148	return(csr == SBIC_CSR_SEL_TIMEO);
1149}
1150
1151int
1152sbicxfstart(sbic_regmap_t regs, int len, u_char phase, int wait)
1153{
1154	u_char id;
1155
1156	switch (phase) {
1157	case DATA_IN_PHASE:
1158	case MESG_IN_PHASE:
1159		GET_SBIC_selid (regs, id);
1160		id |= SBIC_SID_FROM_SCSI;
1161		SET_SBIC_selid (regs, id);
1162		SBIC_TC_PUT (regs, (unsigned)len);
1163		break;
1164	case DATA_OUT_PHASE:
1165	case MESG_OUT_PHASE:
1166	case CMD_PHASE:
1167		GET_SBIC_selid (regs, id);
1168		id &= ~SBIC_SID_FROM_SCSI;
1169		SET_SBIC_selid (regs, id);
1170		SBIC_TC_PUT (regs, (unsigned)len);
1171		break;
1172	default:
1173		SBIC_TC_PUT (regs, 0);
1174	}
1175	QPRINTF(("sbicxfstart %d, %d, %d\n", len, phase, wait));
1176
1177	return(1);
1178}
1179
1180int
1181sbicxfout(sbic_regmap_t regs, int len, void *bp, int phase)
1182{
1183	u_char orig_csr, asr, *buf;
1184	int wait;
1185
1186	buf = bp;
1187	wait = sbic_data_wait;
1188
1189	QPRINTF(("sbicxfout {%d} %02x %02x %02x %02x %02x "
1190	    "%02x %02x %02x %02x %02x\n", len, buf[0], buf[1], buf[2],
1191	    buf[3], buf[4], buf[5], buf[6], buf[7], buf[8], buf[9]));
1192
1193	GET_SBIC_csr (regs, orig_csr);
1194	CSR_TRACE('>',orig_csr,0,0);
1195
1196	/*
1197	 * sigh.. WD-PROTO strikes again.. sending the command in one go
1198	 * causes the chip to lock up if talking to certain (misbehaving?)
1199	 * targets. Anyway, this procedure should work for all targets, but
1200	 * it's slightly slower due to the overhead
1201	 */
1202	WAIT_CIP (regs);
1203	SET_SBIC_cmd (regs, SBIC_CMD_XFER_INFO);
1204	for (;len > 0; len--) {
1205		GET_SBIC_asr (regs, asr);
1206		while ((asr & SBIC_ASR_DBR) == 0) {
1207			if ((asr & SBIC_ASR_INT) || --wait < 0) {
1208#ifdef DEBUG
1209				if (sbic_debug)
1210					printf("sbicxfout fail: l%d i%x w%d\n",
1211					    len, asr, wait);
1212#endif
1213				return (len);
1214			}
1215/*			DELAY(1);*/
1216			GET_SBIC_asr (regs, asr);
1217		}
1218
1219		SET_SBIC_data (regs, *buf);
1220		buf++;
1221	}
1222	SBIC_TC_GET(regs, len);
1223	QPRINTF(("sbicxfout done %d bytes\n", len));
1224	/*
1225	 * this leaves with one csr to be read
1226	 */
1227	return(0);
1228}
1229
1230/* returns # bytes left to read */
1231int
1232sbicxfin(sbic_regmap_t regs, int len, void *bp)
1233{
1234	int wait;
1235	u_char *obp, *buf;
1236	u_char orig_csr, csr, asr;
1237
1238	wait = sbic_data_wait;
1239	obp = bp;
1240	buf = bp;
1241
1242	GET_SBIC_csr (regs, orig_csr);
1243	CSR_TRACE('<',orig_csr,0,0);
1244
1245	QPRINTF(("sbicxfin %d, csr=%02x\n", len, orig_csr));
1246
1247	WAIT_CIP (regs);
1248	SET_SBIC_cmd (regs, SBIC_CMD_XFER_INFO);
1249	for (;len > 0; len--) {
1250		GET_SBIC_asr (regs, asr);
1251		if((asr & SBIC_ASR_PE)) {
1252#ifdef DEBUG
1253			printf("sbicxfin parity error: l%d i%x w%d\n",
1254			       len, asr, wait);
1255/*			return ((unsigned long)buf - (unsigned long)bp); */
1256#ifdef DDB
1257			Debugger();
1258#endif
1259#endif
1260		}
1261		while ((asr & SBIC_ASR_DBR) == 0) {
1262			if ((asr & SBIC_ASR_INT) || --wait < 0) {
1263#ifdef DEBUG
1264				if (sbic_debug) {
1265	QPRINTF(("sbicxfin fail:{%d} %02x %02x %02x %02x %02x %02x "
1266	    "%02x %02x %02x %02x\n", len, obp[0], obp[1], obp[2],
1267	    obp[3], obp[4], obp[5], obp[6], obp[7], obp[8], obp[9]));
1268					printf("sbicxfin fail: l%d i%x w%d\n",
1269					    len, asr, wait);
1270}
1271#endif
1272				return len;
1273			}
1274
1275			if (!(asr & SBIC_ASR_BSY)) {
1276				GET_SBIC_csr(regs, csr);
1277				CSR_TRACE('<',csr,asr,len);
1278				QPRINTF(("[CSR%02xASR%02x]", csr, asr));
1279			}
1280
1281/*			DELAY(1);*/
1282			GET_SBIC_asr (regs, asr);
1283		}
1284
1285		GET_SBIC_data (regs, *buf);
1286/*		QPRINTF(("asr=%02x, csr=%02x, data=%02x\n", asr, csr, *buf));*/
1287		buf++;
1288	}
1289
1290	QPRINTF(("sbicxfin {%d} %02x %02x %02x %02x %02x %02x "
1291	    "%02x %02x %02x %02x\n", len, obp[0], obp[1], obp[2],
1292	    obp[3], obp[4], obp[5], obp[6], obp[7], obp[8], obp[9]));
1293
1294	/* this leaves with one csr to be read */
1295	return len;
1296}
1297
1298/*
1299 * SCSI 'immediate' command:  issue a command to some SCSI device
1300 * and get back an 'immediate' response (i.e., do programmed xfer
1301 * to get the response data).  'cbuf' is a buffer containing a scsi
1302 * command of length clen bytes.  'buf' is a buffer of length 'len'
1303 * bytes for data.  The transfer direction is determined by the device
1304 * (i.e., by the scsi bus data xfer phase).  If 'len' is zero, the
1305 * command must supply no data.
1306 */
1307int
1308sbicicmd(struct sbic_softc *dev, int target, int lun, void *cbuf, int clen,
1309         void *buf, int len)
1310{
1311	sbic_regmap_t regs;
1312	u_char phase, csr, asr;
1313	int wait, i;
1314	struct sbic_acb *acb;
1315
1316#define CSR_LOG_BUF_SIZE 0
1317#if CSR_LOG_BUF_SIZE
1318	int bufptr;
1319	int csrbuf[CSR_LOG_BUF_SIZE];
1320	bufptr=0;
1321#endif
1322
1323	SBIC_TRACE(dev);
1324	regs = dev->sc_sbic;
1325	acb = dev->sc_nexus;
1326
1327	/* Make sure pointers are OK */
1328	dev->sc_last = dev->sc_cur = &acb->sc_pa;
1329	dev->sc_tcnt = acb->sc_tcnt = 0;
1330	acb->sc_pa.dc_count = 0; /* No DMA */
1331	acb->sc_kv.dc_addr = buf;
1332	acb->sc_kv.dc_count = len;
1333
1334#ifdef DEBUG
1335	routine = 3;
1336	debug_sbic_regs = regs; /* store this to allow debug calls */
1337	if( data_pointer_debug > 1 )
1338		printf("sbicicmd(%d,%d):%d\n", target, lun,
1339		       acb->sc_kv.dc_count);
1340#endif
1341
1342	/*
1343	 * set the sbic into non-DMA mode
1344	 */
1345	SET_SBIC_control(regs, SBIC_CTL_EDI | SBIC_CTL_IDI /*| SBIC_CTL_HSP*/);
1346
1347	dev->sc_stat[0] = 0xff;
1348	dev->sc_msg[0] = 0xff;
1349	i = 1; /* pre-load */
1350
1351	/* We're stealing the SCSI bus */
1352	dev->sc_flags |= SBICF_ICMD;
1353
1354	do {
1355		/*
1356		 * select the SCSI bus (it's an error if bus isn't free)
1357		 */
1358		if (!( dev->sc_flags & SBICF_SELECTED )
1359		    && sbicselectbus(dev, regs, target, lun, dev->sc_scsiaddr)) {
1360			/* printf("sbicicmd: trying to select busy bus!\n"); */
1361			dev->sc_flags &= ~SBICF_ICMD;
1362			return(-1);
1363		}
1364
1365		/*
1366		 * Wait for a phase change (or error) then let the device sequence
1367		 * us through the various SCSI phases.
1368		 */
1369
1370		wait = sbic_cmd_wait;
1371
1372		GET_SBIC_asr (regs, asr);
1373		GET_SBIC_csr (regs, csr);
1374		CSR_TRACE('I',csr,asr,target);
1375		QPRINTF((">ASR:%02xCSR:%02x<", asr, csr));
1376
1377#if CSR_LOG_BUF_SIZE
1378		csrbuf[bufptr++] = csr;
1379#endif
1380
1381
1382		switch (csr) {
1383		case SBIC_CSR_S_XFERRED:
1384		case SBIC_CSR_DISC:
1385		case SBIC_CSR_DISC_1:
1386			dev->sc_flags &= ~SBICF_SELECTED;
1387			GET_SBIC_cmd_phase (regs, phase);
1388			if (phase == 0x60) {
1389				GET_SBIC_tlun (regs, dev->sc_stat[0]);
1390				i = 0; /* done */
1391/*				break; */ /* Bypass all the state gobldygook */
1392			} else {
1393#ifdef DEBUG
1394				if(reselect_debug>1)
1395					printf("sbicicmd: handling disconnect\n");
1396#endif
1397				i = SBIC_STATE_DISCONNECT;
1398			}
1399			break;
1400
1401		case SBIC_CSR_XFERRED|CMD_PHASE:
1402		case SBIC_CSR_MIS|CMD_PHASE:
1403		case SBIC_CSR_MIS_1|CMD_PHASE:
1404		case SBIC_CSR_MIS_2|CMD_PHASE:
1405			if (sbicxfstart(regs, clen, CMD_PHASE, sbic_cmd_wait))
1406				if (sbicxfout(regs, clen,
1407					      cbuf, CMD_PHASE))
1408					i = sbicabort(dev, regs, "icmd sending cmd");
1409#if 0
1410			GET_SBIC_csr(regs, csr); /* Lets us reload tcount */
1411			WAIT_CIP(regs);
1412			GET_SBIC_asr(regs, asr);
1413			CSR_TRACE('I',csr,asr,target);
1414			if( asr & (SBIC_ASR_BSY|SBIC_ASR_LCI|SBIC_ASR_CIP) )
1415				printf("next: cmd sent asr %02x, csr %02x\n",
1416				       asr, csr);
1417#endif
1418			break;
1419
1420#if 0
1421		case SBIC_CSR_XFERRED|DATA_OUT_PHASE:
1422		case SBIC_CSR_XFERRED|DATA_IN_PHASE:
1423		case SBIC_CSR_MIS|DATA_OUT_PHASE:
1424		case SBIC_CSR_MIS|DATA_IN_PHASE:
1425		case SBIC_CSR_MIS_1|DATA_OUT_PHASE:
1426		case SBIC_CSR_MIS_1|DATA_IN_PHASE:
1427		case SBIC_CSR_MIS_2|DATA_OUT_PHASE:
1428		case SBIC_CSR_MIS_2|DATA_IN_PHASE:
1429			if (acb->sc_kv.dc_count <= 0)
1430				i = sbicabort(dev, regs, "icmd out of data");
1431			else {
1432			  wait = sbic_data_wait;
1433			  if (sbicxfstart(regs,
1434					  acb->sc_kv.dc_count,
1435					  SBIC_PHASE(csr), wait))
1436			    if (csr & 0x01)
1437			      /* data in? */
1438			      i=sbicxfin(regs,
1439					 acb->sc_kv.dc_count,
1440					 acb->sc_kv.dc_addr);
1441			    else
1442			      i=sbicxfout(regs,
1443					  acb->sc_kv.dc_count,
1444					  acb->sc_kv.dc_addr,
1445					     SBIC_PHASE(csr));
1446			  acb->sc_kv.dc_addr +=
1447				  (acb->sc_kv.dc_count - i);
1448			  acb->sc_kv.dc_count = i;
1449			  i = 1;
1450			}
1451			break;
1452
1453#endif
1454		case SBIC_CSR_XFERRED|STATUS_PHASE:
1455		case SBIC_CSR_MIS|STATUS_PHASE:
1456		case SBIC_CSR_MIS_1|STATUS_PHASE:
1457		case SBIC_CSR_MIS_2|STATUS_PHASE:
1458			/*
1459			 * the sbic does the status/cmd-complete reading ok,
1460			 * so do this with its hi-level commands.
1461			 */
1462#ifdef DEBUG
1463			if(sbic_debug)
1464				printf("SBICICMD status phase\n");
1465#endif
1466			SBIC_TC_PUT(regs, 0);
1467			SET_SBIC_cmd_phase(regs, 0x46);
1468			SET_SBIC_cmd(regs, SBIC_CMD_SEL_ATN_XFER);
1469			break;
1470
1471#if THIS_IS_A_RESERVED_STATE
1472		case BUS_FREE_PHASE:		/* This is not legal */
1473			if( dev->sc_stat[0] != 0xff )
1474				goto out;
1475			break;
1476#endif
1477
1478		default:
1479			i = sbicnextstate(dev, csr, asr);
1480		}
1481
1482		/*
1483		 * make sure the last command was taken,
1484		 * ie. we're not hunting after an ignored command..
1485		 */
1486		GET_SBIC_asr(regs, asr);
1487
1488		/* tapes may take a loooong time.. */
1489		while (asr & SBIC_ASR_BSY){
1490			if(asr & SBIC_ASR_DBR) {
1491				printf("sbicicmd: Waiting while sbic is jammed, CSR:%02x,ASR:%02x\n",
1492				       csr,asr);
1493#ifdef DDB
1494				Debugger();
1495#endif
1496				/* SBIC is jammed */
1497				/* DUNNO which direction */
1498				/* Try old direction */
1499				GET_SBIC_data(regs,i);
1500				GET_SBIC_asr(regs, asr);
1501				if( asr & SBIC_ASR_DBR) /* Wants us to write */
1502					SET_SBIC_data(regs,i);
1503			}
1504			GET_SBIC_asr(regs, asr);
1505		}
1506
1507		/*
1508		 * wait for last command to complete
1509		 */
1510		if (asr & SBIC_ASR_LCI) {
1511			printf("sbicicmd: last command ignored\n");
1512		}
1513		else if( i == 1 ) /* Bsy */
1514			SBIC_WAIT (regs, SBIC_ASR_INT, wait);
1515
1516		/*
1517		 * do it again
1518		 */
1519	} while ( i > 0 && dev->sc_stat[0] == 0xff);
1520
1521	/* Sometimes we need to do an extra read of the CSR */
1522	GET_SBIC_csr(regs, csr);
1523	CSR_TRACE('I',csr,asr,0xff);
1524
1525#if CSR_LOG_BUF_SIZE
1526	if(reselect_debug>1)
1527		for(i=0; i<bufptr; i++)
1528			printf("CSR:%02x", csrbuf[i]);
1529#endif
1530
1531#ifdef DEBUG
1532	if(data_pointer_debug > 1)
1533		printf("sbicicmd done(%d,%d):%d =%d=\n",
1534		       dev->target, lun,
1535		       acb->sc_kv.dc_count,
1536		       dev->sc_stat[0]);
1537#endif
1538
1539	QPRINTF(("=STS:%02x=", dev->sc_stat[0]));
1540	dev->sc_flags &= ~SBICF_ICMD;
1541
1542	SBIC_TRACE(dev);
1543	return(dev->sc_stat[0]);
1544}
1545
1546/*
1547 * Finish SCSI xfer command:  After the completion interrupt from
1548 * a read/write operation, sequence through the final phases in
1549 * programmed i/o.  This routine is a lot like sbicicmd except we
1550 * skip (and don't allow) the select, cmd out and data in/out phases.
1551 */
1552void
1553sbicxfdone(struct sbic_softc *dev, sbic_regmap_t regs, int target)
1554{
1555	u_char phase, asr, csr;
1556	int s;
1557
1558	SBIC_TRACE(dev);
1559	QPRINTF(("{"));
1560	s = splbio();
1561
1562	/*
1563	 * have the sbic complete on its own
1564	 */
1565	SBIC_TC_PUT(regs, 0);
1566	SET_SBIC_cmd_phase(regs, 0x46);
1567	SET_SBIC_cmd(regs, SBIC_CMD_SEL_ATN_XFER);
1568
1569	do {
1570		asr = SBIC_WAIT (regs, SBIC_ASR_INT, 0);
1571		GET_SBIC_csr (regs, csr);
1572		CSR_TRACE('f',csr,asr,target);
1573		QPRINTF(("%02x:", csr));
1574	} while ((csr != SBIC_CSR_DISC) && (csr != SBIC_CSR_DISC_1)
1575	    && (csr != SBIC_CSR_S_XFERRED));
1576
1577	dev->sc_flags &= ~SBICF_SELECTED;
1578
1579	GET_SBIC_cmd_phase (regs, phase);
1580	QPRINTF(("}%02x", phase));
1581	if (phase == 0x60)
1582		GET_SBIC_tlun(regs, dev->sc_stat[0]);
1583	else
1584		sbicerror(dev, regs, csr);
1585
1586	QPRINTF(("=STS:%02x=\n", dev->sc_stat[0]));
1587	splx(s);
1588	SBIC_TRACE(dev);
1589}
1590
1591	/*
1592	 * No DMA chains
1593	 */
1594
1595int
1596sbicgo(struct sbic_softc *dev, struct scsipi_xfer *xs)
1597{
1598	int i, dmaflags, count, usedma;
1599	u_char csr, asr, *addr;
1600	sbic_regmap_t regs;
1601	struct sbic_acb *acb;
1602
1603	SBIC_TRACE(dev);
1604	dev->target = xs->xs_periph->periph_target;
1605	dev->lun = xs->xs_periph->periph_lun;
1606	acb = dev->sc_nexus;
1607	regs = dev->sc_sbic;
1608
1609	usedma = sbicdmaok(dev, xs);
1610#ifdef DEBUG
1611	routine = 1;
1612	debug_sbic_regs = regs; /* store this to allow debug calls */
1613	if( data_pointer_debug > 1 )
1614		printf("sbicgo(%d,%d)\n", dev->target, dev->lun);
1615#endif
1616
1617	/*
1618	 * set the sbic into DMA mode
1619	 */
1620	if( usedma )
1621		SET_SBIC_control(regs, SBIC_CTL_EDI | SBIC_CTL_IDI |
1622				 SBIC_MACHINE_DMA_MODE);
1623	else
1624		SET_SBIC_control(regs, SBIC_CTL_EDI | SBIC_CTL_IDI);
1625
1626
1627	/*
1628	 * select the SCSI bus (it's an error if bus isn't free)
1629	 */
1630	if (sbicselectbus(dev, regs, dev->target, dev->lun,
1631	    dev->sc_scsiaddr)) {
1632		/* printf("sbicgo: Trying to select busy bus!\n"); */
1633		SBIC_TRACE(dev);
1634		return(0); /* Not done: needs to be rescheduled */
1635	}
1636	dev->sc_stat[0] = 0xff;
1637
1638	/*
1639	 * Calculate DMA chains now
1640	 */
1641
1642	dmaflags = 0;
1643	if (acb->flags & ACB_DATAIN)
1644		dmaflags |= DMAGO_READ;
1645
1646
1647	/*
1648	 * Deal w/bounce buffers.
1649	 */
1650
1651	addr = acb->sc_kv.dc_addr;
1652	count = acb->sc_kv.dc_count;
1653	if (count && (char *)kvtop(addr) != acb->sc_pa.dc_addr)	{ /* XXXX check */
1654		printf("sbic: DMA buffer mapping changed %p->%x\n",
1655		    acb->sc_pa.dc_addr, (unsigned)kvtop(addr));
1656#ifdef DDB
1657		Debugger();
1658#endif
1659	}
1660
1661#ifdef DEBUG
1662	++sbicdma_ops;			/* count total DMA operations */
1663#endif
1664	if (count && usedma && dev->sc_flags & SBICF_BADDMA &&
1665	    sbiccheckdmap(addr, count, dev->sc_dmamask)) {
1666		/*
1667		 * need to bounce the DMA.
1668		 */
1669		if (dmaflags & DMAGO_READ) {
1670			acb->flags |= ACB_BBUF;
1671			acb->sc_dmausrbuf = addr;
1672			acb->sc_dmausrlen = count;
1673			acb->sc_usrbufpa = (u_char *)kvtop(addr);
1674			if(!dev->sc_tinfo[dev->target].bounce) {
1675				printf("sbicgo: HELP! no bounce allocated for %d\n",
1676				       dev->target);
1677				printf("xfer: (%p->%p,%lx)\n", acb->sc_dmausrbuf,
1678				       acb->sc_usrbufpa, acb->sc_dmausrlen);
1679				dev->sc_tinfo[xs->xs_periph->periph_target].bounce
1680					= (char *)alloc_z2mem(MAXPHYS);
1681				if (isztwomem(dev->sc_tinfo[xs->xs_periph->periph_target].bounce))
1682					printf("alloc ZII target %d bounce pa 0x%x\n",
1683					       xs->xs_periph->periph_target,
1684					       (unsigned)kvtop(dev->sc_tinfo[xs->xs_periph->periph_target].bounce));
1685				else if (dev->sc_tinfo[xs->xs_periph->periph_target].bounce)
1686					printf("alloc CHIP target %d bounce pa %p\n",
1687					       xs->xs_periph->periph_target,
1688					       PREP_DMA_MEM(dev->sc_tinfo[xs->xs_periph->periph_target].bounce));
1689
1690				printf("Allocating %d bounce at %x\n",
1691				       dev->target,
1692				       (unsigned)kvtop(dev->sc_tinfo[dev->target].bounce));
1693			}
1694		} else {	/* write: copy to DMA buffer */
1695#ifdef DEBUG
1696			if(data_pointer_debug)
1697			printf("sbicgo: copying %x bytes to target %d bounce %x\n",
1698			       count, dev->target,
1699			       (unsigned)kvtop(dev->sc_tinfo[dev->target].bounce));
1700#endif
1701			bcopy (addr, dev->sc_tinfo[dev->target].bounce, count);
1702		}
1703		addr = dev->sc_tinfo[dev->target].bounce;/* and use DMA buffer */
1704		acb->sc_kv.dc_addr = addr;
1705#ifdef DEBUG
1706		++sbicdma_bounces;		/* count number of bounced */
1707#endif
1708	}
1709
1710	/*
1711	 * Allocate the DMA chain
1712	 */
1713
1714	/* Set start KVM addresses */
1715#if 0
1716	acb->sc_kv.dc_addr = addr;
1717	acb->sc_kv.dc_count = count;
1718#endif
1719
1720	/* Mark end of segment */
1721	acb->sc_tcnt = dev->sc_tcnt = 0;
1722	acb->sc_pa.dc_count = 0;
1723
1724	sbic_load_ptrs(dev, regs, dev->target, dev->lun);
1725	SBIC_TRACE(dev);
1726	/* Enable interrupts but don't do any DMA */
1727	dev->sc_enintr(dev);
1728	if (usedma) {
1729		dev->sc_tcnt = dev->sc_dmago(dev, acb->sc_pa.dc_addr,
1730		    acb->sc_pa.dc_count,
1731		    dmaflags);
1732#ifdef DEBUG
1733		dev->sc_dmatimo = dev->sc_tcnt ? 1 : 0;
1734#endif
1735        } else
1736		dev->sc_dmacmd = 0; /* Don't use DMA */
1737	dev->sc_flags |= SBICF_INDMA;
1738/*	SBIC_TC_PUT(regs, dev->sc_tcnt); */ /* XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX */
1739	SBIC_TRACE(dev);
1740	sbic_save_ptrs(dev, regs, dev->target, dev->lun);
1741
1742	/*
1743	 * push the data cache ( I think this won't work (EH))
1744	 */
1745#if defined(M68040) || defined(M68060)
1746	if (mmutype == MMU_68040 && usedma && count) {
1747		dma_cachectl(addr, count);
1748		if (((u_int)addr & 0xF) || (((u_int)addr + count) & 0xF))
1749			dev->sc_flags |= SBICF_DCFLUSH;
1750	}
1751#endif
1752#ifdef __powerpc__
1753	dma_cachectl(addr, count);
1754#endif
1755
1756	/*
1757	 * enintr() also enables interrupts for the sbic
1758	 */
1759#ifdef DEBUG
1760	if( data_pointer_debug > 1 )
1761		printf("sbicgo dmago:%d(%p:%lx)\n",
1762		       dev->target,dev->sc_cur->dc_addr,dev->sc_tcnt);
1763#if 0
1764	/*
1765	 * Hmm - this isn't right:  asr and csr haven't been set yet.
1766	 */
1767	debug_asr = asr;
1768	debug_csr = csr;
1769#endif
1770#endif
1771
1772	/*
1773	 * Lets cycle a while then let the interrupt handler take over
1774	 */
1775
1776	GET_SBIC_asr(regs, asr);
1777	do {
1778		GET_SBIC_csr(regs, csr);
1779		CSR_TRACE('g',csr,asr,dev->target);
1780#ifdef DEBUG
1781		debug_csr = csr;
1782		routine = 1;
1783#endif
1784		QPRINTF(("go[0x%x]", csr));
1785
1786		i = sbicnextstate(dev, csr, asr);
1787
1788		WAIT_CIP(regs);
1789		GET_SBIC_asr(regs, asr);
1790#ifdef DEBUG
1791		debug_asr = asr;
1792#endif
1793		if(asr & SBIC_ASR_LCI) printf("sbicgo: LCI asr:%02x csr:%02x\n",
1794					      asr,csr);
1795	} while( i == SBIC_STATE_RUNNING
1796		&& asr & (SBIC_ASR_INT|SBIC_ASR_LCI) );
1797
1798	CSR_TRACE('g',csr,asr,i<<4);
1799	SBIC_TRACE(dev);
1800if (i == SBIC_STATE_DONE && dev->sc_stat[0] == 0xff) printf("sbicgo: done & stat = 0xff\n");
1801	if (i == SBIC_STATE_DONE && dev->sc_stat[0] != 0xff) {
1802/*	if( i == SBIC_STATE_DONE && dev->sc_stat[0] ) { */
1803		/* Did we really finish that fast? */
1804		return 1;
1805	}
1806	return 0;
1807}
1808
1809
1810int
1811sbicintr(struct sbic_softc *dev)
1812{
1813	sbic_regmap_t regs;
1814	u_char asr, csr;
1815	int i;
1816
1817	regs = dev->sc_sbic;
1818
1819	/*
1820	 * pending interrupt?
1821	 */
1822	GET_SBIC_asr (regs, asr);
1823	if ((asr & SBIC_ASR_INT) == 0)
1824		return(0);
1825
1826	SBIC_TRACE(dev);
1827	do {
1828		GET_SBIC_csr(regs, csr);
1829		CSR_TRACE('i',csr,asr,dev->target);
1830#ifdef DEBUG
1831		debug_csr = csr;
1832		routine = 2;
1833#endif
1834		QPRINTF(("intr[0x%x]", csr));
1835
1836		i = sbicnextstate(dev, csr, asr);
1837
1838		WAIT_CIP(regs);
1839		GET_SBIC_asr(regs, asr);
1840#ifdef DEBUG
1841		debug_asr = asr;
1842#endif
1843#if 0
1844		if(asr & SBIC_ASR_LCI) printf("sbicintr: LCI asr:%02x csr:%02x\n",
1845					      asr,csr);
1846#endif
1847	} while(i == SBIC_STATE_RUNNING &&
1848		asr & (SBIC_ASR_INT|SBIC_ASR_LCI));
1849	CSR_TRACE('i',csr,asr,i<<4);
1850	SBIC_TRACE(dev);
1851	return(1);
1852}
1853
1854/*
1855 * Run commands and wait for disconnect
1856 */
1857int
1858sbicpoll(struct sbic_softc *dev)
1859{
1860	sbic_regmap_t regs;
1861	u_char asr, csr;
1862	int i;
1863
1864	SBIC_TRACE(dev);
1865	regs = dev->sc_sbic;
1866
1867	do {
1868		GET_SBIC_asr (regs, asr);
1869#ifdef DEBUG
1870		debug_asr = asr;
1871#endif
1872		GET_SBIC_csr(regs, csr);
1873		CSR_TRACE('p',csr,asr,dev->target);
1874#ifdef DEBUG
1875		debug_csr = csr;
1876		routine = 2;
1877#endif
1878		QPRINTF(("poll[0x%x]", csr));
1879
1880		i = sbicnextstate(dev, csr, asr);
1881
1882		WAIT_CIP(regs);
1883		GET_SBIC_asr(regs, asr);
1884		/* tapes may take a loooong time.. */
1885		while (asr & SBIC_ASR_BSY){
1886			if(asr & SBIC_ASR_DBR) {
1887				printf("sbipoll: Waiting while sbic is jammed, CSR:%02x,ASR:%02x\n",
1888				       csr,asr);
1889#ifdef DDB
1890				Debugger();
1891#endif
1892				/* SBIC is jammed */
1893				/* DUNNO which direction */
1894				/* Try old direction */
1895				GET_SBIC_data(regs,i);
1896				GET_SBIC_asr(regs, asr);
1897				if( asr & SBIC_ASR_DBR) /* Wants us to write */
1898					SET_SBIC_data(regs,i);
1899			}
1900			GET_SBIC_asr(regs, asr);
1901		}
1902
1903		if(asr & SBIC_ASR_LCI) printf("sbicpoll: LCI asr:%02x csr:%02x\n",
1904					      asr,csr);
1905		else if( i == 1 ) /* BSY */
1906			SBIC_WAIT(regs, SBIC_ASR_INT, sbic_cmd_wait);
1907	} while(i == SBIC_STATE_RUNNING);
1908	CSR_TRACE('p',csr,asr,i<<4);
1909	SBIC_TRACE(dev);
1910	return(1);
1911}
1912
1913/*
1914 * Handle a single msgin
1915 */
1916
1917int
1918sbicmsgin(struct sbic_softc *dev)
1919{
1920	sbic_regmap_t regs;
1921	int recvlen;
1922	u_char asr, csr, *tmpaddr;
1923
1924	regs = dev->sc_sbic;
1925
1926	dev->sc_msg[0] = 0xff;
1927	dev->sc_msg[1] = 0xff;
1928
1929	GET_SBIC_asr(regs, asr);
1930#ifdef DEBUG
1931	if(reselect_debug>1)
1932		printf("sbicmsgin asr=%02x\n", asr);
1933#endif
1934
1935	sbic_save_ptrs(dev, regs, dev->target, dev->lun);
1936
1937	GET_SBIC_selid (regs, csr);
1938	SET_SBIC_selid (regs, csr | SBIC_SID_FROM_SCSI);
1939
1940	SBIC_TC_PUT(regs, 0);
1941	tmpaddr = dev->sc_msg;
1942	recvlen = 1;
1943	do {
1944		while( recvlen-- ) {
1945			GET_SBIC_asr(regs, asr);
1946			GET_SBIC_csr(regs, csr);
1947			QPRINTF(("sbicmsgin ready to go (csr,asr)=(%02x,%02x)\n",
1948				 csr, asr));
1949
1950			RECV_BYTE(regs, *tmpaddr);
1951			CSR_TRACE('m',csr,asr,*tmpaddr);
1952#if 1
1953			/*
1954			 * get the command completion interrupt, or we
1955			 * can't send a new command (LCI)
1956			 */
1957			SBIC_WAIT(regs, SBIC_ASR_INT, 0);
1958			GET_SBIC_csr(regs, csr);
1959			CSR_TRACE('X',csr,asr,dev->target);
1960#else
1961			WAIT_CIP(regs);
1962			do {
1963				GET_SBIC_asr(regs, asr);
1964				csr = 0xff;
1965				GET_SBIC_csr(regs, csr);
1966				CSR_TRACE('X',csr,asr,dev->target);
1967				if( csr == 0xff )
1968					printf("sbicmsgin waiting: csr %02x asr %02x\n", csr, asr);
1969			} while( csr == 0xff );
1970#endif
1971#ifdef DEBUG
1972			if(reselect_debug>1)
1973				printf("sbicmsgin: got %02x csr %02x asr %02x\n",
1974				       *tmpaddr, csr, asr);
1975#endif
1976#if do_parity_check
1977			if( asr & SBIC_ASR_PE ) {
1978				printf ("Parity error");
1979				/* This code simply does not work. */
1980				WAIT_CIP(regs);
1981				SET_SBIC_cmd(regs, SBIC_CMD_SET_ATN);
1982				WAIT_CIP(regs);
1983				GET_SBIC_asr(regs, asr);
1984				WAIT_CIP(regs);
1985				SET_SBIC_cmd(regs, SBIC_CMD_CLR_ACK);
1986				WAIT_CIP(regs);
1987				if( !(asr & SBIC_ASR_LCI) )
1988					/* Target wants to send garbled msg*/
1989					continue;
1990				printf("--fixing\n");
1991				/* loop until a msgout phase occurs on target */
1992				while(csr & 0x07 != MESG_OUT_PHASE) {
1993					while( asr & SBIC_ASR_BSY &&
1994					      !(asr & SBIC_ASR_DBR|SBIC_ASR_INT) )
1995						GET_SBIC_asr(regs, asr);
1996					if( asr & SBIC_ASR_DBR )
1997						panic("msgin: jammed again!");
1998					GET_SBIC_csr(regs, csr);
1999					CSR_TRACE('e',csr,asr,dev->target);
2000					if( csr & 0x07 != MESG_OUT_PHASE ) {
2001						sbicnextstate(dev, csr, asr);
2002						sbic_save_ptrs(dev, regs,
2003							       dev->target,
2004							       dev->lun);
2005					}
2006				}
2007				/* Should be msg out by now */
2008				SEND_BYTE(regs, MSG_PARITY_ERROR);
2009			}
2010			else
2011#endif
2012				tmpaddr++;
2013
2014			if(recvlen) {
2015				/* Clear ACK */
2016				WAIT_CIP(regs);
2017				GET_SBIC_asr(regs, asr);
2018				GET_SBIC_csr(regs, csr);
2019				CSR_TRACE('X',csr,asr,dev->target);
2020				QPRINTF(("sbicmsgin pre byte CLR_ACK (csr,asr)=(%02x,%02x)\n",
2021					 csr, asr));
2022				SET_SBIC_cmd(regs, SBIC_CMD_CLR_ACK);
2023				SBIC_WAIT(regs, SBIC_ASR_INT, 0);
2024			}
2025
2026		};
2027
2028		if(dev->sc_msg[0] == 0xff) {
2029			printf("sbicmsgin: sbic swallowed our message\n");
2030			break;
2031		}
2032#ifdef DEBUG
2033		if (sync_debug)
2034			printf("msgin done csr 0x%x asr 0x%x msg 0x%x\n",
2035			       csr, asr, dev->sc_msg[0]);
2036#endif
2037		/*
2038		 * test whether this is a reply to our sync
2039		 * request
2040		 */
2041		if (MSG_ISIDENTIFY(dev->sc_msg[0])) {
2042			QPRINTF(("IFFY"));
2043#if 0
2044			/* There is an implied load-ptrs here */
2045			sbic_load_ptrs(dev, regs, dev->target, dev->lun);
2046#endif
2047			/* Got IFFY msg -- ack it */
2048		} else if (dev->sc_msg[0] == MSG_REJECT
2049			   && dev->sc_sync[dev->target].state == SYNC_SENT) {
2050			QPRINTF(("REJECT of SYN"));
2051#ifdef DEBUG
2052			if (sync_debug)
2053				printf("target %d rejected sync, going async\n",
2054				       dev->target);
2055#endif
2056			dev->sc_sync[dev->target].period = sbic_min_period;
2057			dev->sc_sync[dev->target].offset = 0;
2058			dev->sc_sync[dev->target].state = SYNC_DONE;
2059			SET_SBIC_syn(regs,
2060				     SBIC_SYN(dev->sc_sync[dev->target].offset,
2061					      dev->sc_sync[dev->target].period));
2062		} else if ((dev->sc_msg[0] == MSG_REJECT)) {
2063			QPRINTF(("REJECT"));
2064			/*
2065			 * we'll never REJECt a REJECT message..
2066			 */
2067		} else if ((dev->sc_msg[0] == MSG_SAVE_DATA_PTR)) {
2068			QPRINTF(("MSG_SAVE_DATA_PTR"));
2069			/*
2070			 * don't reject this either.
2071			 */
2072		} else if ((dev->sc_msg[0] == MSG_DISCONNECT)) {
2073			QPRINTF(("DISCONNECT"));
2074#ifdef DEBUG
2075			if( reselect_debug>1 && dev->sc_msg[0] == MSG_DISCONNECT )
2076				printf("sbicmsgin: got disconnect msg %s\n",
2077				       (dev->sc_flags & SBICF_ICMD)?"rejecting":"");
2078#endif
2079			if( dev->sc_flags & SBICF_ICMD ) {
2080				/* We're in immediate mode. Prevent disconnects. */
2081				/* prepare to reject the message, NACK */
2082				SET_SBIC_cmd(regs, SBIC_CMD_SET_ATN);
2083				WAIT_CIP(regs);
2084			}
2085		} else if (dev->sc_msg[0] == MSG_CMD_COMPLETE ) {
2086			QPRINTF(("CMD_COMPLETE"));
2087			/* !! KLUDGE ALERT !! quite a few drives don't seem to
2088			 * really like the current way of sending the
2089			 * sync-handshake together with the ident-message, and
2090			 * they react by sending command-complete and
2091			 * disconnecting right after returning the valid sync
2092			 * handshake. So, all I can do is reselect the drive,
2093			 * and hope it won't disconnect again. I don't think
2094			 * this is valid behavior, but I can't help fixing a
2095			 * problem that apparently exists.
2096			 *
2097			 * Note: we should not get here on `normal' command
2098			 * completion, as that condition is handled by the
2099			 * high-level sel&xfer resume command used to walk
2100			 * thru status/cc-phase.
2101			 */
2102
2103#ifdef DEBUG
2104			if (sync_debug)
2105				printf ("GOT MSG %d! target %d acting weird.."
2106					" waiting for disconnect...\n",
2107					dev->sc_msg[0], dev->target);
2108#endif
2109			/* Check to see if sbic is handling this */
2110			GET_SBIC_asr(regs, asr);
2111			if(asr & SBIC_ASR_BSY)
2112				return SBIC_STATE_RUNNING;
2113
2114			/* Let's try this: Assume it works and set status to 00 */
2115			dev->sc_stat[0] = 0;
2116		} else if (dev->sc_msg[0] == MSG_EXT_MESSAGE
2117			   && tmpaddr == &dev->sc_msg[1]) {
2118			QPRINTF(("ExtMSG\n"));
2119			/* Read in whole extended message */
2120			SET_SBIC_cmd(regs, SBIC_CMD_CLR_ACK);
2121			SBIC_WAIT(regs, SBIC_ASR_INT, 0);
2122			GET_SBIC_asr(regs, asr);
2123			GET_SBIC_csr(regs, csr);
2124			QPRINTF(("CLR ACK asr %02x, csr %02x\n", asr, csr));
2125			RECV_BYTE(regs, *tmpaddr);
2126			CSR_TRACE('x',csr,asr,*tmpaddr);
2127			/* Wait for command completion IRQ */
2128			SBIC_WAIT(regs, SBIC_ASR_INT, 0);
2129			recvlen = *tmpaddr++;
2130			QPRINTF(("Recving ext msg, asr %02x csr %02x len %02x\n",
2131			       asr, csr, recvlen));
2132		} else if (dev->sc_msg[0] == MSG_EXT_MESSAGE && dev->sc_msg[1] == 3
2133			   && dev->sc_msg[2] == MSG_SYNC_REQ) {
2134			QPRINTF(("SYN"));
2135			dev->sc_sync[dev->target].period =
2136				sbicfromscsiperiod(dev,
2137						   regs, dev->sc_msg[3]);
2138			dev->sc_sync[dev->target].offset = dev->sc_msg[4];
2139			dev->sc_sync[dev->target].state = SYNC_DONE;
2140			SET_SBIC_syn(regs,
2141				     SBIC_SYN(dev->sc_sync[dev->target].offset,
2142					      dev->sc_sync[dev->target].period));
2143			printf("%s: target %d now synchronous,"
2144			       " period=%dns, offset=%d.\n",
2145			       dev->sc_dev.dv_xname, dev->target,
2146			       dev->sc_msg[3] * 4, dev->sc_msg[4]);
2147		} else {
2148#ifdef DEBUG
2149			if (sbic_debug || sync_debug)
2150				printf ("sbicmsgin: Rejecting message 0x%02x\n",
2151					dev->sc_msg[0]);
2152#endif
2153			/* prepare to reject the message, NACK */
2154			SET_SBIC_cmd(regs, SBIC_CMD_SET_ATN);
2155			WAIT_CIP(regs);
2156		}
2157		/* Clear ACK */
2158		WAIT_CIP(regs);
2159		GET_SBIC_asr(regs, asr);
2160		GET_SBIC_csr(regs, csr);
2161		CSR_TRACE('X',csr,asr,dev->target);
2162		QPRINTF(("sbicmsgin pre CLR_ACK (csr,asr)=(%02x,%02x)%d\n",
2163			 csr, asr, recvlen));
2164		SET_SBIC_cmd(regs, SBIC_CMD_CLR_ACK);
2165		SBIC_WAIT(regs, SBIC_ASR_INT, 0);
2166	}
2167#if 0
2168	while((csr == SBIC_CSR_MSGIN_W_ACK)
2169	      || (SBIC_PHASE(csr) == MESG_IN_PHASE));
2170#else
2171	while (recvlen>0);
2172#endif
2173
2174	QPRINTF(("sbicmsgin finished: csr %02x, asr %02x\n",csr, asr));
2175
2176	/* Should still have one CSR to read */
2177	return SBIC_STATE_RUNNING;
2178}
2179
2180
2181/*
2182 * sbicnextstate()
2183 * return:
2184 *		0  == done
2185 *		1  == working
2186 *		2  == disconnected
2187 *		-1 == error
2188 */
2189int
2190sbicnextstate(struct sbic_softc *dev, u_char csr, u_char asr)
2191{
2192	sbic_regmap_t regs;
2193	struct sbic_acb *acb;
2194	int i, newtarget, newlun, wait;
2195#if 0
2196	unsigned tcnt;
2197#endif
2198
2199	i = 0;
2200	SBIC_TRACE(dev);
2201	regs = dev->sc_sbic;
2202	acb = dev->sc_nexus;
2203
2204	QPRINTF(("next[%02x,%02x]",asr,csr));
2205
2206	switch (csr) {
2207	case SBIC_CSR_XFERRED|CMD_PHASE:
2208	case SBIC_CSR_MIS|CMD_PHASE:
2209	case SBIC_CSR_MIS_1|CMD_PHASE:
2210	case SBIC_CSR_MIS_2|CMD_PHASE:
2211		sbic_save_ptrs(dev, regs, dev->target, dev->lun);
2212		if (sbicxfstart(regs, acb->clen, CMD_PHASE, sbic_cmd_wait))
2213			if (sbicxfout(regs, acb->clen,
2214				      &acb->cmd, CMD_PHASE))
2215				goto abort;
2216		break;
2217
2218	case SBIC_CSR_XFERRED|STATUS_PHASE:
2219	case SBIC_CSR_MIS|STATUS_PHASE:
2220	case SBIC_CSR_MIS_1|STATUS_PHASE:
2221	case SBIC_CSR_MIS_2|STATUS_PHASE:
2222		/*
2223		 * this should be the normal i/o completion case.
2224		 * get the status & cmd complete msg then let the
2225		 * device driver look at what happened.
2226		 */
2227		sbicxfdone(dev,regs,dev->target);
2228		/*
2229		 * check for overlapping cache line, flush if so
2230		 */
2231#if defined(M68040) || defined(M68060)
2232		if (dev->sc_flags & SBICF_DCFLUSH) {
2233#if 0
2234			printf("sbic: 68040/68060 DMA cache flush needs"
2235			    "fixing? %x:%x\n",
2236			    dev->sc_xs->data, dev->sc_xs->datalen);
2237#endif
2238		}
2239#endif
2240#ifdef DEBUG
2241		if( data_pointer_debug > 1 )
2242			printf("next dmastop: %d(%p:%lx)\n",
2243			       dev->target,dev->sc_cur->dc_addr,dev->sc_tcnt);
2244		dev->sc_dmatimo = 0;
2245#endif
2246		dev->sc_dmastop(dev); /* was dmafree */
2247		if (acb->flags & ACB_BBUF) {
2248			if ((u_char *)kvtop(acb->sc_dmausrbuf) != acb->sc_usrbufpa)
2249				printf("%s: WARNING - buffer mapping changed %p->%x\n",
2250				    dev->sc_dev.dv_xname, acb->sc_usrbufpa,
2251				    (unsigned)kvtop(acb->sc_dmausrbuf));
2252#ifdef DEBUG
2253			if(data_pointer_debug)
2254			printf("sbicgo:copying %lx bytes from target %d bounce %x\n",
2255			       acb->sc_dmausrlen,
2256			       dev->target,
2257			       (unsigned)kvtop(dev->sc_tinfo[dev->target].bounce));
2258#endif
2259			bcopy(dev->sc_tinfo[dev->target].bounce,
2260			      acb->sc_dmausrbuf,
2261			      acb->sc_dmausrlen);
2262		}
2263		dev->sc_flags &= ~(SBICF_INDMA | SBICF_DCFLUSH);
2264		sbic_scsidone(acb, dev->sc_stat[0]);
2265		SBIC_TRACE(dev);
2266		return SBIC_STATE_DONE;
2267
2268	case SBIC_CSR_XFERRED|DATA_OUT_PHASE:
2269	case SBIC_CSR_XFERRED|DATA_IN_PHASE:
2270	case SBIC_CSR_MIS|DATA_OUT_PHASE:
2271	case SBIC_CSR_MIS|DATA_IN_PHASE:
2272	case SBIC_CSR_MIS_1|DATA_OUT_PHASE:
2273	case SBIC_CSR_MIS_1|DATA_IN_PHASE:
2274	case SBIC_CSR_MIS_2|DATA_OUT_PHASE:
2275	case SBIC_CSR_MIS_2|DATA_IN_PHASE:
2276		if( dev->sc_xs->xs_control & XS_CTL_POLL || dev->sc_flags & SBICF_ICMD
2277		   || acb->sc_dmacmd == 0 ) {
2278			/* Do PIO */
2279			SET_SBIC_control(regs, SBIC_CTL_EDI | SBIC_CTL_IDI);
2280			if (acb->sc_kv.dc_count <= 0) {
2281				printf("sbicnextstate:xfer count %d asr%x csr%x\n",
2282				       acb->sc_kv.dc_count, asr, csr);
2283				goto abort;
2284			}
2285			wait = sbic_data_wait;
2286			if( sbicxfstart(regs,
2287					acb->sc_kv.dc_count,
2288					SBIC_PHASE(csr), wait)) {
2289				if( SBIC_PHASE(csr) == DATA_IN_PHASE )
2290					/* data in? */
2291					i=sbicxfin(regs,
2292						   acb->sc_kv.dc_count,
2293						   acb->sc_kv.dc_addr);
2294				else
2295					i=sbicxfout(regs,
2296						    acb->sc_kv.dc_count,
2297						    acb->sc_kv.dc_addr,
2298						    SBIC_PHASE(csr));
2299			}
2300			acb->sc_kv.dc_addr +=
2301				(acb->sc_kv.dc_count - i);
2302			acb->sc_kv.dc_count = i;
2303		} else {
2304			if (acb->sc_kv.dc_count <= 0) {
2305				printf("sbicnextstate:xfer count %d asr%x csr%x\n",
2306				       acb->sc_kv.dc_count, asr, csr);
2307				goto abort;
2308			}
2309			/*
2310			 * do scatter-gather DMA
2311			 * hacking the controller chip, ouch..
2312			 */
2313			SET_SBIC_control(regs, SBIC_CTL_EDI | SBIC_CTL_IDI |
2314					 SBIC_MACHINE_DMA_MODE);
2315			/*
2316			 * set next DMA addr and dec count
2317			 */
2318#if 0
2319			SBIC_TC_GET(regs, tcnt);
2320			dev->sc_cur->dc_count -= ((dev->sc_tcnt - tcnt) >> 1);
2321			dev->sc_cur->dc_addr += (dev->sc_tcnt - tcnt);
2322			dev->sc_tcnt = acb->sc_tcnt = tcnt;
2323#else
2324			sbic_save_ptrs(dev, regs, dev->target, dev->lun);
2325			sbic_load_ptrs(dev, regs, dev->target, dev->lun);
2326#endif
2327#ifdef DEBUG
2328			if( data_pointer_debug > 1 )
2329				printf("next dmanext: %d(%p:%lx)\n",
2330				       dev->target,dev->sc_cur->dc_addr,
2331				       dev->sc_tcnt);
2332			dev->sc_dmatimo = 1;
2333#endif
2334			dev->sc_tcnt = dev->sc_dmanext(dev);
2335			SBIC_TC_PUT(regs, (unsigned)dev->sc_tcnt);
2336			SET_SBIC_cmd(regs, SBIC_CMD_XFER_INFO);
2337			dev->sc_flags |= SBICF_INDMA;
2338		}
2339		break;
2340
2341	case SBIC_CSR_XFERRED|MESG_IN_PHASE:
2342	case SBIC_CSR_MIS|MESG_IN_PHASE:
2343	case SBIC_CSR_MIS_1|MESG_IN_PHASE:
2344	case SBIC_CSR_MIS_2|MESG_IN_PHASE:
2345		SBIC_TRACE(dev);
2346		return sbicmsgin(dev);
2347
2348	case SBIC_CSR_MSGIN_W_ACK:
2349		SET_SBIC_cmd(regs, SBIC_CMD_CLR_ACK); /* Dunno what I'm ACKing */
2350		printf("Acking unknown msgin CSR:%02x",csr);
2351		break;
2352
2353	case SBIC_CSR_XFERRED|MESG_OUT_PHASE:
2354	case SBIC_CSR_MIS|MESG_OUT_PHASE:
2355	case SBIC_CSR_MIS_1|MESG_OUT_PHASE:
2356	case SBIC_CSR_MIS_2|MESG_OUT_PHASE:
2357#ifdef DEBUG
2358		if (sync_debug)
2359			printf ("sending REJECT msg to last msg.\n");
2360#endif
2361
2362		sbic_save_ptrs(dev, regs, dev->target, dev->lun);
2363		/*
2364		 * should only get here on reject,
2365		 * since it's always US that
2366		 * initiate a sync transfer
2367		 */
2368		SEND_BYTE(regs, MSG_REJECT);
2369		WAIT_CIP(regs);
2370		if( asr & (SBIC_ASR_BSY|SBIC_ASR_LCI|SBIC_ASR_CIP) )
2371			printf("next: REJECT sent asr %02x\n", asr);
2372		SBIC_TRACE(dev);
2373		return SBIC_STATE_RUNNING;
2374
2375	case SBIC_CSR_DISC:
2376	case SBIC_CSR_DISC_1:
2377		dev->sc_flags &= ~(SBICF_INDMA|SBICF_SELECTED);
2378
2379		/* Try to schedule another target */
2380#ifdef DEBUG
2381		if(reselect_debug>1)
2382			printf("sbicnext target %d disconnected\n", dev->target);
2383#endif
2384		TAILQ_INSERT_HEAD(&dev->nexus_list, acb, chain);
2385		++dev->sc_tinfo[dev->target].dconns;
2386		dev->sc_nexus = NULL;
2387		dev->sc_xs = NULL;
2388
2389		if( acb->xs->xs_control & XS_CTL_POLL
2390		   || (dev->sc_flags & SBICF_ICMD)
2391		   || !sbic_parallel_operations ) {
2392			SBIC_TRACE(dev);
2393			return SBIC_STATE_DISCONNECT;
2394		}
2395		sbic_sched(dev);
2396		SBIC_TRACE(dev);
2397		return SBIC_STATE_DISCONNECT;
2398
2399	case SBIC_CSR_RSLT_NI:
2400	case SBIC_CSR_RSLT_IFY:
2401		GET_SBIC_rselid(regs, newtarget);
2402		/* check SBIC_RID_SIV? */
2403		newtarget &= SBIC_RID_MASK;
2404		if (csr == SBIC_CSR_RSLT_IFY) {
2405			/* Read IFY msg to avoid lockup */
2406			GET_SBIC_data(regs, newlun);
2407			WAIT_CIP(regs);
2408			newlun &= SBIC_TLUN_MASK;
2409			CSR_TRACE('r',csr,asr,newtarget);
2410		} else {
2411			/* Need to get IFY message */
2412			for (newlun = 256; newlun; --newlun) {
2413				GET_SBIC_asr(regs, asr);
2414				if (asr & SBIC_ASR_INT)
2415					break;
2416				delay(1);
2417			}
2418			newlun = 0;	/* XXXX */
2419			if ((asr & SBIC_ASR_INT) == 0) {
2420#ifdef DEBUG
2421				if (reselect_debug)
2422					printf("RSLT_NI - no IFFY message? asr %x\n", asr);
2423#endif
2424			} else {
2425				GET_SBIC_csr(regs,csr);
2426				CSR_TRACE('n',csr,asr,newtarget);
2427				if (csr == (SBIC_CSR_MIS | MESG_IN_PHASE) ||
2428				    csr == (SBIC_CSR_MIS_1 | MESG_IN_PHASE) ||
2429				    csr == (SBIC_CSR_MIS_2 | MESG_IN_PHASE)) {
2430					sbicmsgin(dev);
2431					newlun = dev->sc_msg[0] & 7;
2432				} else {
2433					printf("RSLT_NI - not MESG_IN_PHASE %x\n",
2434					    csr);
2435				}
2436			}
2437		}
2438#ifdef DEBUG
2439		if(reselect_debug>1 || (reselect_debug && csr==SBIC_CSR_RSLT_NI))
2440			printf("sbicnext: reselect %s from targ %d lun %d\n",
2441			    csr == SBIC_CSR_RSLT_NI ? "NI" : "IFY",
2442			    newtarget, newlun);
2443#endif
2444		if (dev->sc_nexus) {
2445#ifdef DEBUG
2446			if (reselect_debug > 1)
2447				printf("%s: reselect %s with active command\n",
2448				    dev->sc_dev.dv_xname,
2449				    csr == SBIC_CSR_RSLT_NI ? "NI" : "IFY");
2450#ifdef DDB
2451/*			Debugger();*/
2452#endif
2453#endif
2454			TAILQ_INSERT_HEAD(&dev->ready_list, dev->sc_nexus, chain);
2455			dev->sc_tinfo[dev->target].lubusy &= ~(1 << dev->lun);
2456			dev->sc_nexus = NULL;
2457			dev->sc_xs = NULL;
2458		}
2459		/* Reload sync values for this target */
2460		if (dev->sc_sync[newtarget].state == SYNC_DONE)
2461			SET_SBIC_syn(regs, SBIC_SYN (dev->sc_sync[newtarget].offset,
2462			    dev->sc_sync[newtarget].period));
2463		else
2464			SET_SBIC_syn(regs, SBIC_SYN (0, sbic_min_period));
2465		for (acb = dev->nexus_list.tqh_first; acb;
2466		    acb = acb->chain.tqe_next) {
2467			if (acb->xs->xs_periph->periph_target != newtarget ||
2468			    acb->xs->xs_periph->periph_lun != newlun)
2469				continue;
2470			TAILQ_REMOVE(&dev->nexus_list, acb, chain);
2471			dev->sc_nexus = acb;
2472			dev->sc_xs = acb->xs;
2473			dev->sc_flags |= SBICF_SELECTED;
2474			dev->target = newtarget;
2475			dev->lun = newlun;
2476			break;
2477		}
2478		if (acb == NULL) {
2479			printf("%s: reselect %s targ %d not in nexus_list %p\n",
2480			    dev->sc_dev.dv_xname,
2481			    csr == SBIC_CSR_RSLT_NI ? "NI" : "IFY", newtarget,
2482			    &dev->nexus_list.tqh_first);
2483			panic("bad reselect in sbic");
2484		}
2485		if (csr == SBIC_CSR_RSLT_IFY)
2486			SET_SBIC_cmd(regs, SBIC_CMD_CLR_ACK);
2487		break;
2488
2489	default:
2490        abort:
2491		/*
2492		 * Something unexpected happened -- deal with it.
2493		 */
2494		printf("sbicnextstate: aborting csr %02x asr %02x\n", csr, asr);
2495#ifdef DDB
2496		Debugger();
2497#endif
2498#ifdef DEBUG
2499		if( data_pointer_debug > 1 )
2500			printf("next dmastop: %d(%p:%lx)\n",
2501			       dev->target,dev->sc_cur->dc_addr,dev->sc_tcnt);
2502		dev->sc_dmatimo = 0;
2503#endif
2504		dev->sc_dmastop(dev);
2505		SET_SBIC_control(regs, SBIC_CTL_EDI | SBIC_CTL_IDI);
2506		sbicerror(dev, regs, csr);
2507		sbicabort(dev, regs, "next");
2508		if (dev->sc_flags & SBICF_INDMA) {
2509			/*
2510			 * check for overlapping cache line, flush if so
2511			 */
2512#if defined(M68040) || defined(M68060)
2513			if (dev->sc_flags & SBICF_DCFLUSH) {
2514#if 0
2515				printf("sbic: 68040/060 DMA cache flush needs"
2516				    "fixing? %x:%x\n",
2517				    dev->sc_xs->data, dev->sc_xs->datalen);
2518#endif
2519			}
2520#endif
2521			dev->sc_flags &=
2522				~(SBICF_INDMA | SBICF_DCFLUSH);
2523#ifdef DEBUG
2524			if( data_pointer_debug > 1 )
2525				printf("next dmastop: %d(%p:%lx)\n",
2526				    dev->target,dev->sc_cur->dc_addr,dev->sc_tcnt);
2527			dev->sc_dmatimo = 0;
2528#endif
2529			dev->sc_dmastop(dev);
2530			sbic_scsidone(acb, -1);
2531		}
2532		SBIC_TRACE(dev);
2533                return SBIC_STATE_ERROR;
2534	}
2535
2536	SBIC_TRACE(dev);
2537	return(SBIC_STATE_RUNNING);
2538}
2539
2540
2541/*
2542 * Check if DMA can not be used with specified buffer
2543 */
2544
2545int
2546sbiccheckdmap(void *bp, u_long len, u_long mask)
2547{
2548	u_char *buffer;
2549	u_long phy_buf;
2550	u_long phy_len;
2551
2552	buffer = bp;
2553
2554	if (len == 0)
2555		return(0);
2556
2557	while (len) {
2558		phy_buf = kvtop(buffer);
2559		if (len < (phy_len = PAGE_SIZE - ((int) buffer & PGOFSET)))
2560			phy_len = len;
2561		if (phy_buf & mask)
2562			return(1);
2563		buffer += phy_len;
2564		len -= phy_len;
2565	}
2566	return(0);
2567}
2568
2569int
2570sbictoscsiperiod(struct sbic_softc *dev, sbic_regmap_t regs, int a)
2571{
2572	unsigned int fs;
2573
2574	/*
2575	 * cycle = DIV / (2*CLK)
2576	 * DIV = FS+2
2577	 * best we can do is 200ns at 20 MHz, 2 cycles
2578	 */
2579
2580	GET_SBIC_myid(regs,fs);
2581	fs = (fs >>6) + 2;		/* DIV */
2582	fs = (fs * 10000) / (dev->sc_clkfreq<<1);	/* Cycle, in ns */
2583	if (a < 2) a = 8;		/* map to Cycles */
2584	return ((fs*a)>>2);		/* in 4 ns units */
2585}
2586
2587int
2588sbicfromscsiperiod(struct sbic_softc *dev, sbic_regmap_t regs, int p)
2589{
2590	register unsigned int fs, ret;
2591
2592	/* Just the inverse of the above */
2593
2594	GET_SBIC_myid(regs,fs);
2595	fs = (fs >>6) + 2;		/* DIV */
2596	fs = (fs * 10000) / (dev->sc_clkfreq<<1);   /* Cycle, in ns */
2597
2598	ret = p << 2;			/* in ns units */
2599	ret = ret / fs;			/* in Cycles */
2600	if (ret < sbic_min_period)
2601		return(sbic_min_period);
2602
2603	/* verify rounding */
2604	if (sbictoscsiperiod(dev, regs, ret) < p)
2605		ret++;
2606	return (ret >= 8) ? 0 : ret;
2607}
2608
2609#ifdef DEBUG
2610
2611void
2612sbicdumpstate(void)
2613{
2614	u_char csr, asr;
2615
2616	GET_SBIC_asr(debug_sbic_regs,asr);
2617	GET_SBIC_csr(debug_sbic_regs,csr);
2618	printf("%s: asr:csr(%02x:%02x)->(%02x:%02x)\n",
2619	       (routine==1)?"sbicgo":
2620	       (routine==2)?"sbicintr":
2621	       (routine==3)?"sbicicmd":
2622	       (routine==4)?"sbicnext":"unknown",
2623	       debug_asr, debug_csr, asr, csr);
2624
2625}
2626
2627void
2628sbictimeout(struct sbic_softc *dev)
2629{
2630	int s, asr;
2631
2632	s = splbio();
2633	if (dev->sc_dmatimo) {
2634		if (dev->sc_dmatimo > 1) {
2635			printf("%s: DMA timeout #%d\n",
2636			    dev->sc_dev.dv_xname, dev->sc_dmatimo - 1);
2637			GET_SBIC_asr(dev->sc_sbic, asr);
2638			if( asr & SBIC_ASR_INT ) {
2639				/* We need to service a missed IRQ */
2640				printf("Servicing a missed int:(%02x,%02x)->(%02x,?)\n",
2641				    debug_asr, debug_csr, asr);
2642				sbicintr(dev);
2643			}
2644			sbicdumpstate();
2645		}
2646		dev->sc_dmatimo++;
2647	}
2648	splx(s);
2649	callout_reset(&dev->sc_timo_ch, 30 * hz,
2650	    (void *)sbictimeout, dev);
2651}
2652
2653void
2654sbic_dump_acb(struct sbic_acb *acb)
2655{
2656	u_char *b = (u_char *) &acb->cmd;
2657	int i;
2658
2659	printf("acb@%p ", acb);
2660	if (acb->xs == NULL) {
2661		printf("<unused>\n");
2662		return;
2663	}
2664	printf("(%d:%d) flags %2x clen %2d cmd ",
2665		acb->xs->xs_periph->periph_target,
2666	    acb->xs->xs_periph->periph_lun, acb->flags, acb->clen);
2667	for (i = acb->clen; i; --i)
2668		printf(" %02x", *b++);
2669	printf("\n");
2670	printf("  xs: %8p data %8p:%04x ", acb->xs, acb->xs->data,
2671	    acb->xs->datalen);
2672	printf("va %8p:%04x ", acb->sc_kv.dc_addr, acb->sc_kv.dc_count);
2673	printf("pa %8p:%04x tcnt %lx\n", acb->sc_pa.dc_addr, acb->sc_pa.dc_count,
2674	    acb->sc_tcnt);
2675}
2676
2677void
2678sbic_dump(struct sbic_softc *dev)
2679{
2680	sbic_regmap_t regs;
2681	u_char csr, asr;
2682	struct sbic_acb *acb;
2683	int s;
2684	int i;
2685
2686	s = splbio();
2687	regs = dev->sc_sbic;
2688#if CSR_TRACE_SIZE
2689	printf("csr trace: ");
2690	i = csr_traceptr;
2691	do {
2692		printf("%c%02x%02x%02x ", csr_trace[i].whr,
2693		    csr_trace[i].csr, csr_trace[i].asr, csr_trace[i].xtn);
2694		switch(csr_trace[i].whr) {
2695		case 'g':
2696			printf("go "); break;
2697		case 's':
2698			printf("select "); break;
2699		case 'y':
2700			printf("select+ "); break;
2701		case 'i':
2702			printf("intr "); break;
2703		case 'f':
2704			printf("finish "); break;
2705		case '>':
2706			printf("out "); break;
2707		case '<':
2708			printf("in "); break;
2709		case 'm':
2710			printf("msgin "); break;
2711		case 'x':
2712			printf("msginx "); break;
2713		case 'X':
2714			printf("msginX "); break;
2715		case 'r':
2716			printf("reselect "); break;
2717		case 'I':
2718			printf("icmd "); break;
2719		case 'a':
2720			printf("abort "); break;
2721		default:
2722			printf("? ");
2723		}
2724		switch(csr_trace[i].csr) {
2725		case 0x11:
2726			printf("INITIATOR"); break;
2727		case 0x16:
2728			printf("S_XFERRED"); break;
2729		case 0x20:
2730			printf("MSGIN_ACK"); break;
2731		case 0x41:
2732			printf("DISC"); break;
2733		case 0x42:
2734			printf("SEL_TIMEO"); break;
2735		case 0x80:
2736			printf("RSLT_NI"); break;
2737		case 0x81:
2738			printf("RSLT_IFY"); break;
2739		case 0x85:
2740			printf("DISC_1"); break;
2741		case 0x18: case 0x19: case 0x1a:
2742		case 0x1b: case 0x1e: case 0x1f:
2743		case 0x28: case 0x29: case 0x2a:
2744		case 0x2b: case 0x2e: case 0x2f:
2745		case 0x48: case 0x49: case 0x4a:
2746		case 0x4b: case 0x4e: case 0x4f:
2747		case 0x88: case 0x89: case 0x8a:
2748		case 0x8b: case 0x8e: case 0x8f:
2749			switch(csr_trace[i].csr & 0xf0) {
2750			case 0x10:
2751				printf("DONE_"); break;
2752			case 0x20:
2753				printf("STOP_"); break;
2754			case 0x40:
2755				printf("ERR_"); break;
2756			case 0x80:
2757				printf("REQ_"); break;
2758			}
2759			switch(csr_trace[i].csr & 7) {
2760			case 0:
2761				printf("DATA_OUT"); break;
2762			case 1:
2763				printf("DATA_IN"); break;
2764			case 2:
2765				printf("CMD"); break;
2766			case 3:
2767				printf("STATUS"); break;
2768			case 6:
2769				printf("MSG_OUT"); break;
2770			case 7:
2771				printf("MSG_IN"); break;
2772			default:
2773				printf("invld phs");
2774			}
2775			break;
2776		default:    printf("****"); break;
2777		}
2778		if (csr_trace[i].asr & SBIC_ASR_INT)
2779			printf(" ASR_INT");
2780		if (csr_trace[i].asr & SBIC_ASR_LCI)
2781			printf(" ASR_LCI");
2782		if (csr_trace[i].asr & SBIC_ASR_BSY)
2783			printf(" ASR_BSY");
2784		if (csr_trace[i].asr & SBIC_ASR_CIP)
2785			printf(" ASR_CIP");
2786		printf("\n");
2787		i = (i + 1) & (CSR_TRACE_SIZE - 1);
2788	} while (i != csr_traceptr);
2789#endif
2790	GET_SBIC_asr(regs, asr);
2791	if ((asr & SBIC_ASR_INT) == 0)
2792		GET_SBIC_csr(regs, csr);
2793	else
2794		csr = 0;
2795	printf("%s@%p regs %p/%p asr %x csr %x\n", dev->sc_dev.dv_xname,
2796	    dev, regs.sbic_asr_p, regs.sbic_value_p, asr, csr);
2797	if ((acb = dev->free_list.tqh_first)) {
2798		printf("Free list:\n");
2799		while (acb) {
2800			sbic_dump_acb(acb);
2801			acb = acb->chain.tqe_next;
2802		}
2803	}
2804	if ((acb = dev->ready_list.tqh_first)) {
2805		printf("Ready list:\n");
2806		while (acb) {
2807			sbic_dump_acb(acb);
2808			acb = acb->chain.tqe_next;
2809		}
2810	}
2811	if ((acb = dev->nexus_list.tqh_first)) {
2812		printf("Nexus list:\n");
2813		while (acb) {
2814			sbic_dump_acb(acb);
2815			acb = acb->chain.tqe_next;
2816		}
2817	}
2818	if (dev->sc_nexus) {
2819		printf("nexus:\n");
2820		sbic_dump_acb(dev->sc_nexus);
2821	}
2822	printf("sc_xs %p targ %d lun %d flags %x tcnt %lx dmacmd %x mask %lx\n",
2823	    dev->sc_xs, dev->target, dev->lun, dev->sc_flags, dev->sc_tcnt,
2824	    dev->sc_dmacmd, dev->sc_dmamask);
2825	for (i = 0; i < 8; ++i) {
2826		if (dev->sc_tinfo[i].cmds > 2) {
2827			printf("tgt %d: cmds %d disc %d lubusy %x\n",
2828			    i, dev->sc_tinfo[i].cmds,
2829			    dev->sc_tinfo[i].dconns,
2830			    dev->sc_tinfo[i].lubusy);
2831		}
2832	}
2833	splx(s);
2834}
2835
2836#endif
2837