Merge from vendor branch LESS:
[dragonfly.git] / sys / dev / disk / ncr / ncr.c
1 /**************************************************************************
2 **
3 ** $FreeBSD: src/sys/pci/ncr.c,v 1.155.2.3 2001/03/05 13:09:10 obrien Exp $
4 ** $DragonFly: src/sys/dev/disk/ncr/ncr.c,v 1.7 2004/03/15 01:10:44 dillon Exp $
5 **
6 **  Device driver for the   NCR 53C8XX   PCI-SCSI-Controller Family.
7 **
8 **-------------------------------------------------------------------------
9 **
10 **  Written for 386bsd and FreeBSD by
11 **      Wolfgang Stanglmeier    <wolf@cologne.de>
12 **      Stefan Esser            <se@mi.Uni-Koeln.de>
13 **
14 **-------------------------------------------------------------------------
15 **
16 ** Copyright (c) 1994 Wolfgang Stanglmeier.  All rights reserved.
17 **
18 ** Redistribution and use in source and binary forms, with or without
19 ** modification, are permitted provided that the following conditions
20 ** are met:
21 ** 1. Redistributions of source code must retain the above copyright
22 **    notice, this list of conditions and the following disclaimer.
23 ** 2. Redistributions in binary form must reproduce the above copyright
24 **    notice, this list of conditions and the following disclaimer in the
25 **    documentation and/or other materials provided with the distribution.
26 ** 3. The name of the author may not be used to endorse or promote products
27 **    derived from this software without specific prior written permission.
28 **
29 ** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
30 ** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
31 ** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
32 ** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
33 ** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
34 ** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
35 ** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
36 ** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
37 ** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
38 ** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
39 **
40 ***************************************************************************
41 */
42
43 #define NCR_DATE "pl30 98/1/1"
44
45 #define NCR_VERSION     (2)
46 #define MAX_UNITS       (16)
47
48 #define NCR_GETCC_WITHMSG
49
50 #if (defined(__DragonFly__) || defined (__FreeBSD__)) && defined(_KERNEL)
51 #include "opt_ncr.h"
52 #endif
53
54 /*==========================================================
55 **
56 **      Configuration and Debugging
57 **
58 **      May be overwritten in <arch/conf/xxxx>
59 **
60 **==========================================================
61 */
62
63 /*
64 **    SCSI address of this device.
65 **    The boot routines should have set it.
66 **    If not, use this.
67 */
68
69 #ifndef SCSI_NCR_MYADDR
70 #define SCSI_NCR_MYADDR      (7)
71 #endif /* SCSI_NCR_MYADDR */
72
73 /*
74 **    The default synchronous period factor
75 **    (0=asynchronous)
76 **    If maximum synchronous frequency is defined, use it instead.
77 */
78
79 #ifndef SCSI_NCR_MAX_SYNC
80
81 #ifndef SCSI_NCR_DFLT_SYNC
82 #define SCSI_NCR_DFLT_SYNC   (12)
83 #endif /* SCSI_NCR_DFLT_SYNC */
84
85 #else
86
87 #if     SCSI_NCR_MAX_SYNC == 0
88 #define SCSI_NCR_DFLT_SYNC 0
89 #else
90 #define SCSI_NCR_DFLT_SYNC (250000 / SCSI_NCR_MAX_SYNC)
91 #endif
92
93 #endif
94
95 /*
96 **    The minimal asynchronous pre-scaler period (ns)
97 **    Shall be 40.
98 */
99
100 #ifndef SCSI_NCR_MIN_ASYNC
101 #define SCSI_NCR_MIN_ASYNC   (40)
102 #endif /* SCSI_NCR_MIN_ASYNC */
103
104 /*
105 **    The maximal bus with (in log2 byte)
106 **    (0=8 bit, 1=16 bit)
107 */
108
109 #ifndef SCSI_NCR_MAX_WIDE
110 #define SCSI_NCR_MAX_WIDE   (1)
111 #endif /* SCSI_NCR_MAX_WIDE */
112
113 /*==========================================================
114 **
115 **      Configuration and Debugging
116 **
117 **==========================================================
118 */
119
120 /*
121 **    Number of targets supported by the driver.
122 **    n permits target numbers 0..n-1.
123 **    Default is 7, meaning targets #0..#6.
124 **    #7 .. is myself.
125 */
126
127 #define MAX_TARGET  (16)
128
129 /*
130 **    Number of logic units supported by the driver.
131 **    n enables logic unit numbers 0..n-1.
132 **    The common SCSI devices require only
133 **    one lun, so take 1 as the default.
134 */
135
136 #ifndef MAX_LUN
137 #define MAX_LUN     (8)
138 #endif  /* MAX_LUN */
139
140 /*
141 **    The maximum number of jobs scheduled for starting.
142 **    There should be one slot per target, and one slot
143 **    for each tag of each target in use.
144 */
145
146 #define MAX_START   (256)
147
148 /*
149 **    The maximum number of segments a transfer is split into.
150 */
151
152 #define MAX_SCATTER (33)
153
154 /*
155 **    The maximum transfer length (should be >= 64k).
156 **    MUST NOT be greater than (MAX_SCATTER-1) * PAGE_SIZE.
157 */
158
159 #define MAX_SIZE  ((MAX_SCATTER-1) * (long) PAGE_SIZE)
160
161 /*
162 **      other
163 */
164
165 #define NCR_SNOOP_TIMEOUT (1000000)
166
167 /*==========================================================
168 **
169 **      Include files
170 **
171 **==========================================================
172 */
173
174 #include <sys/param.h>
175 #include <sys/time.h>
176
177 #ifdef _KERNEL
178 #include <sys/systm.h>
179 #include <sys/malloc.h>
180 #include <sys/buf.h>
181 #include <sys/kernel.h>
182 #include <sys/sysctl.h>
183 #include <sys/bus.h>
184 #include <machine/clock.h>
185 #include <machine/md_var.h>
186 #include <machine/bus.h>
187 #include <machine/resource.h>
188 #include <sys/rman.h>
189 #include <vm/vm.h>
190 #include <vm/pmap.h>
191 #include <vm/vm_extern.h>
192 #endif
193
194 #include <bus/pci/pcivar.h>
195 #include <bus/pci/pcireg.h>
196 #include "ncrreg.h"
197
198 #include <bus/cam/cam.h>
199 #include <bus/cam/cam_ccb.h>
200 #include <bus/cam/cam_sim.h>
201 #include <bus/cam/cam_xpt_sim.h>
202 #include <bus/cam/cam_debug.h>
203
204 #include <bus/cam/scsi/scsi_all.h>
205 #include <bus/cam/scsi/scsi_message.h>
206
207 /*==========================================================
208 **
209 **      Debugging tags
210 **
211 **==========================================================
212 */
213
214 #define DEBUG_ALLOC    (0x0001)
215 #define DEBUG_PHASE    (0x0002)
216 #define DEBUG_POLL     (0x0004)
217 #define DEBUG_QUEUE    (0x0008)
218 #define DEBUG_RESULT   (0x0010)
219 #define DEBUG_SCATTER  (0x0020)
220 #define DEBUG_SCRIPT   (0x0040)
221 #define DEBUG_TINY     (0x0080)
222 #define DEBUG_TIMING   (0x0100)
223 #define DEBUG_NEGO     (0x0200)
224 #define DEBUG_TAGS     (0x0400)
225 #define DEBUG_FREEZE   (0x0800)
226 #define DEBUG_RESTART  (0x1000)
227
228 /*
229 **    Enable/Disable debug messages.
230 **    Can be changed at runtime too.
231 */
232 #ifdef SCSI_NCR_DEBUG
233         #define DEBUG_FLAGS ncr_debug
234 #else /* SCSI_NCR_DEBUG */
235         #define SCSI_NCR_DEBUG  0
236         #define DEBUG_FLAGS     0
237 #endif /* SCSI_NCR_DEBUG */
238
239
240
241 /*==========================================================
242 **
243 **      assert ()
244 **
245 **==========================================================
246 **
247 **      modified copy from 386bsd:/usr/include/sys/assert.h
248 **
249 **----------------------------------------------------------
250 */
251
252 #ifdef DIAGNOSTIC
253 #define assert(expression) {                                    \
254         if (!(expression)) {                                    \
255                 (void)printf("assertion \"%s\" failed: "        \
256                              "file \"%s\", line %d\n",          \
257                              #expression, __FILE__, __LINE__);  \
258              Debugger("");                                      \
259         }                                                       \
260 }
261 #else
262 #define assert(expression) {                                    \
263         if (!(expression)) {                                    \
264                 (void)printf("assertion \"%s\" failed: "        \
265                              "file \"%s\", line %d\n",          \
266                              #expression, __FILE__, __LINE__);  \
267         }                                                       \
268 }
269 #endif
270
271 /*==========================================================
272 **
273 **      Access to the controller chip.
274 **
275 **==========================================================
276 */
277
278 #ifdef __alpha__
279 /* XXX */
280 #undef vtophys
281 #define vtophys(va)     alpha_XXX_dmamap((vm_offset_t)va)
282 #endif
283
284 #define INB(r) bus_space_read_1(np->bst, np->bsh, offsetof(struct ncr_reg, r))
285 #define INW(r) bus_space_read_2(np->bst, np->bsh, offsetof(struct ncr_reg, r))
286 #define INL(r) bus_space_read_4(np->bst, np->bsh, offsetof(struct ncr_reg, r))
287
288 #define OUTB(r, val) bus_space_write_1(np->bst, np->bsh, \
289                                        offsetof(struct ncr_reg, r), val)
290 #define OUTW(r, val) bus_space_write_2(np->bst, np->bsh, \
291                                        offsetof(struct ncr_reg, r), val)
292 #define OUTL(r, val) bus_space_write_4(np->bst, np->bsh, \
293                                        offsetof(struct ncr_reg, r), val)
294 #define OUTL_OFF(o, val) bus_space_write_4(np->bst, np->bsh, o, val)
295
296 #define INB_OFF(o) bus_space_read_1(np->bst, np->bsh, o)
297 #define INW_OFF(o) bus_space_read_2(np->bst, np->bsh, o)
298 #define INL_OFF(o) bus_space_read_4(np->bst, np->bsh, o)
299
300 #define READSCRIPT_OFF(base, off)                                       \
301     (base ? *((volatile u_int32_t *)((volatile char *)base + (off))) :  \
302     bus_space_read_4(np->bst2, np->bsh2, off))
303
304 #define WRITESCRIPT_OFF(base, off, val)                                 \
305     do {                                                                \
306         if (base)                                                       \
307                 *((volatile u_int32_t *)                                \
308                         ((volatile char *)base + (off))) = (val);       \
309         else                                                            \
310                 bus_space_write_4(np->bst2, np->bsh2, off, val);        \
311     } while (0)
312
313 #define READSCRIPT(r) \
314     READSCRIPT_OFF(np->script, offsetof(struct script, r))
315
316 #define WRITESCRIPT(r, val) \
317     WRITESCRIPT_OFF(np->script, offsetof(struct script, r), val)
318
319 /*
320 **      Set bit field ON, OFF 
321 */
322
323 #define OUTONB(r, m)    OUTB(r, INB(r) | (m))
324 #define OUTOFFB(r, m)   OUTB(r, INB(r) & ~(m))
325 #define OUTONW(r, m)    OUTW(r, INW(r) | (m))
326 #define OUTOFFW(r, m)   OUTW(r, INW(r) & ~(m))
327 #define OUTONL(r, m)    OUTL(r, INL(r) | (m))
328 #define OUTOFFL(r, m)   OUTL(r, INL(r) & ~(m))
329
330 /*==========================================================
331 **
332 **      Command control block states.
333 **
334 **==========================================================
335 */
336
337 #define HS_IDLE         (0)
338 #define HS_BUSY         (1)
339 #define HS_NEGOTIATE    (2)     /* sync/wide data transfer*/
340 #define HS_DISCONNECT   (3)     /* Disconnected by target */
341
342 #define HS_COMPLETE     (4)
343 #define HS_SEL_TIMEOUT  (5)     /* Selection timeout      */
344 #define HS_RESET        (6)     /* SCSI reset        */
345 #define HS_ABORTED      (7)     /* Transfer aborted       */
346 #define HS_TIMEOUT      (8)     /* Software timeout       */
347 #define HS_FAIL         (9)     /* SCSI or PCI bus errors */
348 #define HS_UNEXPECTED   (10)    /* Unexpected disconnect  */
349 #define HS_STALL        (11)    /* QUEUE FULL or BUSY     */
350
351 #define HS_DONEMASK     (0xfc)
352
353 /*==========================================================
354 **
355 **      Software Interrupt Codes
356 **
357 **==========================================================
358 */
359
360 #define SIR_SENSE_RESTART       (1)
361 #define SIR_SENSE_FAILED        (2)
362 #define SIR_STALL_RESTART       (3)
363 #define SIR_STALL_QUEUE         (4)
364 #define SIR_NEGO_SYNC           (5)
365 #define SIR_NEGO_WIDE           (6)
366 #define SIR_NEGO_FAILED         (7)
367 #define SIR_NEGO_PROTO          (8)
368 #define SIR_REJECT_RECEIVED     (9)
369 #define SIR_REJECT_SENT         (10)
370 #define SIR_IGN_RESIDUE         (11)
371 #define SIR_MISSING_SAVE        (12)
372 #define SIR_MAX                 (12)
373
374 /*==========================================================
375 **
376 **      Extended error codes.
377 **      xerr_status field of struct nccb.
378 **
379 **==========================================================
380 */
381
382 #define XE_OK           (0)
383 #define XE_EXTRA_DATA   (1)     /* unexpected data phase */
384 #define XE_BAD_PHASE    (2)     /* illegal phase (4/5)   */
385
386 /*==========================================================
387 **
388 **      Negotiation status.
389 **      nego_status field       of struct nccb.
390 **
391 **==========================================================
392 */
393
394 #define NS_SYNC         (1)
395 #define NS_WIDE         (2)
396
397 /*==========================================================
398 **
399 **      XXX These are no longer used.  Remove once the
400 **          script is updated.
401 **      "Special features" of targets.
402 **      quirks field of struct tcb.
403 **      actualquirks field of struct nccb.
404 **
405 **==========================================================
406 */
407
408 #define QUIRK_AUTOSAVE  (0x01)
409 #define QUIRK_NOMSG     (0x02)
410 #define QUIRK_NOSYNC    (0x10)
411 #define QUIRK_NOWIDE16  (0x20)
412 #define QUIRK_NOTAGS    (0x40)
413 #define QUIRK_UPDATE    (0x80)
414
415 /*==========================================================
416 **
417 **      Misc.
418 **
419 **==========================================================
420 */
421
422 #define CCB_MAGIC       (0xf2691ad2)
423 #define MAX_TAGS        (32)            /* hard limit */
424
425 /*==========================================================
426 **
427 **      OS dependencies.
428 **
429 **==========================================================
430 */
431
432 #define PRINT_ADDR(ccb) xpt_print_path((ccb)->ccb_h.path)
433
434 /*==========================================================
435 **
436 **      Declaration of structs.
437 **
438 **==========================================================
439 */
440
441 struct tcb;
442 struct lcb;
443 struct nccb;
444 struct ncb;
445 struct script;
446
447 typedef struct ncb * ncb_p;
448 typedef struct tcb * tcb_p;
449 typedef struct lcb * lcb_p;
450 typedef struct nccb * nccb_p;
451
452 struct link {
453         ncrcmd  l_cmd;
454         ncrcmd  l_paddr;
455 };
456
457 struct  usrcmd {
458         u_long  target;
459         u_long  lun;
460         u_long  data;
461         u_long  cmd;
462 };
463
464 #define UC_SETSYNC      10
465 #define UC_SETTAGS      11
466 #define UC_SETDEBUG     12
467 #define UC_SETORDER     13
468 #define UC_SETWIDE      14
469 #define UC_SETFLAG      15
470
471 #define UF_TRACE        (0x01)
472
473 /*---------------------------------------
474 **
475 **      Timestamps for profiling
476 **
477 **---------------------------------------
478 */
479
480 /* Type of the kernel variable `ticks'.  XXX should be declared with the var. */
481 typedef int ticks_t;
482
483 struct tstamp {
484         ticks_t start;
485         ticks_t end;
486         ticks_t select;
487         ticks_t command;
488         ticks_t data;
489         ticks_t status;
490         ticks_t disconnect;
491 };
492
493 /*
494 **      profiling data (per device)
495 */
496
497 struct profile {
498         u_long  num_trans;
499         u_long  num_bytes;
500         u_long  num_disc;
501         u_long  num_break;
502         u_long  num_int;
503         u_long  num_fly;
504         u_long  ms_setup;
505         u_long  ms_data;
506         u_long  ms_disc;
507         u_long  ms_post;
508 };
509
510 /*==========================================================
511 **
512 **      Declaration of structs:         target control block
513 **
514 **==========================================================
515 */
516
517 #define NCR_TRANS_CUR           0x01    /* Modify current neogtiation status */
518 #define NCR_TRANS_ACTIVE        0x03    /* Assume this is the active target */
519 #define NCR_TRANS_GOAL          0x04    /* Modify negotiation goal */
520 #define NCR_TRANS_USER          0x08    /* Modify user negotiation settings */
521
522 struct ncr_transinfo {
523         u_int8_t width;
524         u_int8_t period;
525         u_int8_t offset;
526 };
527
528 struct ncr_target_tinfo {
529         /* Hardware version of our sync settings */
530         u_int8_t disc_tag;
531 #define         NCR_CUR_DISCENB 0x01
532 #define         NCR_CUR_TAGENB  0x02
533 #define         NCR_USR_DISCENB 0x04
534 #define         NCR_USR_TAGENB  0x08
535         u_int8_t sval;
536         struct   ncr_transinfo current;
537         struct   ncr_transinfo goal;
538         struct   ncr_transinfo user;
539         /* Hardware version of our wide settings */
540         u_int8_t wval;
541 };
542
543 struct tcb {
544         /*
545         **      during reselection the ncr jumps to this point
546         **      with SFBR set to the encoded target number
547         **      with bit 7 set.
548         **      if it's not this target, jump to the next.
549         **
550         **      JUMP  IF (SFBR != #target#)
551         **      @(next tcb)
552         */
553
554         struct link   jump_tcb;
555
556         /*
557         **      load the actual values for the sxfer and the scntl3
558         **      register (sync/wide mode).
559         **
560         **      SCR_COPY (1);
561         **      @(sval field of this tcb)
562         **      @(sxfer register)
563         **      SCR_COPY (1);
564         **      @(wval field of this tcb)
565         **      @(scntl3 register)
566         */
567
568         ncrcmd  getscr[6];
569
570         /*
571         **      if next message is "identify"
572         **      then load the message to SFBR,
573         **      else load 0 to SFBR.
574         **
575         **      CALL
576         **      <RESEL_LUN>
577         */
578
579         struct link   call_lun;
580
581         /*
582         **      now look for the right lun.
583         **
584         **      JUMP
585         **      @(first nccb of this lun)
586         */
587
588         struct link   jump_lcb;
589
590         /*
591         **      pointer to interrupted getcc nccb
592         */
593
594         nccb_p   hold_cp;
595
596         /*
597         **      pointer to nccb used for negotiating.
598         **      Avoid to start a nego for all queued commands 
599         **      when tagged command queuing is enabled.
600         */
601
602         nccb_p   nego_cp;
603
604         /*
605         **      statistical data
606         */
607
608         u_long  transfers;
609         u_long  bytes;
610
611         /*
612         **      user settable limits for sync transfer
613         **      and tagged commands.
614         */
615
616         struct   ncr_target_tinfo tinfo;
617
618         /*
619         **      the lcb's of this tcb
620         */
621
622         lcb_p   lp[MAX_LUN];
623 };
624
625 /*==========================================================
626 **
627 **      Declaration of structs:         lun control block
628 **
629 **==========================================================
630 */
631
632 struct lcb {
633         /*
634         **      during reselection the ncr jumps to this point
635         **      with SFBR set to the "Identify" message.
636         **      if it's not this lun, jump to the next.
637         **
638         **      JUMP  IF (SFBR != #lun#)
639         **      @(next lcb of this target)
640         */
641
642         struct link     jump_lcb;
643
644         /*
645         **      if next message is "simple tag",
646         **      then load the tag to SFBR,
647         **      else load 0 to SFBR.
648         **
649         **      CALL
650         **      <RESEL_TAG>
651         */
652
653         struct link     call_tag;
654
655         /*
656         **      now look for the right nccb.
657         **
658         **      JUMP
659         **      @(first nccb of this lun)
660         */
661
662         struct link     jump_nccb;
663
664         /*
665         **      start of the nccb chain
666         */
667
668         nccb_p  next_nccb;
669
670         /*
671         **      Control of tagged queueing
672         */
673
674         u_char          reqnccbs;
675         u_char          reqlink;
676         u_char          actlink;
677         u_char          usetags;
678         u_char          lasttag;
679 };
680
681 /*==========================================================
682 **
683 **      Declaration of structs:     COMMAND control block
684 **
685 **==========================================================
686 **
687 **      This substructure is copied from the nccb to a
688 **      global address after selection (or reselection)
689 **      and copied back before disconnect.
690 **
691 **      These fields are accessible to the script processor.
692 **
693 **----------------------------------------------------------
694 */
695
696 struct head {
697         /*
698         **      Execution of a nccb starts at this point.
699         **      It's a jump to the "SELECT" label
700         **      of the script.
701         **
702         **      After successful selection the script
703         **      processor overwrites it with a jump to
704         **      the IDLE label of the script.
705         */
706
707         struct link     launch;
708
709         /*
710         **      Saved data pointer.
711         **      Points to the position in the script
712         **      responsible for the actual transfer
713         **      of data.
714         **      It's written after reception of a
715         **      "SAVE_DATA_POINTER" message.
716         **      The goalpointer points after
717         **      the last transfer command.
718         */
719
720         u_int32_t       savep;
721         u_int32_t       lastp;
722         u_int32_t       goalp;
723
724         /*
725         **      The virtual address of the nccb
726         **      containing this header.
727         */
728
729         nccb_p  cp;
730
731         /*
732         **      space for some timestamps to gather
733         **      profiling data about devices and this driver.
734         */
735
736         struct tstamp   stamp;
737
738         /*
739         **      status fields.
740         */
741
742         u_char          status[8];
743 };
744
745 /*
746 **      The status bytes are used by the host and the script processor.
747 **
748 **      The first four byte are copied to the scratchb register
749 **      (declared as scr0..scr3 in ncr_reg.h) just after the select/reselect,
750 **      and copied back just after disconnecting.
751 **      Inside the script the XX_REG are used.
752 **
753 **      The last four bytes are used inside the script by "COPY" commands.
754 **      Because source and destination must have the same alignment
755 **      in a longword, the fields HAVE to be at the choosen offsets.
756 **              xerr_st (4)     0       (0x34)  scratcha
757 **              sync_st (5)     1       (0x05)  sxfer
758 **              wide_st (7)     3       (0x03)  scntl3
759 */
760
761 /*
762 **      First four bytes (script)
763 */
764 #define  QU_REG scr0
765 #define  HS_REG scr1
766 #define  HS_PRT nc_scr1
767 #define  SS_REG scr2
768 #define  PS_REG scr3
769
770 /*
771 **      First four bytes (host)
772 */
773 #define  actualquirks  phys.header.status[0]
774 #define  host_status   phys.header.status[1]
775 #define  s_status      phys.header.status[2]
776 #define  parity_status phys.header.status[3]
777
778 /*
779 **      Last four bytes (script)
780 */
781 #define  xerr_st       header.status[4] /* MUST be ==0 mod 4 */
782 #define  sync_st       header.status[5] /* MUST be ==1 mod 4 */
783 #define  nego_st       header.status[6]
784 #define  wide_st       header.status[7] /* MUST be ==3 mod 4 */
785
786 /*
787 **      Last four bytes (host)
788 */
789 #define  xerr_status   phys.xerr_st
790 #define  sync_status   phys.sync_st
791 #define  nego_status   phys.nego_st
792 #define  wide_status   phys.wide_st
793
794 /*==========================================================
795 **
796 **      Declaration of structs:     Data structure block
797 **
798 **==========================================================
799 **
800 **      During execution of a nccb by the script processor,
801 **      the DSA (data structure address) register points
802 **      to this substructure of the nccb.
803 **      This substructure contains the header with
804 **      the script-processor-changable data and
805 **      data blocks for the indirect move commands.
806 **
807 **----------------------------------------------------------
808 */
809
810 struct dsb {
811
812         /*
813         **      Header.
814         **      Has to be the first entry,
815         **      because it's jumped to by the
816         **      script processor
817         */
818
819         struct head     header;
820
821         /*
822         **      Table data for Script
823         */
824
825         struct scr_tblsel  select;
826         struct scr_tblmove smsg  ;
827         struct scr_tblmove smsg2 ;
828         struct scr_tblmove cmd   ;
829         struct scr_tblmove scmd  ;
830         struct scr_tblmove sense ;
831         struct scr_tblmove data [MAX_SCATTER];
832 };
833
834 /*==========================================================
835 **
836 **      Declaration of structs:     Command control block.
837 **
838 **==========================================================
839 **
840 **      During execution of a nccb by the script processor,
841 **      the DSA (data structure address) register points
842 **      to this substructure of the nccb.
843 **      This substructure contains the header with
844 **      the script-processor-changable data and then
845 **      data blocks for the indirect move commands.
846 **
847 **----------------------------------------------------------
848 */
849
850
851 struct nccb {
852         /*
853         **      This filler ensures that the global header is 
854         **      cache line size aligned.
855         */
856         ncrcmd  filler[4];
857
858         /*
859         **      during reselection the ncr jumps to this point.
860         **      If a "SIMPLE_TAG" message was received,
861         **      then SFBR is set to the tag.
862         **      else SFBR is set to 0
863         **      If looking for another tag, jump to the next nccb.
864         **
865         **      JUMP  IF (SFBR != #TAG#)
866         **      @(next nccb of this lun)
867         */
868
869         struct link             jump_nccb;
870
871         /*
872         **      After execution of this call, the return address
873         **      (in  the TEMP register) points to the following
874         **      data structure block.
875         **      So copy it to the DSA register, and start
876         **      processing of this data structure.
877         **
878         **      CALL
879         **      <RESEL_TMP>
880         */
881
882         struct link             call_tmp;
883
884         /*
885         **      This is the data structure which is
886         **      to be executed by the script processor.
887         */
888
889         struct dsb              phys;
890
891         /*
892         **      If a data transfer phase is terminated too early
893         **      (after reception of a message (i.e. DISCONNECT)),
894         **      we have to prepare a mini script to transfer
895         **      the rest of the data.
896         */
897
898         ncrcmd                  patch[8];
899
900         /*
901         **      The general SCSI driver provides a
902         **      pointer to a control block.
903         */
904
905         union   ccb *ccb;
906
907         /*
908         **      We prepare a message to be sent after selection,
909         **      and a second one to be sent after getcc selection.
910         **      Contents are IDENTIFY and SIMPLE_TAG.
911         **      While negotiating sync or wide transfer,
912         **      a SDTM or WDTM message is appended.
913         */
914
915         u_char                  scsi_smsg [8];
916         u_char                  scsi_smsg2[8];
917
918         /*
919         **      Lock this nccb.
920         **      Flag is used while looking for a free nccb.
921         */
922
923         u_long          magic;
924
925         /*
926         **      Physical address of this instance of nccb
927         */
928
929         u_long          p_nccb;
930
931         /*
932         **      Completion time out for this job.
933         **      It's set to time of start + allowed number of seconds.
934         */
935
936         time_t          tlimit;
937
938         /*
939         **      All nccbs of one hostadapter are chained.
940         */
941
942         nccb_p          link_nccb;
943
944         /*
945         **      All nccbs of one target/lun are chained.
946         */
947
948         nccb_p          next_nccb;
949
950         /*
951         **      Sense command
952         */
953
954         u_char          sensecmd[6];
955
956         /*
957         **      Tag for this transfer.
958         **      It's patched into jump_nccb.
959         **      If it's not zero, a SIMPLE_TAG
960         **      message is included in smsg.
961         */
962
963         u_char                  tag;
964 };
965
966 #define CCB_PHYS(cp,lbl)        (cp->p_nccb + offsetof(struct nccb, lbl))
967
968 /*==========================================================
969 **
970 **      Declaration of structs:     NCR device descriptor
971 **
972 **==========================================================
973 */
974
975 struct ncb {
976         /*
977         **      The global header.
978         **      Accessible to both the host and the
979         **      script-processor.
980         **      We assume it is cache line size aligned.
981         */
982         struct head     header;
983
984         int     unit;
985
986         /*-----------------------------------------------
987         **      Scripts ..
988         **-----------------------------------------------
989         **
990         **      During reselection the ncr jumps to this point.
991         **      The SFBR register is loaded with the encoded target id.
992         **
993         **      Jump to the first target.
994         **
995         **      JUMP
996         **      @(next tcb)
997         */
998         struct link     jump_tcb;
999
1000         /*-----------------------------------------------
1001         **      Configuration ..
1002         **-----------------------------------------------
1003         **
1004         **      virtual and physical addresses
1005         **      of the 53c810 chip.
1006         */
1007         int             reg_rid;
1008         struct resource *reg_res;
1009         bus_space_tag_t bst;
1010         bus_space_handle_t bsh;
1011
1012         int             sram_rid;
1013         struct resource *sram_res;
1014         bus_space_tag_t bst2;
1015         bus_space_handle_t bsh2;
1016
1017         struct resource *irq_res;
1018         void            *irq_handle;
1019
1020         /*
1021         **      Scripts instance virtual address.
1022         */
1023         struct script   *script;
1024         struct scripth  *scripth;
1025
1026         /*
1027         **      Scripts instance physical address.
1028         */
1029         u_long          p_script;
1030         u_long          p_scripth;
1031
1032         /*
1033         **      The SCSI address of the host adapter.
1034         */
1035         u_char          myaddr;
1036
1037         /*
1038         **      timing parameters
1039         */
1040         u_char          minsync;        /* Minimum sync period factor   */
1041         u_char          maxsync;        /* Maximum sync period factor   */
1042         u_char          maxoffs;        /* Max scsi offset              */
1043         u_char          clock_divn;     /* Number of clock divisors     */
1044         u_long          clock_khz;      /* SCSI clock frequency in KHz  */
1045         u_long          features;       /* Chip features map            */
1046         u_char          multiplier;     /* Clock multiplier (1,2,4)     */
1047
1048         u_char          maxburst;       /* log base 2 of dwords burst   */
1049
1050         /*
1051         **      BIOS supplied PCI bus options
1052         */
1053         u_char          rv_scntl3;
1054         u_char          rv_dcntl;
1055         u_char          rv_dmode;
1056         u_char          rv_ctest3;
1057         u_char          rv_ctest4;
1058         u_char          rv_ctest5;
1059         u_char          rv_gpcntl;
1060         u_char          rv_stest2;
1061
1062         /*-----------------------------------------------
1063         **      CAM SIM information for this instance
1064         **-----------------------------------------------
1065         */
1066
1067         struct          cam_sim  *sim;
1068         struct          cam_path *path;
1069
1070         /*-----------------------------------------------
1071         **      Job control
1072         **-----------------------------------------------
1073         **
1074         **      Commands from user
1075         */
1076         struct usrcmd   user;
1077
1078         /*
1079         **      Target data
1080         */
1081         struct tcb      target[MAX_TARGET];
1082
1083         /*
1084         **      Start queue.
1085         */
1086         u_int32_t       squeue [MAX_START];
1087         u_short         squeueput;
1088
1089         /*
1090         **      Timeout handler
1091         */
1092         time_t          heartbeat;
1093         u_short         ticks;
1094         u_short         latetime;
1095         time_t          lasttime;
1096         struct          callout_handle timeout_ch;
1097
1098         /*-----------------------------------------------
1099         **      Debug and profiling
1100         **-----------------------------------------------
1101         **
1102         **      register dump
1103         */
1104         struct ncr_reg  regdump;
1105         time_t          regtime;
1106
1107         /*
1108         **      Profiling data
1109         */
1110         struct profile  profile;
1111         u_long          disc_phys;
1112         u_long          disc_ref;
1113
1114         /*
1115         **      Head of list of all nccbs for this controller.
1116         */
1117         nccb_p          link_nccb;
1118         
1119         /*
1120         **      message buffers.
1121         **      Should be longword aligned,
1122         **      because they're written with a
1123         **      COPY script command.
1124         */
1125         u_char          msgout[8];
1126         u_char          msgin [8];
1127         u_int32_t       lastmsg;
1128
1129         /*
1130         **      Buffer for STATUS_IN phase.
1131         */
1132         u_char          scratch;
1133
1134         /*
1135         **      controller chip dependent maximal transfer width.
1136         */
1137         u_char          maxwide;
1138
1139 #ifdef NCR_IOMAPPED
1140         /*
1141         **      address of the ncr control registers in io space
1142         */
1143         pci_port_t      port;
1144 #endif
1145 };
1146
1147 #define NCB_SCRIPT_PHYS(np,lbl) (np->p_script + offsetof (struct script, lbl))
1148 #define NCB_SCRIPTH_PHYS(np,lbl) (np->p_scripth + offsetof (struct scripth,lbl))
1149
1150 /*==========================================================
1151 **
1152 **
1153 **      Script for NCR-Processor.
1154 **
1155 **      Use ncr_script_fill() to create the variable parts.
1156 **      Use ncr_script_copy_and_bind() to make a copy and
1157 **      bind to physical addresses.
1158 **
1159 **
1160 **==========================================================
1161 **
1162 **      We have to know the offsets of all labels before
1163 **      we reach them (for forward jumps).
1164 **      Therefore we declare a struct here.
1165 **      If you make changes inside the script,
1166 **      DONT FORGET TO CHANGE THE LENGTHS HERE!
1167 **
1168 **----------------------------------------------------------
1169 */
1170
1171 /*
1172 **      Script fragments which are loaded into the on-board RAM 
1173 **      of 825A, 875 and 895 chips.
1174 */
1175 struct script {
1176         ncrcmd  start           [  7];
1177         ncrcmd  start0          [  2];
1178         ncrcmd  start1          [  3];
1179         ncrcmd  startpos        [  1];
1180         ncrcmd  trysel          [  8];
1181         ncrcmd  skip            [  8];
1182         ncrcmd  skip2           [  3];
1183         ncrcmd  idle            [  2];
1184         ncrcmd  select          [ 18];
1185         ncrcmd  prepare         [  4];
1186         ncrcmd  loadpos         [ 14];
1187         ncrcmd  prepare2        [ 24];
1188         ncrcmd  setmsg          [  5];
1189         ncrcmd  clrack          [  2];
1190         ncrcmd  dispatch        [ 33];
1191         ncrcmd  no_data         [ 17];
1192         ncrcmd  checkatn        [ 10];
1193         ncrcmd  command         [ 15];
1194         ncrcmd  status          [ 27];
1195         ncrcmd  msg_in          [ 26];
1196         ncrcmd  msg_bad         [  6];
1197         ncrcmd  complete        [ 13];
1198         ncrcmd  cleanup         [ 12];
1199         ncrcmd  cleanup0        [  9];
1200         ncrcmd  signal          [ 12];
1201         ncrcmd  save_dp         [  5];
1202         ncrcmd  restore_dp      [  5];
1203         ncrcmd  disconnect      [ 12];
1204         ncrcmd  disconnect0     [  5];
1205         ncrcmd  disconnect1     [ 23];
1206         ncrcmd  msg_out         [  9];
1207         ncrcmd  msg_out_done    [  7];
1208         ncrcmd  badgetcc        [  6];
1209         ncrcmd  reselect        [  8];
1210         ncrcmd  reselect1       [  8];
1211         ncrcmd  reselect2       [  8];
1212         ncrcmd  resel_tmp       [  5];
1213         ncrcmd  resel_lun       [ 18];
1214         ncrcmd  resel_tag       [ 24];
1215         ncrcmd  data_in         [MAX_SCATTER * 4 + 7];
1216         ncrcmd  data_out        [MAX_SCATTER * 4 + 7];
1217 };
1218
1219 /*
1220 **      Script fragments which stay in main memory for all chips.
1221 */
1222 struct scripth {
1223         ncrcmd  tryloop         [MAX_START*5+2];
1224         ncrcmd  msg_parity      [  6];
1225         ncrcmd  msg_reject      [  8];
1226         ncrcmd  msg_ign_residue [ 32];
1227         ncrcmd  msg_extended    [ 18];
1228         ncrcmd  msg_ext_2       [ 18];
1229         ncrcmd  msg_wdtr        [ 27];
1230         ncrcmd  msg_ext_3       [ 18];
1231         ncrcmd  msg_sdtr        [ 27];
1232         ncrcmd  msg_out_abort   [ 10];
1233         ncrcmd  getcc           [  4];
1234         ncrcmd  getcc1          [  5];
1235 #ifdef NCR_GETCC_WITHMSG
1236         ncrcmd  getcc2          [ 29];
1237 #else
1238         ncrcmd  getcc2          [ 14];
1239 #endif
1240         ncrcmd  getcc3          [  6];
1241         ncrcmd  aborttag        [  4];
1242         ncrcmd  abort           [ 22];
1243         ncrcmd  snooptest       [  9];
1244         ncrcmd  snoopend        [  2];
1245 };
1246
1247 /*==========================================================
1248 **
1249 **
1250 **      Function headers.
1251 **
1252 **
1253 **==========================================================
1254 */
1255
1256 #ifdef _KERNEL
1257 static  nccb_p  ncr_alloc_nccb  (ncb_p np, u_long target, u_long lun);
1258 static  void    ncr_complete    (ncb_p np, nccb_p cp);
1259 static  int     ncr_delta       (int * from, int * to);
1260 static  void    ncr_exception   (ncb_p np);
1261 static  void    ncr_free_nccb   (ncb_p np, nccb_p cp);
1262 static  void    ncr_freeze_devq (ncb_p np, struct cam_path *path);
1263 static  void    ncr_selectclock (ncb_p np, u_char scntl3);
1264 static  void    ncr_getclock    (ncb_p np, u_char multiplier);
1265 static  nccb_p  ncr_get_nccb    (ncb_p np, u_long t,u_long l);
1266 #if 0
1267 static  u_int32_t ncr_info      (int unit);
1268 #endif
1269 static  void    ncr_init        (ncb_p np, char * msg, u_long code);
1270 static  void    ncr_intr        (void *vnp);
1271 static  void    ncr_int_ma      (ncb_p np, u_char dstat);
1272 static  void    ncr_int_sir     (ncb_p np);
1273 static  void    ncr_int_sto     (ncb_p np);
1274 #if 0
1275 static  void    ncr_min_phys    (struct buf *bp);
1276 #endif
1277 static  void    ncr_poll        (struct cam_sim *sim);
1278 static  void    ncb_profile     (ncb_p np, nccb_p cp);
1279 static  void    ncr_script_copy_and_bind
1280                                 (ncb_p np, ncrcmd *src, ncrcmd *dst, int len);
1281 static  void    ncr_script_fill (struct script * scr, struct scripth *scrh);
1282 static  int     ncr_scatter     (struct dsb* phys, vm_offset_t vaddr,
1283                                  vm_size_t datalen);
1284 static  void    ncr_getsync     (ncb_p np, u_char sfac, u_char *fakp,
1285                                  u_char *scntl3p);
1286 static  void    ncr_setsync     (ncb_p np, nccb_p cp,u_char scntl3,u_char sxfer,
1287                                  u_char period);
1288 static  void    ncr_setwide     (ncb_p np, nccb_p cp, u_char wide, u_char ack);
1289 static  int     ncr_show_msg    (u_char * msg);
1290 static  int     ncr_snooptest   (ncb_p np);
1291 static  void    ncr_action      (struct cam_sim *sim, union ccb *ccb);
1292 static  void    ncr_timeout     (void *arg);
1293 static  void    ncr_wakeup      (ncb_p np, u_long code);
1294
1295 static  int     ncr_probe       (device_t dev);
1296 static  int     ncr_attach      (device_t dev);
1297
1298 #endif /* _KERNEL */
1299
1300 /*==========================================================
1301 **
1302 **
1303 **      Global static data.
1304 **
1305 **
1306 **==========================================================
1307 */
1308
1309
1310 /*
1311  * $FreeBSD: src/sys/pci/ncr.c,v 1.155.2.3 2001/03/05 13:09:10 obrien Exp $
1312  */
1313 static const u_long     ncr_version = NCR_VERSION       * 11
1314         + (u_long) sizeof (struct ncb)  *  7
1315         + (u_long) sizeof (struct nccb) *  5
1316         + (u_long) sizeof (struct lcb)  *  3
1317         + (u_long) sizeof (struct tcb)  *  2;
1318
1319 #ifdef _KERNEL
1320
1321 static int ncr_debug = SCSI_NCR_DEBUG;
1322 SYSCTL_INT(_debug, OID_AUTO, ncr_debug, CTLFLAG_RW, &ncr_debug, 0, "");
1323
1324 static int ncr_cache; /* to be aligned _NOT_ static */
1325
1326 /*==========================================================
1327 **
1328 **
1329 **      Global static data:     auto configure
1330 **
1331 **
1332 **==========================================================
1333 */
1334
1335 #define NCR_810_ID      (0x00011000ul)
1336 #define NCR_815_ID      (0x00041000ul)
1337 #define NCR_820_ID      (0x00021000ul)
1338 #define NCR_825_ID      (0x00031000ul)
1339 #define NCR_860_ID      (0x00061000ul)
1340 #define NCR_875_ID      (0x000f1000ul)
1341 #define NCR_875_ID2     (0x008f1000ul)
1342 #define NCR_885_ID      (0x000d1000ul)
1343 #define NCR_895_ID      (0x000c1000ul)
1344 #define NCR_896_ID      (0x000b1000ul)
1345 #define NCR_895A_ID     (0x00121000ul)
1346 #define NCR_1510D_ID    (0x000a1000ul)
1347
1348
1349 static char *ncr_name (ncb_p np)
1350 {
1351         static char name[10];
1352         snprintf(name, sizeof(name), "ncr%d", np->unit);
1353         return (name);
1354 }
1355
1356 /*==========================================================
1357 **
1358 **
1359 **      Scripts for NCR-Processor.
1360 **
1361 **      Use ncr_script_bind for binding to physical addresses.
1362 **
1363 **
1364 **==========================================================
1365 **
1366 **      NADDR generates a reference to a field of the controller data.
1367 **      PADDR generates a reference to another part of the script.
1368 **      RADDR generates a reference to a script processor register.
1369 **      FADDR generates a reference to a script processor register
1370 **              with offset.
1371 **
1372 **----------------------------------------------------------
1373 */
1374
1375 #define RELOC_SOFTC     0x40000000
1376 #define RELOC_LABEL     0x50000000
1377 #define RELOC_REGISTER  0x60000000
1378 #define RELOC_KVAR      0x70000000
1379 #define RELOC_LABELH    0x80000000
1380 #define RELOC_MASK      0xf0000000
1381
1382 #define NADDR(label)    (RELOC_SOFTC | offsetof(struct ncb, label))
1383 #define PADDR(label)    (RELOC_LABEL | offsetof(struct script, label))
1384 #define PADDRH(label)   (RELOC_LABELH | offsetof(struct scripth, label))
1385 #define RADDR(label)    (RELOC_REGISTER | REG(label))
1386 #define FADDR(label,ofs)(RELOC_REGISTER | ((REG(label))+(ofs)))
1387 #define KVAR(which)     (RELOC_KVAR | (which))
1388
1389 #define KVAR_SECOND                     (0)
1390 #define KVAR_TICKS                      (1)
1391 #define KVAR_NCR_CACHE                  (2)
1392
1393 #define SCRIPT_KVAR_FIRST               (0)
1394 #define SCRIPT_KVAR_LAST                (3)
1395
1396 /*
1397  * Kernel variables referenced in the scripts.
1398  * THESE MUST ALL BE ALIGNED TO A 4-BYTE BOUNDARY.
1399  */
1400 static void *script_kvars[] =
1401         { &time_second, &ticks, &ncr_cache };
1402
1403 static  struct script script0 = {
1404 /*--------------------------< START >-----------------------*/ {
1405         /*
1406         **      Claim to be still alive ...
1407         */
1408         SCR_COPY (sizeof (((struct ncb *)0)->heartbeat)),
1409                 KVAR (KVAR_SECOND),
1410                 NADDR (heartbeat),
1411         /*
1412         **      Make data structure address invalid.
1413         **      clear SIGP.
1414         */
1415         SCR_LOAD_REG (dsa, 0xff),
1416                 0,
1417         SCR_FROM_REG (ctest2),
1418                 0,
1419 }/*-------------------------< START0 >----------------------*/,{
1420         /*
1421         **      Hook for interrupted GetConditionCode.
1422         **      Will be patched to ... IFTRUE by
1423         **      the interrupt handler.
1424         */
1425         SCR_INT ^ IFFALSE (0),
1426                 SIR_SENSE_RESTART,
1427
1428 }/*-------------------------< START1 >----------------------*/,{
1429         /*
1430         **      Hook for stalled start queue.
1431         **      Will be patched to IFTRUE by the interrupt handler.
1432         */
1433         SCR_INT ^ IFFALSE (0),
1434                 SIR_STALL_RESTART,
1435         /*
1436         **      Then jump to a certain point in tryloop.
1437         **      Due to the lack of indirect addressing the code
1438         **      is self modifying here.
1439         */
1440         SCR_JUMP,
1441 }/*-------------------------< STARTPOS >--------------------*/,{
1442                 PADDRH(tryloop),
1443
1444 }/*-------------------------< TRYSEL >----------------------*/,{
1445         /*
1446         **      Now:
1447         **      DSA: Address of a Data Structure
1448         **      or   Address of the IDLE-Label.
1449         **
1450         **      TEMP:   Address of a script, which tries to
1451         **              start the NEXT entry.
1452         **
1453         **      Save the TEMP register into the SCRATCHA register.
1454         **      Then copy the DSA to TEMP and RETURN.
1455         **      This is kind of an indirect jump.
1456         **      (The script processor has NO stack, so the
1457         **      CALL is actually a jump and link, and the
1458         **      RETURN is an indirect jump.)
1459         **
1460         **      If the slot was empty, DSA contains the address
1461         **      of the IDLE part of this script. The processor
1462         **      jumps to IDLE and waits for a reselect.
1463         **      It will wake up and try the same slot again
1464         **      after the SIGP bit becomes set by the host.
1465         **
1466         **      If the slot was not empty, DSA contains
1467         **      the address of the phys-part of a nccb.
1468         **      The processor jumps to this address.
1469         **      phys starts with head,
1470         **      head starts with launch,
1471         **      so actually the processor jumps to
1472         **      the lauch part.
1473         **      If the entry is scheduled for execution,
1474         **      then launch contains a jump to SELECT.
1475         **      If it's not scheduled, it contains a jump to IDLE.
1476         */
1477         SCR_COPY (4),
1478                 RADDR (temp),
1479                 RADDR (scratcha),
1480         SCR_COPY (4),
1481                 RADDR (dsa),
1482                 RADDR (temp),
1483         SCR_RETURN,
1484                 0
1485
1486 }/*-------------------------< SKIP >------------------------*/,{
1487         /*
1488         **      This entry has been canceled.
1489         **      Next time use the next slot.
1490         */
1491         SCR_COPY (4),
1492                 RADDR (scratcha),
1493                 PADDR (startpos),
1494         /*
1495         **      patch the launch field.
1496         **      should look like an idle process.
1497         */
1498         SCR_COPY_F (4),
1499                 RADDR (dsa),
1500                 PADDR (skip2),
1501         SCR_COPY (8),
1502                 PADDR (idle),
1503 }/*-------------------------< SKIP2 >-----------------------*/,{
1504                 0,
1505         SCR_JUMP,
1506                 PADDR(start),
1507 }/*-------------------------< IDLE >------------------------*/,{
1508         /*
1509         **      Nothing to do?
1510         **      Wait for reselect.
1511         */
1512         SCR_JUMP,
1513                 PADDR(reselect),
1514
1515 }/*-------------------------< SELECT >----------------------*/,{
1516         /*
1517         **      DSA     contains the address of a scheduled
1518         **              data structure.
1519         **
1520         **      SCRATCHA contains the address of the script,
1521         **              which starts the next entry.
1522         **
1523         **      Set Initiator mode.
1524         **
1525         **      (Target mode is left as an exercise for the reader)
1526         */
1527
1528         SCR_CLR (SCR_TRG),
1529                 0,
1530         SCR_LOAD_REG (HS_REG, 0xff),
1531                 0,
1532
1533         /*
1534         **      And try to select this target.
1535         */
1536         SCR_SEL_TBL_ATN ^ offsetof (struct dsb, select),
1537                 PADDR (reselect),
1538
1539         /*
1540         **      Now there are 4 possibilities:
1541         **
1542         **      (1) The ncr looses arbitration.
1543         **      This is ok, because it will try again,
1544         **      when the bus becomes idle.
1545         **      (But beware of the timeout function!)
1546         **
1547         **      (2) The ncr is reselected.
1548         **      Then the script processor takes the jump
1549         **      to the RESELECT label.
1550         **
1551         **      (3) The ncr completes the selection.
1552         **      Then it will execute the next statement.
1553         **
1554         **      (4) There is a selection timeout.
1555         **      Then the ncr should interrupt the host and stop.
1556         **      Unfortunately, it seems to continue execution
1557         **      of the script. But it will fail with an
1558         **      IID-interrupt on the next WHEN.
1559         */
1560
1561         SCR_JUMPR ^ IFTRUE (WHEN (SCR_MSG_IN)),
1562                 0,
1563
1564         /*
1565         **      Send the IDENTIFY and SIMPLE_TAG messages
1566         **      (and the MSG_EXT_SDTR message)
1567         */
1568         SCR_MOVE_TBL ^ SCR_MSG_OUT,
1569                 offsetof (struct dsb, smsg),
1570 #ifdef undef /* XXX better fail than try to deal with this ... */
1571         SCR_JUMPR ^ IFTRUE (WHEN (SCR_MSG_OUT)),
1572                 -16,
1573 #endif
1574         SCR_CLR (SCR_ATN),
1575                 0,
1576         SCR_COPY (1),
1577                 RADDR (sfbr),
1578                 NADDR (lastmsg),
1579         /*
1580         **      Selection complete.
1581         **      Next time use the next slot.
1582         */
1583         SCR_COPY (4),
1584                 RADDR (scratcha),
1585                 PADDR (startpos),
1586 }/*-------------------------< PREPARE >----------------------*/,{
1587         /*
1588         **      The ncr doesn't have an indirect load
1589         **      or store command. So we have to
1590         **      copy part of the control block to a
1591         **      fixed place, where we can access it.
1592         **
1593         **      We patch the address part of a
1594         **      COPY command with the DSA-register.
1595         */
1596         SCR_COPY_F (4),
1597                 RADDR (dsa),
1598                 PADDR (loadpos),
1599         /*
1600         **      then we do the actual copy.
1601         */
1602         SCR_COPY (sizeof (struct head)),
1603         /*
1604         **      continued after the next label ...
1605         */
1606
1607 }/*-------------------------< LOADPOS >---------------------*/,{
1608                 0,
1609                 NADDR (header),
1610         /*
1611         **      Mark this nccb as not scheduled.
1612         */
1613         SCR_COPY (8),
1614                 PADDR (idle),
1615                 NADDR (header.launch),
1616         /*
1617         **      Set a time stamp for this selection
1618         */
1619         SCR_COPY (sizeof (ticks)),
1620                 KVAR (KVAR_TICKS),
1621                 NADDR (header.stamp.select),
1622         /*
1623         **      load the savep (saved pointer) into
1624         **      the TEMP register (actual pointer)
1625         */
1626         SCR_COPY (4),
1627                 NADDR (header.savep),
1628                 RADDR (temp),
1629         /*
1630         **      Initialize the status registers
1631         */
1632         SCR_COPY (4),
1633                 NADDR (header.status),
1634                 RADDR (scr0),
1635
1636 }/*-------------------------< PREPARE2 >---------------------*/,{
1637         /*
1638         **      Load the synchronous mode register
1639         */
1640         SCR_COPY (1),
1641                 NADDR (sync_st),
1642                 RADDR (sxfer),
1643         /*
1644         **      Load the wide mode and timing register
1645         */
1646         SCR_COPY (1),
1647                 NADDR (wide_st),
1648                 RADDR (scntl3),
1649         /*
1650         **      Initialize the msgout buffer with a NOOP message.
1651         */
1652         SCR_LOAD_REG (scratcha, MSG_NOOP),
1653                 0,
1654         SCR_COPY (1),
1655                 RADDR (scratcha),
1656                 NADDR (msgout),
1657         SCR_COPY (1),
1658                 RADDR (scratcha),
1659                 NADDR (msgin),
1660         /*
1661         **      Message in phase ?
1662         */
1663         SCR_JUMP ^ IFFALSE (WHEN (SCR_MSG_IN)),
1664                 PADDR (dispatch),
1665         /*
1666         **      Extended or reject message ?
1667         */
1668         SCR_FROM_REG (sbdl),
1669                 0,
1670         SCR_JUMP ^ IFTRUE (DATA (MSG_EXTENDED)),
1671                 PADDR (msg_in),
1672         SCR_JUMP ^ IFTRUE (DATA (MSG_MESSAGE_REJECT)),
1673                 PADDRH (msg_reject),
1674         /*
1675         **      normal processing
1676         */
1677         SCR_JUMP,
1678                 PADDR (dispatch),
1679 }/*-------------------------< SETMSG >----------------------*/,{
1680         SCR_COPY (1),
1681                 RADDR (scratcha),
1682                 NADDR (msgout),
1683         SCR_SET (SCR_ATN),
1684                 0,
1685 }/*-------------------------< CLRACK >----------------------*/,{
1686         /*
1687         **      Terminate possible pending message phase.
1688         */
1689         SCR_CLR (SCR_ACK),
1690                 0,
1691
1692 }/*-----------------------< DISPATCH >----------------------*/,{
1693         SCR_FROM_REG (HS_REG),
1694                 0,
1695         SCR_INT ^ IFTRUE (DATA (HS_NEGOTIATE)),
1696                 SIR_NEGO_FAILED,
1697         /*
1698         **      remove bogus output signals
1699         */
1700         SCR_REG_REG (socl, SCR_AND, CACK|CATN),
1701                 0,
1702         SCR_RETURN ^ IFTRUE (WHEN (SCR_DATA_OUT)),
1703                 0,
1704         SCR_RETURN ^ IFTRUE (IF (SCR_DATA_IN)),
1705                 0,
1706         SCR_JUMP ^ IFTRUE (IF (SCR_MSG_OUT)),
1707                 PADDR (msg_out),
1708         SCR_JUMP ^ IFTRUE (IF (SCR_MSG_IN)),
1709                 PADDR (msg_in),
1710         SCR_JUMP ^ IFTRUE (IF (SCR_COMMAND)),
1711                 PADDR (command),
1712         SCR_JUMP ^ IFTRUE (IF (SCR_STATUS)),
1713                 PADDR (status),
1714         /*
1715         **      Discard one illegal phase byte, if required.
1716         */
1717         SCR_LOAD_REG (scratcha, XE_BAD_PHASE),
1718                 0,
1719         SCR_COPY (1),
1720                 RADDR (scratcha),
1721                 NADDR (xerr_st),
1722         SCR_JUMPR ^ IFFALSE (IF (SCR_ILG_OUT)),
1723                 8,
1724         SCR_MOVE_ABS (1) ^ SCR_ILG_OUT,
1725                 NADDR (scratch),
1726         SCR_JUMPR ^ IFFALSE (IF (SCR_ILG_IN)),
1727                 8,
1728         SCR_MOVE_ABS (1) ^ SCR_ILG_IN,
1729                 NADDR (scratch),
1730         SCR_JUMP,
1731                 PADDR (dispatch),
1732
1733 }/*-------------------------< NO_DATA >--------------------*/,{
1734         /*
1735         **      The target wants to tranfer too much data
1736         **      or in the wrong direction.
1737         **      Remember that in extended error.
1738         */
1739         SCR_LOAD_REG (scratcha, XE_EXTRA_DATA),
1740                 0,
1741         SCR_COPY (1),
1742                 RADDR (scratcha),
1743                 NADDR (xerr_st),
1744         /*
1745         **      Discard one data byte, if required.
1746         */
1747         SCR_JUMPR ^ IFFALSE (WHEN (SCR_DATA_OUT)),
1748                 8,
1749         SCR_MOVE_ABS (1) ^ SCR_DATA_OUT,
1750                 NADDR (scratch),
1751         SCR_JUMPR ^ IFFALSE (IF (SCR_DATA_IN)),
1752                 8,
1753         SCR_MOVE_ABS (1) ^ SCR_DATA_IN,
1754                 NADDR (scratch),
1755         /*
1756         **      .. and repeat as required.
1757         */
1758         SCR_CALL,
1759                 PADDR (dispatch),
1760         SCR_JUMP,
1761                 PADDR (no_data),
1762 }/*-------------------------< CHECKATN >--------------------*/,{
1763         /*
1764         **      If AAP (bit 1 of scntl0 register) is set
1765         **      and a parity error is detected,
1766         **      the script processor asserts ATN.
1767         **
1768         **      The target should switch to a MSG_OUT phase
1769         **      to get the message.
1770         */
1771         SCR_FROM_REG (socl),
1772                 0,
1773         SCR_JUMP ^ IFFALSE (MASK (CATN, CATN)),
1774                 PADDR (dispatch),
1775         /*
1776         **      count it
1777         */
1778         SCR_REG_REG (PS_REG, SCR_ADD, 1),
1779                 0,
1780         /*
1781         **      Prepare a MSG_INITIATOR_DET_ERR message
1782         **      (initiator detected error).
1783         **      The target should retry the transfer.
1784         */
1785         SCR_LOAD_REG (scratcha, MSG_INITIATOR_DET_ERR),
1786                 0,
1787         SCR_JUMP,
1788                 PADDR (setmsg),
1789
1790 }/*-------------------------< COMMAND >--------------------*/,{
1791         /*
1792         **      If this is not a GETCC transfer ...
1793         */
1794         SCR_FROM_REG (SS_REG),
1795                 0,
1796 /*<<<*/ SCR_JUMPR ^ IFTRUE (DATA (SCSI_STATUS_CHECK_COND)),
1797                 28,
1798         /*
1799         **      ... set a timestamp ...
1800         */
1801         SCR_COPY (sizeof (ticks)),
1802                 KVAR (KVAR_TICKS),
1803                 NADDR (header.stamp.command),
1804         /*
1805         **      ... and send the command
1806         */
1807         SCR_MOVE_TBL ^ SCR_COMMAND,
1808                 offsetof (struct dsb, cmd),
1809         SCR_JUMP,
1810                 PADDR (dispatch),
1811         /*
1812         **      Send the GETCC command
1813         */
1814 /*>>>*/ SCR_MOVE_TBL ^ SCR_COMMAND,
1815                 offsetof (struct dsb, scmd),
1816         SCR_JUMP,
1817                 PADDR (dispatch),
1818
1819 }/*-------------------------< STATUS >--------------------*/,{
1820         /*
1821         **      set the timestamp.
1822         */
1823         SCR_COPY (sizeof (ticks)),
1824                 KVAR (KVAR_TICKS),
1825                 NADDR (header.stamp.status),
1826         /*
1827         **      If this is a GETCC transfer,
1828         */
1829         SCR_FROM_REG (SS_REG),
1830                 0,
1831 /*<<<*/ SCR_JUMPR ^ IFFALSE (DATA (SCSI_STATUS_CHECK_COND)),
1832                 40,
1833         /*
1834         **      get the status
1835         */
1836         SCR_MOVE_ABS (1) ^ SCR_STATUS,
1837                 NADDR (scratch),
1838         /*
1839         **      Save status to scsi_status.
1840         **      Mark as complete.
1841         **      And wait for disconnect.
1842         */
1843         SCR_TO_REG (SS_REG),
1844                 0,
1845         SCR_REG_REG (SS_REG, SCR_OR, SCSI_STATUS_SENSE),
1846                 0,
1847         SCR_LOAD_REG (HS_REG, HS_COMPLETE),
1848                 0,
1849         SCR_JUMP,
1850                 PADDR (checkatn),
1851         /*
1852         **      If it was no GETCC transfer,
1853         **      save the status to scsi_status.
1854         */
1855 /*>>>*/ SCR_MOVE_ABS (1) ^ SCR_STATUS,
1856                 NADDR (scratch),
1857         SCR_TO_REG (SS_REG),
1858                 0,
1859         /*
1860         **      if it was no check condition ...
1861         */
1862         SCR_JUMP ^ IFTRUE (DATA (SCSI_STATUS_CHECK_COND)),
1863                 PADDR (checkatn),
1864         /*
1865         **      ... mark as complete.
1866         */
1867         SCR_LOAD_REG (HS_REG, HS_COMPLETE),
1868                 0,
1869         SCR_JUMP,
1870                 PADDR (checkatn),
1871
1872 }/*-------------------------< MSG_IN >--------------------*/,{
1873         /*
1874         **      Get the first byte of the message
1875         **      and save it to SCRATCHA.
1876         **
1877         **      The script processor doesn't negate the
1878         **      ACK signal after this transfer.
1879         */
1880         SCR_MOVE_ABS (1) ^ SCR_MSG_IN,
1881                 NADDR (msgin[0]),
1882         /*
1883         **      Check for message parity error.
1884         */
1885         SCR_TO_REG (scratcha),
1886                 0,
1887         SCR_FROM_REG (socl),
1888                 0,
1889         SCR_JUMP ^ IFTRUE (MASK (CATN, CATN)),
1890                 PADDRH (msg_parity),
1891         SCR_FROM_REG (scratcha),
1892                 0,
1893         /*
1894         **      Parity was ok, handle this message.
1895         */
1896         SCR_JUMP ^ IFTRUE (DATA (MSG_CMDCOMPLETE)),
1897                 PADDR (complete),
1898         SCR_JUMP ^ IFTRUE (DATA (MSG_SAVEDATAPOINTER)),
1899                 PADDR (save_dp),
1900         SCR_JUMP ^ IFTRUE (DATA (MSG_RESTOREPOINTERS)),
1901                 PADDR (restore_dp),
1902         SCR_JUMP ^ IFTRUE (DATA (MSG_DISCONNECT)),
1903                 PADDR (disconnect),
1904         SCR_JUMP ^ IFTRUE (DATA (MSG_EXTENDED)),
1905                 PADDRH (msg_extended),
1906         SCR_JUMP ^ IFTRUE (DATA (MSG_NOOP)),
1907                 PADDR (clrack),
1908         SCR_JUMP ^ IFTRUE (DATA (MSG_MESSAGE_REJECT)),
1909                 PADDRH (msg_reject),
1910         SCR_JUMP ^ IFTRUE (DATA (MSG_IGN_WIDE_RESIDUE)),
1911                 PADDRH (msg_ign_residue),
1912         /*
1913         **      Rest of the messages left as
1914         **      an exercise ...
1915         **
1916         **      Unimplemented messages:
1917         **      fall through to MSG_BAD.
1918         */
1919 }/*-------------------------< MSG_BAD >------------------*/,{
1920         /*
1921         **      unimplemented message - reject it.
1922         */
1923         SCR_INT,
1924                 SIR_REJECT_SENT,
1925         SCR_LOAD_REG (scratcha, MSG_MESSAGE_REJECT),
1926                 0,
1927         SCR_JUMP,
1928                 PADDR (setmsg),
1929
1930 }/*-------------------------< COMPLETE >-----------------*/,{
1931         /*
1932         **      Complete message.
1933         **
1934         **      If it's not the get condition code,
1935         **      copy TEMP register to LASTP in header.
1936         */
1937         SCR_FROM_REG (SS_REG),
1938                 0,
1939 /*<<<*/ SCR_JUMPR ^ IFTRUE (MASK (SCSI_STATUS_SENSE, SCSI_STATUS_SENSE)),
1940                 12,
1941         SCR_COPY (4),
1942                 RADDR (temp),
1943                 NADDR (header.lastp),
1944 /*>>>*/ /*
1945         **      When we terminate the cycle by clearing ACK,
1946         **      the target may disconnect immediately.
1947         **
1948         **      We don't want to be told of an
1949         **      "unexpected disconnect",
1950         **      so we disable this feature.
1951         */
1952         SCR_REG_REG (scntl2, SCR_AND, 0x7f),
1953                 0,
1954         /*
1955         **      Terminate cycle ...
1956         */
1957         SCR_CLR (SCR_ACK|SCR_ATN),
1958                 0,
1959         /*
1960         **      ... and wait for the disconnect.
1961         */
1962         SCR_WAIT_DISC,
1963                 0,
1964 }/*-------------------------< CLEANUP >-------------------*/,{
1965         /*
1966         **      dsa:    Pointer to nccb
1967         **            or xxxxxxFF (no nccb)
1968         **
1969         **      HS_REG:   Host-Status (<>0!)
1970         */
1971         SCR_FROM_REG (dsa),
1972                 0,
1973         SCR_JUMP ^ IFTRUE (DATA (0xff)),
1974                 PADDR (signal),
1975         /*
1976         **      dsa is valid.
1977         **      save the status registers
1978         */
1979         SCR_COPY (4),
1980                 RADDR (scr0),
1981                 NADDR (header.status),
1982         /*
1983         **      and copy back the header to the nccb.
1984         */
1985         SCR_COPY_F (4),
1986                 RADDR (dsa),
1987                 PADDR (cleanup0),
1988         SCR_COPY (sizeof (struct head)),
1989                 NADDR (header),
1990 }/*-------------------------< CLEANUP0 >--------------------*/,{
1991                 0,
1992
1993         /*
1994         **      If command resulted in "check condition"
1995         **      status and is not yet completed,
1996         **      try to get the condition code.
1997         */
1998         SCR_FROM_REG (HS_REG),
1999                 0,
2000 /*<<<*/ SCR_JUMPR ^ IFFALSE (MASK (0, HS_DONEMASK)),
2001                 16,
2002         SCR_FROM_REG (SS_REG),
2003                 0,
2004         SCR_JUMP ^ IFTRUE (DATA (SCSI_STATUS_CHECK_COND)),
2005                 PADDRH(getcc2),
2006 }/*-------------------------< SIGNAL >----------------------*/,{
2007         /*
2008         **      if status = queue full,
2009         **      reinsert in startqueue and stall queue.
2010         */
2011 /*>>>*/ SCR_FROM_REG (SS_REG),
2012                 0,
2013         SCR_INT ^ IFTRUE (DATA (SCSI_STATUS_QUEUE_FULL)),
2014                 SIR_STALL_QUEUE,
2015         /*
2016         **      And make the DSA register invalid.
2017         */
2018         SCR_LOAD_REG (dsa, 0xff), /* invalid */
2019                 0,
2020         /*
2021         **      if job completed ...
2022         */
2023         SCR_FROM_REG (HS_REG),
2024                 0,
2025         /*
2026         **      ... signal completion to the host
2027         */
2028         SCR_INT_FLY ^ IFFALSE (MASK (0, HS_DONEMASK)),
2029                 0,
2030         /*
2031         **      Auf zu neuen Schandtaten!
2032         */
2033         SCR_JUMP,
2034                 PADDR(start),
2035
2036 }/*-------------------------< SAVE_DP >------------------*/,{
2037         /*
2038         **      SAVE_DP message:
2039         **      Copy TEMP register to SAVEP in header.
2040         */
2041         SCR_COPY (4),
2042                 RADDR (temp),
2043                 NADDR (header.savep),
2044         SCR_JUMP,
2045                 PADDR (clrack),
2046 }/*-------------------------< RESTORE_DP >---------------*/,{
2047         /*
2048         **      RESTORE_DP message:
2049         **      Copy SAVEP in header to TEMP register.
2050         */
2051         SCR_COPY (4),
2052                 NADDR (header.savep),
2053                 RADDR (temp),
2054         SCR_JUMP,
2055                 PADDR (clrack),
2056
2057 }/*-------------------------< DISCONNECT >---------------*/,{
2058         /*
2059         **      If QUIRK_AUTOSAVE is set,
2060         **      do an "save pointer" operation.
2061         */
2062         SCR_FROM_REG (QU_REG),
2063                 0,
2064 /*<<<*/ SCR_JUMPR ^ IFFALSE (MASK (QUIRK_AUTOSAVE, QUIRK_AUTOSAVE)),
2065                 12,
2066         /*
2067         **      like SAVE_DP message:
2068         **      Copy TEMP register to SAVEP in header.
2069         */
2070         SCR_COPY (4),
2071                 RADDR (temp),
2072                 NADDR (header.savep),
2073 /*>>>*/ /*
2074         **      Check if temp==savep or temp==goalp:
2075         **      if not, log a missing save pointer message.
2076         **      In fact, it's a comparison mod 256.
2077         **
2078         **      Hmmm, I hadn't thought that I would be urged to
2079         **      write this kind of ugly self modifying code.
2080         **
2081         **      It's unbelievable, but the ncr53c8xx isn't able
2082         **      to subtract one register from another.
2083         */
2084         SCR_FROM_REG (temp),
2085                 0,
2086         /*
2087         **      You are not expected to understand this ..
2088         **
2089         **      CAUTION: only little endian architectures supported! XXX
2090         */
2091         SCR_COPY_F (1),
2092                 NADDR (header.savep),
2093                 PADDR (disconnect0),
2094 }/*-------------------------< DISCONNECT0 >--------------*/,{
2095 /*<<<*/ SCR_JUMPR ^ IFTRUE (DATA (1)),
2096                 20,
2097         /*
2098         **      neither this
2099         */
2100         SCR_COPY_F (1),
2101                 NADDR (header.goalp),
2102                 PADDR (disconnect1),
2103 }/*-------------------------< DISCONNECT1 >--------------*/,{
2104         SCR_INT ^ IFFALSE (DATA (1)),
2105                 SIR_MISSING_SAVE,
2106 /*>>>*/
2107
2108         /*
2109         **      DISCONNECTing  ...
2110         **
2111         **      disable the "unexpected disconnect" feature,
2112         **      and remove the ACK signal.
2113         */
2114         SCR_REG_REG (scntl2, SCR_AND, 0x7f),
2115                 0,
2116         SCR_CLR (SCR_ACK|SCR_ATN),
2117                 0,
2118         /*
2119         **      Wait for the disconnect.
2120         */
2121         SCR_WAIT_DISC,
2122                 0,
2123         /*
2124         **      Profiling:
2125         **      Set a time stamp,
2126         **      and count the disconnects.
2127         */
2128         SCR_COPY (sizeof (ticks)),
2129                 KVAR (KVAR_TICKS),
2130                 NADDR (header.stamp.disconnect),
2131         SCR_COPY (4),
2132                 NADDR (disc_phys),
2133                 RADDR (temp),
2134         SCR_REG_REG (temp, SCR_ADD, 0x01),
2135                 0,
2136         SCR_COPY (4),
2137                 RADDR (temp),
2138                 NADDR (disc_phys),
2139         /*
2140         **      Status is: DISCONNECTED.
2141         */
2142         SCR_LOAD_REG (HS_REG, HS_DISCONNECT),
2143                 0,
2144         SCR_JUMP,
2145                 PADDR (cleanup),
2146
2147 }/*-------------------------< MSG_OUT >-------------------*/,{
2148         /*
2149         **      The target requests a message.
2150         */
2151         SCR_MOVE_ABS (1) ^ SCR_MSG_OUT,
2152                 NADDR (msgout),
2153         SCR_COPY (1),
2154                 RADDR (sfbr),
2155                 NADDR (lastmsg),
2156         /*
2157         **      If it was no ABORT message ...
2158         */
2159         SCR_JUMP ^ IFTRUE (DATA (MSG_ABORT)),
2160                 PADDRH (msg_out_abort),
2161         /*
2162         **      ... wait for the next phase
2163         **      if it's a message out, send it again, ...
2164         */
2165         SCR_JUMP ^ IFTRUE (WHEN (SCR_MSG_OUT)),
2166                 PADDR (msg_out),
2167 }/*-------------------------< MSG_OUT_DONE >--------------*/,{
2168         /*
2169         **      ... else clear the message ...
2170         */
2171         SCR_LOAD_REG (scratcha, MSG_NOOP),
2172                 0,
2173         SCR_COPY (4),
2174                 RADDR (scratcha),
2175                 NADDR (msgout),
2176         /*
2177         **      ... and process the next phase
2178         */
2179         SCR_JUMP,
2180                 PADDR (dispatch),
2181
2182 }/*------------------------< BADGETCC >---------------------*/,{
2183         /*
2184         **      If SIGP was set, clear it and try again.
2185         */
2186         SCR_FROM_REG (ctest2),
2187                 0,
2188         SCR_JUMP ^ IFTRUE (MASK (CSIGP,CSIGP)),
2189                 PADDRH (getcc2),
2190         SCR_INT,
2191                 SIR_SENSE_FAILED,
2192 }/*-------------------------< RESELECT >--------------------*/,{
2193         /*
2194         **      This NOP will be patched with LED OFF
2195         **      SCR_REG_REG (gpreg, SCR_OR, 0x01)
2196         */
2197         SCR_NO_OP,
2198                 0,
2199
2200         /*
2201         **      make the DSA invalid.
2202         */
2203         SCR_LOAD_REG (dsa, 0xff),
2204                 0,
2205         SCR_CLR (SCR_TRG),
2206                 0,
2207         /*
2208         **      Sleep waiting for a reselection.
2209         **      If SIGP is set, special treatment.
2210         **
2211         **      Zu allem bereit ..
2212         */
2213         SCR_WAIT_RESEL,
2214                 PADDR(reselect2),
2215 }/*-------------------------< RESELECT1 >--------------------*/,{
2216         /*
2217         **      This NOP will be patched with LED ON
2218         **      SCR_REG_REG (gpreg, SCR_AND, 0xfe)
2219         */
2220         SCR_NO_OP,
2221                 0,
2222         /*
2223         **      ... zu nichts zu gebrauchen ?
2224         **
2225         **      load the target id into the SFBR
2226         **      and jump to the control block.
2227         **
2228         **      Look at the declarations of
2229         **      - struct ncb
2230         **      - struct tcb
2231         **      - struct lcb
2232         **      - struct nccb
2233         **      to understand what's going on.
2234         */
2235         SCR_REG_SFBR (ssid, SCR_AND, 0x8F),
2236                 0,
2237         SCR_TO_REG (sdid),
2238                 0,
2239         SCR_JUMP,
2240                 NADDR (jump_tcb),
2241 }/*-------------------------< RESELECT2 >-------------------*/,{
2242         /*
2243         **      This NOP will be patched with LED ON
2244         **      SCR_REG_REG (gpreg, SCR_AND, 0xfe)
2245         */
2246         SCR_NO_OP,
2247                 0,
2248         /*
2249         **      If it's not connected :(
2250         **      -> interrupted by SIGP bit.
2251         **      Jump to start.
2252         */
2253         SCR_FROM_REG (ctest2),
2254                 0,
2255         SCR_JUMP ^ IFTRUE (MASK (CSIGP,CSIGP)),
2256                 PADDR (start),
2257         SCR_JUMP,
2258                 PADDR (reselect),
2259
2260 }/*-------------------------< RESEL_TMP >-------------------*/,{
2261         /*
2262         **      The return address in TEMP
2263         **      is in fact the data structure address,
2264         **      so copy it to the DSA register.
2265         */
2266         SCR_COPY (4),
2267                 RADDR (temp),
2268                 RADDR (dsa),
2269         SCR_JUMP,
2270                 PADDR (prepare),
2271
2272 }/*-------------------------< RESEL_LUN >-------------------*/,{
2273         /*
2274         **      come back to this point
2275         **      to get an IDENTIFY message
2276         **      Wait for a msg_in phase.
2277         */
2278 /*<<<*/ SCR_JUMPR ^ IFFALSE (WHEN (SCR_MSG_IN)),
2279                 48,
2280         /*
2281         **      message phase
2282         **      It's not a sony, it's a trick:
2283         **      read the data without acknowledging it.
2284         */
2285         SCR_FROM_REG (sbdl),
2286                 0,
2287 /*<<<*/ SCR_JUMPR ^ IFFALSE (MASK (MSG_IDENTIFYFLAG, 0x98)),
2288                 32,
2289         /*
2290         **      It WAS an Identify message.
2291         **      get it and ack it!
2292         */
2293         SCR_MOVE_ABS (1) ^ SCR_MSG_IN,
2294                 NADDR (msgin),
2295         SCR_CLR (SCR_ACK),
2296                 0,
2297         /*
2298         **      Mask out the lun.
2299         */
2300         SCR_REG_REG (sfbr, SCR_AND, 0x07),
2301                 0,
2302         SCR_RETURN,
2303                 0,
2304         /*
2305         **      No message phase or no IDENTIFY message:
2306         **      return 0.
2307         */
2308 /*>>>*/ SCR_LOAD_SFBR (0),
2309                 0,
2310         SCR_RETURN,
2311                 0,
2312
2313 }/*-------------------------< RESEL_TAG >-------------------*/,{
2314         /*
2315         **      come back to this point
2316         **      to get a SIMPLE_TAG message
2317         **      Wait for a MSG_IN phase.
2318         */
2319 /*<<<*/ SCR_JUMPR ^ IFFALSE (WHEN (SCR_MSG_IN)),
2320                 64,
2321         /*
2322         **      message phase
2323         **      It's a trick - read the data
2324         **      without acknowledging it.
2325         */
2326         SCR_FROM_REG (sbdl),
2327                 0,
2328 /*<<<*/ SCR_JUMPR ^ IFFALSE (DATA (MSG_SIMPLE_Q_TAG)),
2329                 48,
2330         /*
2331         **      It WAS a SIMPLE_TAG message.
2332         **      get it and ack it!
2333         */
2334         SCR_MOVE_ABS (1) ^ SCR_MSG_IN,
2335                 NADDR (msgin),
2336         SCR_CLR (SCR_ACK),
2337                 0,
2338         /*
2339         **      Wait for the second byte (the tag)
2340         */
2341 /*<<<*/ SCR_JUMPR ^ IFFALSE (WHEN (SCR_MSG_IN)),
2342                 24,
2343         /*
2344         **      Get it and ack it!
2345         */
2346         SCR_MOVE_ABS (1) ^ SCR_MSG_IN,
2347                 NADDR (msgin),
2348         SCR_CLR (SCR_ACK|SCR_CARRY),
2349                 0,
2350         SCR_RETURN,
2351                 0,
2352         /*
2353         **      No message phase or no SIMPLE_TAG message
2354         **      or no second byte: return 0.
2355         */
2356 /*>>>*/ SCR_LOAD_SFBR (0),
2357                 0,
2358         SCR_SET (SCR_CARRY),
2359                 0,
2360         SCR_RETURN,
2361                 0,
2362
2363 }/*-------------------------< DATA_IN >--------------------*/,{
2364 /*
2365 **      Because the size depends on the
2366 **      #define MAX_SCATTER parameter,
2367 **      it is filled in at runtime.
2368 **
2369 **      SCR_JUMP ^ IFFALSE (WHEN (SCR_DATA_IN)),
2370 **              PADDR (no_data),
2371 **      SCR_COPY (sizeof (ticks)),
2372 **              KVAR (KVAR_TICKS),
2373 **              NADDR (header.stamp.data),
2374 **      SCR_MOVE_TBL ^ SCR_DATA_IN,
2375 **              offsetof (struct dsb, data[ 0]),
2376 **
2377 **  ##===========< i=1; i<MAX_SCATTER >=========
2378 **  ||  SCR_CALL ^ IFFALSE (WHEN (SCR_DATA_IN)),
2379 **  ||          PADDR (checkatn),
2380 **  ||  SCR_MOVE_TBL ^ SCR_DATA_IN,
2381 **  ||          offsetof (struct dsb, data[ i]),
2382 **  ##==========================================
2383 **
2384 **      SCR_CALL,
2385 **              PADDR (checkatn),
2386 **      SCR_JUMP,
2387 **              PADDR (no_data),
2388 */
2389 0
2390 }/*-------------------------< DATA_OUT >-------------------*/,{
2391 /*
2392 **      Because the size depends on the
2393 **      #define MAX_SCATTER parameter,
2394 **      it is filled in at runtime.
2395 **
2396 **      SCR_JUMP ^ IFFALSE (WHEN (SCR_DATA_OUT)),
2397 **              PADDR (no_data),
2398 **      SCR_COPY (sizeof (ticks)),
2399 **              KVAR (KVAR_TICKS),
2400 **              NADDR (header.stamp.data),
2401 **      SCR_MOVE_TBL ^ SCR_DATA_OUT,
2402 **              offsetof (struct dsb, data[ 0]),
2403 **
2404 **  ##===========< i=1; i<MAX_SCATTER >=========
2405 **  ||  SCR_CALL ^ IFFALSE (WHEN (SCR_DATA_OUT)),
2406 **  ||          PADDR (dispatch),
2407 **  ||  SCR_MOVE_TBL ^ SCR_DATA_OUT,
2408 **  ||          offsetof (struct dsb, data[ i]),
2409 **  ##==========================================
2410 **
2411 **      SCR_CALL,
2412 **              PADDR (dispatch),
2413 **      SCR_JUMP,
2414 **              PADDR (no_data),
2415 **
2416 **---------------------------------------------------------
2417 */
2418 (u_long)0
2419
2420 }/*--------------------------------------------------------*/
2421 };
2422
2423
2424 static  struct scripth scripth0 = {
2425 /*-------------------------< TRYLOOP >---------------------*/{
2426 /*
2427 **      Load an entry of the start queue into dsa
2428 **      and try to start it by jumping to TRYSEL.
2429 **
2430 **      Because the size depends on the
2431 **      #define MAX_START parameter, it is filled
2432 **      in at runtime.
2433 **
2434 **-----------------------------------------------------------
2435 **
2436 **  ##===========< I=0; i<MAX_START >===========
2437 **  ||  SCR_COPY (4),
2438 **  ||          NADDR (squeue[i]),
2439 **  ||          RADDR (dsa),
2440 **  ||  SCR_CALL,
2441 **  ||          PADDR (trysel),
2442 **  ##==========================================
2443 **
2444 **      SCR_JUMP,
2445 **              PADDRH(tryloop),
2446 **
2447 **-----------------------------------------------------------
2448 */
2449 0
2450 }/*-------------------------< MSG_PARITY >---------------*/,{
2451         /*
2452         **      count it
2453         */
2454         SCR_REG_REG (PS_REG, SCR_ADD, 0x01),
2455                 0,
2456         /*
2457         **      send a "message parity error" message.
2458         */
2459         SCR_LOAD_REG (scratcha, MSG_PARITY_ERROR),
2460                 0,
2461         SCR_JUMP,
2462                 PADDR (setmsg),
2463 }/*-------------------------< MSG_MESSAGE_REJECT >---------------*/,{
2464         /*
2465         **      If a negotiation was in progress,
2466         **      negotiation failed.
2467         */
2468         SCR_FROM_REG (HS_REG),
2469                 0,
2470         SCR_INT ^ IFTRUE (DATA (HS_NEGOTIATE)),
2471                 SIR_NEGO_FAILED,
2472         /*
2473         **      else make host log this message
2474         */
2475         SCR_INT ^ IFFALSE (DATA (HS_NEGOTIATE)),
2476                 SIR_REJECT_RECEIVED,
2477         SCR_JUMP,
2478                 PADDR (clrack),
2479
2480 }/*-------------------------< MSG_IGN_RESIDUE >----------*/,{
2481         /*
2482         **      Terminate cycle
2483         */
2484         SCR_CLR (SCR_ACK),
2485                 0,
2486         SCR_JUMP ^ IFFALSE (WHEN (SCR_MSG_IN)),
2487                 PADDR (dispatch),
2488         /*
2489         **      get residue size.
2490         */
2491         SCR_MOVE_ABS (1) ^ SCR_MSG_IN,
2492                 NADDR (msgin[1]),
2493         /*
2494         **      Check for message parity error.
2495         */
2496         SCR_TO_REG (scratcha),
2497                 0,
2498         SCR_FROM_REG (socl),
2499                 0,
2500         SCR_JUMP ^ IFTRUE (MASK (CATN, CATN)),
2501                 PADDRH (msg_parity),
2502         SCR_FROM_REG (scratcha),
2503                 0,
2504         /*
2505         **      Size is 0 .. ignore message.
2506         */
2507         SCR_JUMP ^ IFTRUE (DATA (0)),
2508                 PADDR (clrack),
2509         /*
2510         **      Size is not 1 .. have to interrupt.
2511         */
2512 /*<<<*/ SCR_JUMPR ^ IFFALSE (DATA (1)),
2513                 40,
2514         /*
2515         **      Check for residue byte in swide register
2516         */
2517         SCR_FROM_REG (scntl2),
2518                 0,
2519 /*<<<*/ SCR_JUMPR ^ IFFALSE (MASK (WSR, WSR)),
2520                 16,
2521         /*
2522         **      There IS data in the swide register.
2523         **      Discard it.
2524         */
2525         SCR_REG_REG (scntl2, SCR_OR, WSR),
2526                 0,
2527         SCR_JUMP,
2528                 PADDR (clrack),
2529         /*
2530         **      Load again the size to the sfbr register.
2531         */
2532 /*>>>*/ SCR_FROM_REG (scratcha),
2533                 0,
2534 /*>>>*/ SCR_INT,
2535                 SIR_IGN_RESIDUE,
2536         SCR_JUMP,
2537                 PADDR (clrack),
2538
2539 }/*-------------------------< MSG_EXTENDED >-------------*/,{
2540         /*
2541         **      Terminate cycle
2542         */
2543         SCR_CLR (SCR_ACK),
2544                 0,
2545         SCR_JUMP ^ IFFALSE (WHEN (SCR_MSG_IN)),
2546                 PADDR (dispatch),
2547         /*
2548         **      get length.
2549         */
2550         SCR_MOVE_ABS (1) ^ SCR_MSG_IN,
2551                 NADDR (msgin[1]),
2552         /*
2553         **      Check for message parity error.
2554         */
2555         SCR_TO_REG (scratcha),
2556                 0,
2557         SCR_FROM_REG (socl),
2558                 0,
2559         SCR_JUMP ^ IFTRUE (MASK (CATN, CATN)),
2560                 PADDRH (msg_parity),
2561         SCR_FROM_REG (scratcha),
2562                 0,
2563         /*
2564         */
2565         SCR_JUMP ^ IFTRUE (DATA (3)),
2566                 PADDRH (msg_ext_3),
2567         SCR_JUMP ^ IFFALSE (DATA (2)),
2568                 PADDR (msg_bad),
2569 }/*-------------------------< MSG_EXT_2 >----------------*/,{
2570         SCR_CLR (SCR_ACK),
2571                 0,
2572         SCR_JUMP ^ IFFALSE (WHEN (SCR_MSG_IN)),
2573                 PADDR (dispatch),
2574         /*
2575         **      get extended message code.
2576         */
2577         SCR_MOVE_ABS (1) ^ SCR_MSG_IN,
2578                 NADDR (msgin[2]),
2579         /*
2580         **      Check for message parity error.
2581         */
2582         SCR_TO_REG (scratcha),
2583                 0,
2584         SCR_FROM_REG (socl),
2585                 0,
2586         SCR_JUMP ^ IFTRUE (MASK (CATN, CATN)),
2587                 PADDRH (msg_parity),
2588         SCR_FROM_REG (scratcha),
2589                 0,
2590         SCR_JUMP ^ IFTRUE (DATA (MSG_EXT_WDTR)),
2591                 PADDRH (msg_wdtr),
2592         /*
2593         **      unknown extended message
2594         */
2595         SCR_JUMP,
2596                 PADDR (msg_bad)
2597 }/*-------------------------< MSG_WDTR >-----------------*/,{
2598         SCR_CLR (SCR_ACK),
2599                 0,
2600         SCR_JUMP ^ IFFALSE (WHEN (SCR_MSG_IN)),
2601                 PADDR (dispatch),
2602         /*
2603         **      get data bus width
2604         */
2605         SCR_MOVE_ABS (1) ^ SCR_MSG_IN,
2606                 NADDR (msgin[3]),
2607         SCR_FROM_REG (socl),
2608                 0,
2609         SCR_JUMP ^ IFTRUE (MASK (CATN, CATN)),
2610                 PADDRH (msg_parity),
2611         /*
2612         **      let the host do the real work.
2613         */
2614         SCR_INT,
2615                 SIR_NEGO_WIDE,
2616         /*
2617         **      let the target fetch our answer.
2618         */
2619         SCR_SET (SCR_ATN),
2620                 0,
2621         SCR_CLR (SCR_ACK),
2622                 0,
2623
2624         SCR_INT ^ IFFALSE (WHEN (SCR_MSG_OUT)),
2625                 SIR_NEGO_PROTO,
2626         /*
2627         **      Send the MSG_EXT_WDTR
2628         */
2629         SCR_MOVE_ABS (4) ^ SCR_MSG_OUT,
2630                 NADDR (msgout),
2631         SCR_CLR (SCR_ATN),
2632                 0,
2633         SCR_COPY (1),
2634                 RADDR (sfbr),
2635                 NADDR (lastmsg),
2636         SCR_JUMP,
2637                 PADDR (msg_out_done),
2638
2639 }/*-------------------------< MSG_EXT_3 >----------------*/,{
2640         SCR_CLR (SCR_ACK),
2641                 0,
2642         SCR_JUMP ^ IFFALSE (WHEN (SCR_MSG_IN)),
2643                 PADDR (dispatch),
2644         /*
2645         **      get extended message code.
2646         */
2647         SCR_MOVE_ABS (1) ^ SCR_MSG_IN,
2648                 NADDR (msgin[2]),
2649         /*
2650         **      Check for message parity error.
2651         */
2652         SCR_TO_REG (scratcha),
2653                 0,
2654         SCR_FROM_REG (socl),
2655                 0,
2656         SCR_JUMP ^ IFTRUE (MASK (CATN, CATN)),
2657                 PADDRH (msg_parity),
2658         SCR_FROM_REG (scratcha),
2659                 0,
2660         SCR_JUMP ^ IFTRUE (DATA (MSG_EXT_SDTR)),
2661                 PADDRH (msg_sdtr),
2662         /*
2663         **      unknown extended message
2664         */
2665         SCR_JUMP,
2666                 PADDR (msg_bad)
2667
2668 }/*-------------------------< MSG_SDTR >-----------------*/,{
2669         SCR_CLR (SCR_ACK),
2670                 0,
2671         SCR_JUMP ^ IFFALSE (WHEN (SCR_MSG_IN)),
2672                 PADDR (dispatch),
2673         /*
2674         **      get period and offset
2675         */
2676         SCR_MOVE_ABS (2) ^ SCR_MSG_IN,
2677                 NADDR (msgin[3]),
2678         SCR_FROM_REG (socl),
2679                 0,
2680         SCR_JUMP ^ IFTRUE (MASK (CATN, CATN)),
2681                 PADDRH (msg_parity),
2682         /*
2683         **      let the host do the real work.
2684         */
2685         SCR_INT,
2686                 SIR_NEGO_SYNC,
2687         /*
2688         **      let the target fetch our answer.
2689         */
2690         SCR_SET (SCR_ATN),
2691                 0,
2692         SCR_CLR (SCR_ACK),
2693                 0,
2694
2695         SCR_INT ^ IFFALSE (WHEN (SCR_MSG_OUT)),
2696                 SIR_NEGO_PROTO,
2697         /*
2698         **      Send the MSG_EXT_SDTR
2699         */
2700         SCR_MOVE_ABS (5) ^ SCR_MSG_OUT,
2701                 NADDR (msgout),
2702         SCR_CLR (SCR_ATN),
2703                 0,
2704         SCR_COPY (1),
2705                 RADDR (sfbr),
2706                 NADDR (lastmsg),
2707         SCR_JUMP,
2708                 PADDR (msg_out_done),
2709
2710 }/*-------------------------< MSG_OUT_ABORT >-------------*/,{
2711         /*
2712         **      After ABORT message,
2713         **
2714         **      expect an immediate disconnect, ...
2715         */
2716         SCR_REG_REG (scntl2, SCR_AND, 0x7f),
2717                 0,
2718         SCR_CLR (SCR_ACK|SCR_ATN),
2719                 0,
2720         SCR_WAIT_DISC,
2721                 0,
2722         /*
2723         **      ... and set the status to "ABORTED"
2724         */
2725         SCR_LOAD_REG (HS_REG, HS_ABORTED),
2726                 0,
2727         SCR_JUMP,
2728                 PADDR (cleanup),
2729
2730 }/*-------------------------< GETCC >-----------------------*/,{
2731         /*
2732         **      The ncr doesn't have an indirect load
2733         **      or store command. So we have to
2734         **      copy part of the control block to a
2735         **      fixed place, where we can modify it.
2736         **
2737         **      We patch the address part of a COPY command
2738         **      with the address of the dsa register ...
2739         */
2740         SCR_COPY_F (4),
2741                 RADDR (dsa),
2742                 PADDRH (getcc1),
2743         /*
2744         **      ... then we do the actual copy.
2745         */
2746         SCR_COPY (sizeof (struct head)),
2747 }/*-------------------------< GETCC1 >----------------------*/,{
2748                 0,
2749                 NADDR (header),
2750         /*
2751         **      Initialize the status registers
2752         */
2753         SCR_COPY (4),
2754                 NADDR (header.status),
2755                 RADDR (scr0),
2756 }/*-------------------------< GETCC2 >----------------------*/,{
2757         /*
2758         **      Get the condition code from a target.
2759         **
2760         **      DSA points to a data structure.
2761         **      Set TEMP to the script location
2762         **      that receives the condition code.
2763         **
2764         **      Because there is no script command
2765         **      to load a longword into a register,
2766         **      we use a CALL command.
2767         */
2768 /*<<<*/ SCR_CALLR,
2769                 24,
2770         /*
2771         **      Get the condition code.
2772         */
2773         SCR_MOVE_TBL ^ SCR_DATA_IN,
2774                 offsetof (struct dsb, sense),
2775         /*
2776         **      No data phase may follow!
2777         */
2778         SCR_CALL,
2779                 PADDR (checkatn),
2780         SCR_JUMP,
2781                 PADDR (no_data),
2782 /*>>>*/
2783
2784         /*
2785         **      The CALL jumps to this point.
2786         **      Prepare for a RESTORE_POINTER message.
2787         **      Save the TEMP register into the saved pointer.
2788         */
2789         SCR_COPY (4),
2790                 RADDR (temp),
2791                 NADDR (header.savep),
2792         /*
2793         **      Load scratcha, because in case of a selection timeout,
2794         **      the host will expect a new value for startpos in
2795         **      the scratcha register.
2796         */
2797         SCR_COPY (4),
2798                 PADDR (startpos),
2799                 RADDR (scratcha),
2800 #ifdef NCR_GETCC_WITHMSG
2801         /*
2802         **      If QUIRK_NOMSG is set, select without ATN.
2803         **      and don't send a message.
2804         */
2805         SCR_FROM_REG (QU_REG),
2806                 0,
2807         SCR_JUMP ^ IFTRUE (MASK (QUIRK_NOMSG, QUIRK_NOMSG)),
2808                 PADDRH(getcc3),
2809         /*
2810         **      Then try to connect to the target.
2811         **      If we are reselected, special treatment
2812         **      of the current job is required before
2813         **      accepting the reselection.
2814         */
2815         SCR_SEL_TBL_ATN ^ offsetof (struct dsb, select),
2816                 PADDR(badgetcc),
2817         /*
2818         **      Send the IDENTIFY message.
2819         **      In case of short transfer, remove ATN.
2820         */
2821         SCR_MOVE_TBL ^ SCR_MSG_OUT,
2822                 offsetof (struct dsb, smsg2),
2823         SCR_CLR (SCR_ATN),
2824                 0,
2825         /*
2826         **      save the first byte of the message.
2827         */
2828         SCR_COPY (1),
2829                 RADDR (sfbr),
2830                 NADDR (lastmsg),
2831         SCR_JUMP,
2832                 PADDR (prepare2),
2833
2834 #endif
2835 }/*-------------------------< GETCC3 >----------------------*/,{
2836         /*
2837         **      Try to connect to the target.
2838         **      If we are reselected, special treatment
2839         **      of the current job is required before
2840         **      accepting the reselection.
2841         **
2842         **      Silly target won't accept a message.
2843         **      Select without ATN.
2844         */
2845         SCR_SEL_TBL ^ offsetof (struct dsb, select),
2846                 PADDR(badgetcc),
2847         /*
2848         **      Force error if selection timeout
2849         */
2850         SCR_JUMPR ^ IFTRUE (WHEN (SCR_MSG_IN)),
2851                 0,
2852         /*
2853         **      don't negotiate.
2854         */
2855         SCR_JUMP,
2856                 PADDR (prepare2),
2857 }/*-------------------------< ABORTTAG >-------------------*/,{
2858         /*
2859         **      Abort a bad reselection.
2860         **      Set the message to ABORT vs. ABORT_TAG
2861         */
2862         SCR_LOAD_REG (scratcha, MSG_ABORT_TAG),
2863                 0,
2864         SCR_JUMPR ^ IFFALSE (CARRYSET),
2865                 8,
2866 }/*-------------------------< ABORT >----------------------*/,{
2867         SCR_LOAD_REG (scratcha, MSG_ABORT),
2868                 0,
2869         SCR_COPY (1),
2870                 RADDR (scratcha),
2871                 NADDR (msgout),
2872         SCR_SET (SCR_ATN),
2873                 0,
2874         SCR_CLR (SCR_ACK),
2875                 0,
2876         /*
2877         **      and send it.
2878         **      we expect an immediate disconnect
2879         */
2880         SCR_REG_REG (scntl2, SCR_AND, 0x7f),
2881                 0,
2882         SCR_MOVE_ABS (1) ^ SCR_MSG_OUT,
2883                 NADDR (msgout),
2884         SCR_COPY (1),
2885                 RADDR (sfbr),
2886                 NADDR (lastmsg),
2887         SCR_CLR (SCR_ACK|SCR_ATN),
2888                 0,
2889         SCR_WAIT_DISC,
2890                 0,
2891         SCR_JUMP,
2892                 PADDR (start),
2893 }/*-------------------------< SNOOPTEST >-------------------*/,{
2894         /*
2895         **      Read the variable.
2896         */
2897         SCR_COPY (4),
2898                 KVAR (KVAR_NCR_CACHE),
2899                 RADDR (scratcha),
2900         /*
2901         **      Write the variable.
2902         */
2903         SCR_COPY (4),
2904                 RADDR (temp),
2905                 KVAR (KVAR_NCR_CACHE),
2906         /*
2907         **      Read back the variable.
2908         */
2909         SCR_COPY (4),
2910                 KVAR (KVAR_NCR_CACHE),
2911                 RADDR (temp),
2912 }/*-------------------------< SNOOPEND >-------------------*/,{
2913         /*
2914         **      And stop.
2915         */
2916         SCR_INT,
2917                 99,
2918 }/*--------------------------------------------------------*/
2919 };
2920
2921
2922 /*==========================================================
2923 **
2924 **
2925 **      Fill in #define dependent parts of the script
2926 **
2927 **
2928 **==========================================================
2929 */
2930
2931 void ncr_script_fill (struct script * scr, struct scripth * scrh)
2932 {
2933         int     i;
2934         ncrcmd  *p;
2935
2936         p = scrh->tryloop;
2937         for (i=0; i<MAX_START; i++) {
2938                 *p++ =SCR_COPY (4);
2939                 *p++ =NADDR (squeue[i]);
2940                 *p++ =RADDR (dsa);
2941                 *p++ =SCR_CALL;
2942                 *p++ =PADDR (trysel);
2943         };
2944         *p++ =SCR_JUMP;
2945         *p++ =PADDRH(tryloop);
2946
2947         assert ((char *)p == (char *)&scrh->tryloop + sizeof (scrh->tryloop));
2948
2949         p = scr->data_in;
2950
2951         *p++ =SCR_JUMP ^ IFFALSE (WHEN (SCR_DATA_IN));
2952         *p++ =PADDR (no_data);
2953         *p++ =SCR_COPY (sizeof (ticks));
2954         *p++ =(ncrcmd) KVAR (KVAR_TICKS);
2955         *p++ =NADDR (header.stamp.data);
2956         *p++ =SCR_MOVE_TBL ^ SCR_DATA_IN;
2957         *p++ =offsetof (struct dsb, data[ 0]);
2958
2959         for (i=1; i<MAX_SCATTER; i++) {
2960                 *p++ =SCR_CALL ^ IFFALSE (WHEN (SCR_DATA_IN));
2961                 *p++ =PADDR (checkatn);
2962                 *p++ =SCR_MOVE_TBL ^ SCR_DATA_IN;
2963                 *p++ =offsetof (struct dsb, data[i]);
2964         };
2965
2966         *p++ =SCR_CALL;
2967         *p++ =PADDR (checkatn);
2968         *p++ =SCR_JUMP;
2969         *p++ =PADDR (no_data);
2970
2971         assert ((char *)p == (char *)&scr->data_in + sizeof (scr->data_in));
2972
2973         p = scr->data_out;
2974
2975         *p++ =SCR_JUMP ^ IFFALSE (WHEN (SCR_DATA_OUT));
2976         *p++ =PADDR (no_data);
2977         *p++ =SCR_COPY (sizeof (ticks));
2978         *p++ =(ncrcmd) KVAR (KVAR_TICKS);
2979         *p++ =NADDR (header.stamp.data);
2980         *p++ =SCR_MOVE_TBL ^ SCR_DATA_OUT;
2981         *p++ =offsetof (struct dsb, data[ 0]);
2982
2983         for (i=1; i<MAX_SCATTER; i++) {
2984                 *p++ =SCR_CALL ^ IFFALSE (WHEN (SCR_DATA_OUT));
2985                 *p++ =PADDR (dispatch);
2986                 *p++ =SCR_MOVE_TBL ^ SCR_DATA_OUT;
2987                 *p++ =offsetof (struct dsb, data[i]);
2988         };
2989
2990         *p++ =SCR_CALL;
2991         *p++ =PADDR (dispatch);
2992         *p++ =SCR_JUMP;
2993         *p++ =PADDR (no_data);
2994
2995         assert ((char *)p == (char *)&scr->data_out + sizeof (scr->data_out));
2996 }
2997
2998 /*==========================================================
2999 **
3000 **
3001 **      Copy and rebind a script.
3002 **
3003 **
3004 **==========================================================
3005 */
3006
3007 static void ncr_script_copy_and_bind (ncb_p np, ncrcmd *src, ncrcmd *dst, int len)
3008 {
3009         ncrcmd  opcode, new, old, tmp1, tmp2;
3010         ncrcmd  *start, *end;
3011         int relocs, offset;
3012
3013         start = src;
3014         end = src + len/4;
3015         offset = 0;
3016
3017         while (src < end) {
3018
3019                 opcode = *src++;
3020                 WRITESCRIPT_OFF(dst, offset, opcode);
3021                 offset += 4;
3022
3023                 /*
3024                 **      If we forget to change the length
3025                 **      in struct script, a field will be
3026                 **      padded with 0. This is an illegal
3027                 **      command.
3028                 */
3029
3030                 if (opcode == 0) {
3031                         printf ("%s: ERROR0 IN SCRIPT at %d.\n",
3032                                 ncr_name(np), (int) (src-start-1));
3033                         DELAY (1000000);
3034                 };
3035
3036                 if (DEBUG_FLAGS & DEBUG_SCRIPT)
3037                         printf ("%p:  <%x>\n",
3038                                 (src-1), (unsigned)opcode);
3039
3040                 /*
3041                 **      We don't have to decode ALL commands
3042                 */
3043                 switch (opcode >> 28) {
3044
3045                 case 0xc:
3046                         /*
3047                         **      COPY has TWO arguments.
3048                         */
3049                         relocs = 2;
3050                         tmp1 = src[0];
3051                         if ((tmp1 & RELOC_MASK) == RELOC_KVAR)
3052                                 tmp1 = 0;
3053                         tmp2 = src[1];
3054                         if ((tmp2 & RELOC_MASK) == RELOC_KVAR)
3055                                 tmp2 = 0;
3056                         if ((tmp1 ^ tmp2) & 3) {
3057                                 printf ("%s: ERROR1 IN SCRIPT at %d.\n",
3058                                         ncr_name(np), (int) (src-start-1));
3059                                 DELAY (1000000);
3060                         }
3061                         /*
3062                         **      If PREFETCH feature not enabled, remove 
3063                         **      the NO FLUSH bit if present.
3064                         */
3065                         if ((opcode & SCR_NO_FLUSH) && !(np->features&FE_PFEN))
3066                                 WRITESCRIPT_OFF(dst, offset - 4,
3067                                     (opcode & ~SCR_NO_FLUSH));
3068                         break;
3069
3070                 case 0x0:
3071                         /*
3072                         **      MOVE (absolute address)
3073                         */
3074                         relocs = 1;
3075                         break;
3076
3077                 case 0x8:
3078                         /*
3079                         **      JUMP / CALL
3080                         **      dont't relocate if relative :-)
3081                         */
3082                         if (opcode & 0x00800000)
3083                                 relocs = 0;
3084                         else
3085                                 relocs = 1;
3086                         break;
3087
3088                 case 0x4:
3089                 case 0x5:
3090                 case 0x6:
3091                 case 0x7:
3092                         relocs = 1;
3093                         break;
3094
3095                 default:
3096                         relocs = 0;
3097                         break;
3098                 };
3099
3100                 if (relocs) {
3101                         while (relocs--) {
3102                                 old = *src++;
3103
3104                                 switch (old & RELOC_MASK) {
3105                                 case RELOC_REGISTER:
3106                                         new = (old & ~RELOC_MASK) + rman_get_start(np->reg_res);
3107                                         break;
3108                                 case RELOC_LABEL:
3109                                         new = (old & ~RELOC_MASK) + np->p_script;
3110                                         break;
3111                                 case RELOC_LABELH:
3112                                         new = (old & ~RELOC_MASK) + np->p_scripth;
3113                                         break;
3114                                 case RELOC_SOFTC:
3115                                         new = (old & ~RELOC_MASK) + vtophys(np);
3116                                         break;
3117                                 case RELOC_KVAR:
3118                                         if (((old & ~RELOC_MASK) <
3119                                              SCRIPT_KVAR_FIRST) ||
3120                                             ((old & ~RELOC_MASK) >
3121                                              SCRIPT_KVAR_LAST))
3122                                                 panic("ncr KVAR out of range");
3123                                         new = vtophys(script_kvars[old &
3124                                             ~RELOC_MASK]);
3125                                         break;
3126                                 case 0:
3127                                         /* Don't relocate a 0 address. */
3128                                         if (old == 0) {
3129                                                 new = old;
3130                                                 break;
3131                                         }
3132                                         /* fall through */
3133                                 default:
3134                                         panic("ncr_script_copy_and_bind: weird relocation %x @ %d\n", old, (int)(src - start));
3135                                         break;
3136                                 }
3137
3138                                 WRITESCRIPT_OFF(dst, offset, new);
3139                                 offset += 4;
3140                         }
3141                 } else {
3142                         WRITESCRIPT_OFF(dst, offset, *src++);
3143                         offset += 4;
3144                 }
3145
3146         };
3147 }
3148
3149 /*==========================================================
3150 **
3151 **
3152 **      Auto configuration.
3153 **
3154 **
3155 **==========================================================
3156 */
3157
3158 #if 0
3159 /*----------------------------------------------------------
3160 **
3161 **      Reduce the transfer length to the max value
3162 **      we can transfer safely.
3163 **
3164 **      Reading a block greater then MAX_SIZE from the
3165 **      raw (character) device exercises a memory leak
3166 **      in the vm subsystem. This is common to ALL devices.
3167 **      We have submitted a description of this bug to
3168 **      <FreeBSD-bugs@freefall.cdrom.com>.
3169 **      It should be fixed in the current release.
3170 **
3171 **----------------------------------------------------------
3172 */
3173
3174 void ncr_min_phys (struct  buf *bp)
3175 {
3176         if ((unsigned long)bp->b_bcount > MAX_SIZE) bp->b_bcount = MAX_SIZE;
3177 }
3178
3179 #endif
3180
3181 #if 0
3182 /*----------------------------------------------------------
3183 **
3184 **      Maximal number of outstanding requests per target.
3185 **
3186 **----------------------------------------------------------
3187 */
3188
3189 u_int32_t ncr_info (int unit)
3190 {
3191         return (1);   /* may be changed later */
3192 }
3193
3194 #endif
3195
3196 /*----------------------------------------------------------
3197 **
3198 **      NCR chip devices table and chip look up function.
3199 **      Features bit are defined in ncrreg.h. Is it the 
3200 **      right place?
3201 **
3202 **----------------------------------------------------------
3203 */
3204 typedef struct {
3205         unsigned long   device_id;
3206         unsigned short  minrevid;
3207         char           *name;
3208         unsigned char   maxburst;
3209         unsigned char   maxoffs;
3210         unsigned char   clock_divn;
3211         unsigned int    features;
3212 } ncr_chip;
3213
3214 static ncr_chip ncr_chip_table[] = {
3215  {NCR_810_ID, 0x00,     "ncr 53c810 fast10 scsi",               4,  8, 4,
3216  FE_ERL}
3217  ,
3218  {NCR_810_ID, 0x10,     "ncr 53c810a fast10 scsi",              4,  8, 4,
3219  FE_ERL|FE_LDSTR|FE_PFEN|FE_BOF}
3220  ,
3221  {NCR_815_ID, 0x00,     "ncr 53c815 fast10 scsi",               4,  8, 4,
3222  FE_ERL|FE_BOF}
3223  ,
3224  {NCR_820_ID, 0x00,     "ncr 53c820 fast10 wide scsi",          4,  8, 4,
3225  FE_WIDE|FE_ERL}
3226  ,
3227  {NCR_825_ID, 0x00,     "ncr 53c825 fast10 wide scsi",          4,  8, 4,
3228  FE_WIDE|FE_ERL|FE_BOF}
3229  ,
3230  {NCR_825_ID, 0x10,     "ncr 53c825a fast10 wide scsi",         7,  8, 4,
3231  FE_WIDE|FE_CACHE_SET|FE_DFS|FE_LDSTR|FE_PFEN|FE_RAM}
3232  ,
3233  {NCR_860_ID, 0x00,     "ncr 53c860 fast20 scsi",               4,  8, 5,
3234  FE_ULTRA|FE_CLK80|FE_CACHE_SET|FE_LDSTR|FE_PFEN}
3235  ,
3236  {NCR_875_ID, 0x00,     "ncr 53c875 fast20 wide scsi",          7, 16, 5,
3237  FE_WIDE|FE_ULTRA|FE_CLK80|FE_CACHE_SET|FE_DFS|FE_LDSTR|FE_PFEN|FE_RAM}
3238  ,
3239  {NCR_875_ID, 0x02,     "ncr 53c875 fast20 wide scsi",          7, 16, 5,
3240  FE_WIDE|FE_ULTRA|FE_DBLR|FE_CACHE_SET|FE_DFS|FE_LDSTR|FE_PFEN|FE_RAM}
3241  ,
3242  {NCR_875_ID2, 0x00,    "ncr 53c875j fast20 wide scsi",         7, 16, 5,
3243  FE_WIDE|FE_ULTRA|FE_DBLR|FE_CACHE_SET|FE_DFS|FE_LDSTR|FE_PFEN|FE_RAM}
3244  ,
3245  {NCR_885_ID, 0x00,     "ncr 53c885 fast20 wide scsi",          7, 16, 5,
3246  FE_WIDE|FE_ULTRA|FE_DBLR|FE_CACHE_SET|FE_DFS|FE_LDSTR|FE_PFEN|FE_RAM}
3247  ,
3248  {NCR_895_ID, 0x00,     "ncr 53c895 fast40 wide scsi",          7, 31, 7,
3249  FE_WIDE|FE_ULTRA2|FE_QUAD|FE_CACHE_SET|FE_DFS|FE_LDSTR|FE_PFEN|FE_RAM}
3250  ,
3251  {NCR_896_ID, 0x00,     "ncr 53c896 fast40 wide scsi",          7, 31, 7,
3252  FE_WIDE|FE_ULTRA2|FE_QUAD|FE_CACHE_SET|FE_DFS|FE_LDSTR|FE_PFEN|FE_RAM}
3253  ,
3254  {NCR_895A_ID, 0x00,    "ncr 53c895a fast40 wide scsi",         7, 31, 7,
3255  FE_WIDE|FE_ULTRA2|FE_QUAD|FE_CACHE_SET|FE_DFS|FE_LDSTR|FE_PFEN|FE_RAM}
3256  ,
3257  {NCR_1510D_ID, 0x00,   "ncr 53c1510d fast40 wide scsi",        7, 31, 7,
3258  FE_WIDE|FE_ULTRA2|FE_QUAD|FE_CACHE_SET|FE_DFS|FE_LDSTR|FE_PFEN|FE_RAM}
3259 };
3260
3261 static int ncr_chip_lookup(u_long device_id, u_char revision_id)
3262 {
3263         int i, found;
3264         
3265         found = -1;
3266         for (i = 0; i < sizeof(ncr_chip_table)/sizeof(ncr_chip_table[0]); i++) {
3267                 if (device_id   == ncr_chip_table[i].device_id &&
3268                     ncr_chip_table[i].minrevid <= revision_id) {
3269                         if (found < 0 || 
3270                             ncr_chip_table[found].minrevid 
3271                               < ncr_chip_table[i].minrevid) {
3272                                 found = i;
3273                         }
3274                 }
3275         }
3276         return found;
3277 }
3278
3279 /*----------------------------------------------------------
3280 **
3281 **      Probe the hostadapter.
3282 **
3283 **----------------------------------------------------------
3284 */
3285
3286
3287
3288 static  int ncr_probe (device_t dev)
3289 {
3290         int i;
3291
3292         i = ncr_chip_lookup(pci_get_devid(dev), pci_get_revid(dev));
3293         if (i >= 0) {
3294                 device_set_desc(dev, ncr_chip_table[i].name);
3295                 return (-1000); /* Allows to use both ncr and sym */
3296         }
3297
3298         return (ENXIO);
3299 }
3300
3301
3302
3303 /*==========================================================
3304 **
3305 **      NCR chip clock divisor table.
3306 **      Divisors are multiplied by 10,000,000 in order to make 
3307 **      calculations more simple.
3308 **
3309 **==========================================================
3310 */
3311
3312 #define _5M 5000000
3313 static u_long div_10M[] =
3314         {2*_5M, 3*_5M, 4*_5M, 6*_5M, 8*_5M, 12*_5M, 16*_5M};
3315
3316 /*===============================================================
3317 **
3318 **      NCR chips allow burst lengths of 2, 4, 8, 16, 32, 64, 128 
3319 **      transfers. 32,64,128 are only supported by 875 and 895 chips.
3320 **      We use log base 2 (burst length) as internal code, with 
3321 **      value 0 meaning "burst disabled".
3322 **
3323 **===============================================================
3324 */
3325
3326 /*
3327  *      Burst length from burst code.
3328  */
3329 #define burst_length(bc) (!(bc))? 0 : 1 << (bc)
3330
3331 /*
3332  *      Burst code from io register bits.
3333  */
3334 #define burst_code(dmode, ctest4, ctest5) \
3335         (ctest4) & 0x80? 0 : (((dmode) & 0xc0) >> 6) + ((ctest5) & 0x04) + 1
3336
3337 /*
3338  *      Set initial io register bits from burst code.
3339  */
3340 static void
3341 ncr_init_burst(ncb_p np, u_char bc)
3342 {
3343         np->rv_ctest4   &= ~0x80;
3344         np->rv_dmode    &= ~(0x3 << 6);
3345         np->rv_ctest5   &= ~0x4;
3346
3347         if (!bc) {
3348                 np->rv_ctest4   |= 0x80;
3349         }
3350         else {
3351                 --bc;
3352                 np->rv_dmode    |= ((bc & 0x3) << 6);
3353                 np->rv_ctest5   |= (bc & 0x4);
3354         }
3355 }
3356
3357 /*==========================================================
3358 **
3359 **
3360 **      Auto configuration:  attach and init a host adapter.
3361 **
3362 **
3363 **==========================================================
3364 */
3365
3366
3367 static int
3368 ncr_attach (device_t dev)
3369 {
3370         ncb_p np = (struct ncb*) device_get_softc(dev);
3371         u_char   rev = 0;
3372         u_long   period;
3373         int      i, rid;
3374         u_int8_t usrsync;
3375         u_int8_t usrwide;
3376         struct cam_devq *devq;
3377
3378         /*
3379         **      allocate and initialize structures.
3380         */
3381
3382         np->unit = device_get_unit(dev);
3383
3384         /*
3385         **      Try to map the controller chip to
3386         **      virtual and physical memory.
3387         */
3388
3389         np->reg_rid = 0x14;
3390         np->reg_res = bus_alloc_resource(dev, SYS_RES_MEMORY, &np->reg_rid,
3391                                          0, ~0, 1, RF_ACTIVE);
3392         if (!np->reg_res) {
3393                 device_printf(dev, "could not map memory\n");
3394                 return ENXIO;
3395         }
3396
3397         /*
3398         **      Make the controller's registers available.
3399         **      Now the INB INW INL OUTB OUTW OUTL macros
3400         **      can be used safely.
3401         */
3402
3403         np->bst = rman_get_bustag(np->reg_res);
3404         np->bsh = rman_get_bushandle(np->reg_res);
3405
3406
3407 #ifdef NCR_IOMAPPED
3408         /*
3409         **      Try to map the controller chip into iospace.
3410         */
3411
3412         if (!pci_map_port (config_id, 0x10, &np->port))
3413                 return;
3414 #endif
3415
3416
3417         /*
3418         **      Save some controller register default values
3419         */
3420
3421         np->rv_scntl3   = INB(nc_scntl3) & 0x77;
3422         np->rv_dmode    = INB(nc_dmode)  & 0xce;
3423         np->rv_dcntl    = INB(nc_dcntl)  & 0xa9;
3424         np->rv_ctest3   = INB(nc_ctest3) & 0x01;
3425         np->rv_ctest4   = INB(nc_ctest4) & 0x88;
3426         np->rv_ctest5   = INB(nc_ctest5) & 0x24;
3427         np->rv_gpcntl   = INB(nc_gpcntl);
3428         np->rv_stest2   = INB(nc_stest2) & 0x20;
3429
3430         if (bootverbose >= 2) {
3431                 printf ("\tBIOS values:  SCNTL3:%02x DMODE:%02x  DCNTL:%02x\n",
3432                         np->rv_scntl3, np->rv_dmode, np->rv_dcntl);
3433                 printf ("\t              CTEST3:%02x CTEST4:%02x CTEST5:%02x\n",
3434                         np->rv_ctest3, np->rv_ctest4, np->rv_ctest5);
3435         }
3436
3437         np->rv_dcntl  |= NOCOM;
3438
3439         /*
3440         **      Do chip dependent initialization.
3441         */
3442
3443         rev = pci_get_revid(dev);
3444
3445         /*
3446         **      Get chip features from chips table.
3447         */
3448         i = ncr_chip_lookup(pci_get_devid(dev), rev);
3449
3450         if (i >= 0) {
3451                 np->maxburst    = ncr_chip_table[i].maxburst;
3452                 np->maxoffs     = ncr_chip_table[i].maxoffs;
3453                 np->clock_divn  = ncr_chip_table[i].clock_divn;
3454                 np->features    = ncr_chip_table[i].features;
3455         } else {        /* Should'nt happen if probe() is ok */
3456                 np->maxburst    = 4;
3457                 np->maxoffs     = 8;
3458                 np->clock_divn  = 4;
3459                 np->features    = FE_ERL;
3460         }
3461
3462         np->maxwide     = np->features & FE_WIDE ? 1 : 0;
3463         np->clock_khz   = np->features & FE_CLK80 ? 80000 : 40000;
3464         if      (np->features & FE_QUAD)        np->multiplier = 4;
3465         else if (np->features & FE_DBLR)        np->multiplier = 2;
3466         else                                    np->multiplier = 1;
3467
3468         /*
3469         **      Get the frequency of the chip's clock.
3470         **      Find the right value for scntl3.
3471         */
3472         if (np->features & (FE_ULTRA|FE_ULTRA2))
3473                 ncr_getclock(np, np->multiplier);
3474
3475 #ifdef NCR_TEKRAM_EEPROM
3476         if (bootverbose) {
3477                 printf ("%s: Tekram EEPROM read %s\n",
3478                         ncr_name(np),
3479                         read_tekram_eeprom (np, NULL) ?
3480                         "succeeded" : "failed");
3481         }
3482 #endif /* NCR_TEKRAM_EEPROM */
3483
3484         /*
3485          *      If scntl3 != 0, we assume BIOS is present.
3486          */
3487         if (np->rv_scntl3)
3488                 np->features |= FE_BIOS;
3489
3490         /*
3491          * Divisor to be used for async (timer pre-scaler).
3492          */
3493         i = np->clock_divn - 1;
3494         while (i >= 0) {
3495                 --i;
3496                 if (10ul * SCSI_NCR_MIN_ASYNC * np->clock_khz > div_10M[i]) {
3497                         ++i;
3498                         break;
3499                 }
3500         }
3501         np->rv_scntl3 = i+1;
3502
3503         /*
3504          * Minimum synchronous period factor supported by the chip.
3505          * Btw, 'period' is in tenths of nanoseconds.
3506          */
3507
3508         period = (4 * div_10M[0] + np->clock_khz - 1) / np->clock_khz;
3509         if      (period <= 250)         np->minsync = 10;
3510         else if (period <= 303)         np->minsync = 11;
3511         else if (period <= 500)         np->minsync = 12;
3512         else                            np->minsync = (period + 40 - 1) / 40;
3513
3514         /*
3515          * Check against chip SCSI standard support (SCSI-2,ULTRA,ULTRA2).
3516          */
3517
3518         if      (np->minsync < 25 && !(np->features & (FE_ULTRA|FE_ULTRA2)))
3519                 np->minsync = 25;
3520         else if (np->minsync < 12 && !(np->features & FE_ULTRA2))
3521                 np->minsync = 12;
3522
3523         /*
3524          * Maximum synchronous period factor supported by the chip.
3525          */
3526
3527         period = (11 * div_10M[np->clock_divn - 1]) / (4 * np->clock_khz);
3528         np->maxsync = period > 2540 ? 254 : period / 10;
3529
3530         /*
3531          * Now, some features available with Symbios compatible boards.
3532          * LED support through GPIO0 and DIFF support.
3533          */
3534
3535 #ifdef  SCSI_NCR_SYMBIOS_COMPAT
3536         if (!(np->rv_gpcntl & 0x01))
3537                 np->features |= FE_LED0;
3538 #if 0   /* Not safe enough without NVRAM support or user settable option */
3539         if (!(INB(nc_gpreg) & 0x08))
3540                 np->features |= FE_DIFF;
3541 #endif
3542 #endif  /* SCSI_NCR_SYMBIOS_COMPAT */
3543
3544         /*
3545          * Prepare initial IO registers settings.
3546          * Trust BIOS only if we believe we have one and if we want to.
3547          */
3548 #ifdef  SCSI_NCR_TRUST_BIOS
3549         if (!(np->features & FE_BIOS)) {
3550 #else
3551         if (1) {
3552 #endif
3553                 np->rv_dmode = 0;
3554                 np->rv_dcntl = NOCOM;
3555                 np->rv_ctest3 = 0;
3556                 np->rv_ctest4 = MPEE;
3557                 np->rv_ctest5 = 0;
3558                 np->rv_stest2 = 0;
3559
3560                 if (np->features & FE_ERL)
3561                         np->rv_dmode    |= ERL;   /* Enable Read Line */
3562                 if (np->features & FE_BOF)
3563                         np->rv_dmode    |= BOF;   /* Burst Opcode Fetch */
3564                 if (np->features & FE_ERMP)
3565                         np->rv_dmode    |= ERMP;  /* Enable Read Multiple */
3566                 if (np->features & FE_CLSE)
3567                         np->rv_dcntl    |= CLSE;  /* Cache Line Size Enable */
3568                 if (np->features & FE_WRIE)
3569                         np->rv_ctest3   |= WRIE;  /* Write and Invalidate */
3570                 if (np->features & FE_PFEN)
3571                         np->rv_dcntl    |= PFEN;  /* Prefetch Enable */
3572                 if (np->features & FE_DFS)
3573                         np->rv_ctest5   |= DFS;   /* Dma Fifo Size */
3574                 if (np->features & FE_DIFF)     
3575                         np->rv_stest2   |= 0x20;  /* Differential mode */
3576                 ncr_init_burst(np, np->maxburst); /* Max dwords burst length */
3577         } else {
3578                 np->maxburst =
3579                         burst_code(np->rv_dmode, np->rv_ctest4, np->rv_ctest5);
3580         }
3581
3582         /*
3583         **      Get on-chip SRAM address, if supported
3584         */
3585         if ((np->features & FE_RAM) && sizeof(struct script) <= 4096) {
3586                 np->sram_rid = 0x18;
3587                 np->sram_res = bus_alloc_resource(dev, SYS_RES_MEMORY,
3588                                                   &np->sram_rid,
3589                                                   0, ~0, 1, RF_ACTIVE);
3590         }
3591
3592         /*
3593         **      Allocate structure for script relocation.
3594         */
3595         if (np->sram_res != NULL) {
3596                 np->script = NULL;
3597                 np->p_script = rman_get_start(np->sram_res);
3598                 np->bst2 = rman_get_bustag(np->sram_res);
3599                 np->bsh2 = rman_get_bushandle(np->sram_res);
3600         } else if (sizeof (struct script) > PAGE_SIZE) {
3601                 np->script  = (struct script*) vm_page_alloc_contig 
3602                         (round_page(sizeof (struct script)), 
3603                          0, 0xffffffff, PAGE_SIZE);
3604         } else {
3605                 np->script  = (struct script *)
3606                         malloc (sizeof (struct script), M_DEVBUF, M_WAITOK);
3607         }
3608
3609         /* XXX JGibbs - Use contigmalloc */
3610         if (sizeof (struct scripth) > PAGE_SIZE) {
3611                 np->scripth = (struct scripth*) vm_page_alloc_contig 
3612                         (round_page(sizeof (struct scripth)), 
3613                          0, 0xffffffff, PAGE_SIZE);
3614         } else 
3615                 {
3616                 np->scripth = (struct scripth *)
3617                         malloc (sizeof (struct scripth), M_DEVBUF, M_WAITOK);
3618         }
3619
3620 #ifdef SCSI_NCR_PCI_CONFIG_FIXUP
3621         /*
3622         **      If cache line size is enabled, check PCI config space and 
3623         **      try to fix it up if necessary.
3624         */
3625 #ifdef PCIR_CACHELNSZ   /* To be sure that new PCI stuff is present */
3626         {
3627                 u_char cachelnsz = pci_read_config(dev, PCIR_CACHELNSZ, 1);
3628                 u_short command  = pci_read_config(dev, PCIR_COMMAND, 2);
3629
3630                 if (!cachelnsz) {
3631                         cachelnsz = 8;
3632                         printf("%s: setting PCI cache line size register to %d.\n",
3633                                 ncr_name(np), (int)cachelnsz);
3634                         pci_write_config(dev, PCIR_CACHELNSZ, cachelnsz, 1);
3635                 }
3636
3637                 if (!(command & (1<<4))) {
3638                         command |= (1<<4);
3639                         printf("%s: setting PCI command write and invalidate.\n",
3640                                 ncr_name(np));
3641                         pci_write_config(dev, PCIR_COMMAND, command, 2);
3642                 }
3643         }
3644 #endif /* PCIR_CACHELNSZ */
3645
3646 #endif /* SCSI_NCR_PCI_CONFIG_FIXUP */
3647
3648         /* Initialize per-target user settings */
3649         usrsync = 0;
3650         if (SCSI_NCR_DFLT_SYNC) {
3651                 usrsync = SCSI_NCR_DFLT_SYNC;
3652                 if (usrsync > np->maxsync)
3653                         usrsync = np->maxsync;
3654                 if (usrsync < np->minsync)
3655                         usrsync = np->minsync;
3656         };
3657
3658         usrwide = (SCSI_NCR_MAX_WIDE);
3659         if (usrwide > np->maxwide) usrwide=np->maxwide;
3660
3661         for (i=0;i<MAX_TARGET;i++) {
3662                 tcb_p tp = &np->target[i];
3663
3664                 tp->tinfo.user.period = usrsync;
3665                 tp->tinfo.user.offset = usrsync != 0 ? np->maxoffs : 0;
3666                 tp->tinfo.user.width = usrwide;
3667                 tp->tinfo.disc_tag = NCR_CUR_DISCENB
3668                                    | NCR_CUR_TAGENB
3669                                    | NCR_USR_DISCENB
3670                                    | NCR_USR_TAGENB;
3671         }
3672
3673         /*
3674         **      Bells and whistles   ;-)
3675         */
3676         if (bootverbose)
3677                 printf("%s: minsync=%d, maxsync=%d, maxoffs=%d, %d dwords burst, %s dma fifo\n",
3678                 ncr_name(np), np->minsync, np->maxsync, np->maxoffs,
3679                 burst_length(np->maxburst),
3680                 (np->rv_ctest5 & DFS) ? "large" : "normal");
3681
3682         /*
3683         **      Print some complementary information that can be helpfull.
3684         */
3685         if (bootverbose)
3686                 printf("%s: %s, %s IRQ driver%s\n",
3687                         ncr_name(np),
3688                         np->rv_stest2 & 0x20 ? "differential" : "single-ended",
3689                         np->rv_dcntl & IRQM ? "totem pole" : "open drain",
3690                         np->sram_res ? ", using on-chip SRAM" : "");
3691                         
3692         /*
3693         **      Patch scripts to physical addresses
3694         */
3695         ncr_script_fill (&script0, &scripth0);
3696
3697         if (np->script)
3698                 np->p_script    = vtophys(np->script);
3699         np->p_scripth   = vtophys(np->scripth);
3700
3701         ncr_script_copy_and_bind (np, (ncrcmd *) &script0,
3702                         (ncrcmd *) np->script, sizeof(struct script));
3703
3704         ncr_script_copy_and_bind (np, (ncrcmd *) &scripth0,
3705                 (ncrcmd *) np->scripth, sizeof(struct scripth));
3706
3707         /*
3708         **    Patch the script for LED support.
3709         */
3710
3711         if (np->features & FE_LED0) {
3712                 WRITESCRIPT(reselect[0],  SCR_REG_REG(gpreg, SCR_OR,  0x01));
3713                 WRITESCRIPT(reselect1[0], SCR_REG_REG(gpreg, SCR_AND, 0xfe));
3714                 WRITESCRIPT(reselect2[0], SCR_REG_REG(gpreg, SCR_AND, 0xfe));
3715         }
3716
3717         /*
3718         **      init data structure
3719         */
3720
3721         np->jump_tcb.l_cmd      = SCR_JUMP;
3722         np->jump_tcb.l_paddr    = NCB_SCRIPTH_PHYS (np, abort);
3723
3724         /*
3725         **  Get SCSI addr of host adapter (set by bios?).
3726         */
3727
3728         np->myaddr = INB(nc_scid) & 0x07;
3729         if (!np->myaddr) np->myaddr = SCSI_NCR_MYADDR;
3730
3731 #ifdef NCR_DUMP_REG
3732         /*
3733         **      Log the initial register contents
3734         */
3735         {
3736                 int reg;
3737                 for (reg=0; reg<256; reg+=4) {
3738                         if (reg%16==0) printf ("reg[%2x]", reg);
3739                         printf (" %08x", (int)pci_conf_read (config_id, reg));
3740                         if (reg%16==12) printf ("\n");
3741                 }
3742         }
3743 #endif /* NCR_DUMP_REG */
3744
3745         /*
3746         **      Reset chip.
3747         */
3748
3749         OUTB (nc_istat,  SRST);
3750         DELAY (1000);
3751         OUTB (nc_istat,  0   );
3752
3753
3754         /*
3755         **      Now check the cache handling of the pci chipset.
3756         */
3757
3758         if (ncr_snooptest (np)) {
3759                 printf ("CACHE INCORRECTLY CONFIGURED.\n");
3760                 return EINVAL;
3761         };
3762
3763         /*
3764         **      Install the interrupt handler.
3765         */
3766
3767         rid = 0;
3768         np->irq_res = bus_alloc_resource(dev, SYS_RES_IRQ, &rid, 0, ~0, 1,
3769                                          RF_SHAREABLE | RF_ACTIVE);
3770         if (np->irq_res == NULL) {
3771                 device_printf(dev,
3772                               "interruptless mode: reduced performance.\n");
3773         } else {
3774                 bus_setup_intr(dev, np->irq_res, INTR_TYPE_CAM,
3775                                ncr_intr, np, &np->irq_handle);
3776         }
3777
3778         /*
3779         ** Create the device queue.  We only allow MAX_START-1 concurrent
3780         ** transactions so we can be sure to have one element free in our
3781         ** start queue to reset to the idle loop.
3782         */
3783         devq = cam_simq_alloc(MAX_START - 1);
3784         if (devq == NULL)
3785                 return ENOMEM;
3786
3787         /*
3788         **      Now tell the generic SCSI layer
3789         **      about our bus.
3790         */
3791         np->sim = cam_sim_alloc(ncr_action, ncr_poll, "ncr", np, np->unit,
3792                                 1, MAX_TAGS, devq);
3793         cam_simq_release(devq);
3794         if (np->sim == NULL)
3795                 return ENOMEM;
3796
3797         
3798         if (xpt_bus_register(np->sim, 0) != CAM_SUCCESS) {
3799                 cam_sim_free(np->sim);
3800                 return ENOMEM;
3801         }
3802         
3803         if (xpt_create_path(&np->path, /*periph*/NULL,
3804                             cam_sim_path(np->sim), CAM_TARGET_WILDCARD,
3805                             CAM_LUN_WILDCARD) != CAM_REQ_CMP) {
3806                 xpt_bus_deregister(cam_sim_path(np->sim));
3807                 cam_sim_free(np->sim);
3808                 return ENOMEM;
3809         }
3810
3811         /*
3812         **      start the timeout daemon
3813         */
3814         ncr_timeout (np);
3815         np->lasttime=0;
3816
3817         return 0;
3818 }
3819
3820 /*==========================================================
3821 **
3822 **
3823 **      Process pending device interrupts.
3824 **
3825 **
3826 **==========================================================
3827 */
3828
3829 static void
3830 ncr_intr(vnp)
3831         void *vnp;
3832 {
3833         ncb_p np = vnp;
3834         int oldspl = splcam();
3835
3836         if (DEBUG_FLAGS & DEBUG_TINY) printf ("[");
3837
3838         if (INB(nc_istat) & (INTF|SIP|DIP)) {
3839                 /*
3840                 **      Repeat until no outstanding ints
3841                 */
3842                 do {
3843                         ncr_exception (np);
3844                 } while (INB(nc_istat) & (INTF|SIP|DIP));
3845
3846                 np->ticks = 100;
3847         };
3848
3849         if (DEBUG_FLAGS & DEBUG_TINY) printf ("]\n");
3850
3851         splx (oldspl);
3852 }
3853
3854 /*==========================================================
3855 **
3856 **
3857 **      Start execution of a SCSI command.
3858 **      This is called from the generic SCSI driver.
3859 **
3860 **
3861 **==========================================================
3862 */
3863
3864 static void
3865 ncr_action (struct cam_sim *sim, union ccb *ccb)
3866 {
3867         ncb_p np;
3868
3869         np = (ncb_p) cam_sim_softc(sim);
3870
3871         switch (ccb->ccb_h.func_code) {
3872         /* Common cases first */
3873         case XPT_SCSI_IO:       /* Execute the requested I/O operation */
3874         {
3875                 nccb_p cp;
3876                 lcb_p lp;
3877                 tcb_p tp;
3878                 int oldspl;
3879                 struct ccb_scsiio *csio;
3880                 u_int8_t *msgptr;
3881                 u_int msglen;
3882                 u_int msglen2;
3883                 int segments;
3884                 u_int8_t nego;
3885                 u_int8_t idmsg;
3886                 int qidx;
3887                 
3888                 tp = &np->target[ccb->ccb_h.target_id];
3889                 csio = &ccb->csio;
3890
3891                 oldspl = splcam();
3892
3893                 /*
3894                  * Last time we need to check if this CCB needs to
3895                  * be aborted.
3896                  */
3897                 if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_INPROG) {
3898                         xpt_done(ccb);
3899                         splx(oldspl);
3900                         return;
3901                 }
3902                 ccb->ccb_h.status |= CAM_SIM_QUEUED;
3903
3904                 /*---------------------------------------------------
3905                 **
3906                 **      Assign an nccb / bind ccb
3907                 **
3908                 **----------------------------------------------------
3909                 */
3910                 cp = ncr_get_nccb (np, ccb->ccb_h.target_id,
3911                                    ccb->ccb_h.target_lun);
3912                 if (cp == NULL) {
3913                         /* XXX JGibbs - Freeze SIMQ */
3914                         ccb->ccb_h.status = CAM_RESRC_UNAVAIL;
3915                         xpt_done(ccb);
3916                         return;
3917                 };
3918                 
3919                 cp->ccb = ccb;
3920                 
3921                 /*---------------------------------------------------
3922                 **
3923                 **      timestamp
3924                 **
3925                 **----------------------------------------------------
3926                 */
3927                 /*
3928                 ** XXX JGibbs - Isn't this expensive
3929                 **              enough to be conditionalized??
3930                 */
3931
3932                 bzero (&cp->phys.header.stamp, sizeof (struct tstamp));
3933                 cp->phys.header.stamp.start = ticks;
3934
3935                 nego = 0;
3936                 if (tp->nego_cp == NULL) {
3937                         
3938                         if (tp->tinfo.current.width
3939                          != tp->tinfo.goal.width) {
3940                                 tp->nego_cp = cp;
3941                                 nego = NS_WIDE;
3942                         } else if ((tp->tinfo.current.period
3943                                     != tp->tinfo.goal.period)
3944                                 || (tp->tinfo.current.offset
3945                                     != tp->tinfo.goal.offset)) {
3946                                 tp->nego_cp = cp;
3947                                 nego = NS_SYNC;
3948                         };
3949                 };
3950
3951                 /*---------------------------------------------------
3952                 **
3953                 **      choose a new tag ...
3954                 **
3955                 **----------------------------------------------------
3956                 */
3957                 lp = tp->lp[ccb->ccb_h.target_lun];
3958
3959                 if ((ccb->ccb_h.flags & CAM_TAG_ACTION_VALID) != 0
3960                  && (ccb->csio.tag_action != CAM_TAG_ACTION_NONE)
3961                  && (nego == 0)) {
3962                         /*
3963                         **      assign a tag to this nccb
3964                         */
3965                         while (!cp->tag) {
3966                                 nccb_p cp2 = lp->next_nccb;
3967                                 lp->lasttag = lp->lasttag % 255 + 1;
3968                                 while (cp2 && cp2->tag != lp->lasttag)
3969                                         cp2 = cp2->next_nccb;
3970                                 if (cp2) continue;
3971                                 cp->tag=lp->lasttag;
3972                                 if (DEBUG_FLAGS & DEBUG_TAGS) {
3973                                         PRINT_ADDR(ccb);
3974                                         printf ("using tag #%d.\n", cp->tag);
3975                                 };
3976                         };
3977                 } else {
3978                         cp->tag=0;
3979                 };
3980
3981                 /*----------------------------------------------------
3982                 **
3983                 **      Build the identify / tag / sdtr message
3984                 **
3985                 **----------------------------------------------------
3986                 */
3987                 idmsg = MSG_IDENTIFYFLAG | ccb->ccb_h.target_lun;
3988                 if (tp->tinfo.disc_tag & NCR_CUR_DISCENB)
3989                         idmsg |= MSG_IDENTIFY_DISCFLAG;
3990
3991                 msgptr = cp->scsi_smsg;
3992                 msglen = 0;
3993                 msgptr[msglen++] = idmsg;
3994
3995                 if (cp->tag) {
3996                         msgptr[msglen++] = ccb->csio.tag_action;
3997                         msgptr[msglen++] = cp->tag;
3998                 }
3999
4000                 switch (nego) {
4001                 case NS_SYNC:
4002                         msgptr[msglen++] = MSG_EXTENDED;
4003                         msgptr[msglen++] = MSG_EXT_SDTR_LEN;
4004                         msgptr[msglen++] = MSG_EXT_SDTR;
4005                         msgptr[msglen++] = tp->tinfo.goal.period;
4006                         msgptr[msglen++] = tp->tinfo.goal.offset;;
4007                         if (DEBUG_FLAGS & DEBUG_NEGO) {
4008                                 PRINT_ADDR(ccb);
4009                                 printf ("sync msgout: ");
4010                                 ncr_show_msg (&cp->scsi_smsg [msglen-5]);
4011                                 printf (".\n");
4012                         };
4013                         break;
4014                 case NS_WIDE:
4015                         msgptr[msglen++] = MSG_EXTENDED;
4016                         msgptr[msglen++] = MSG_EXT_WDTR_LEN;
4017                         msgptr[msglen++] = MSG_EXT_WDTR;
4018                         msgptr[msglen++] = tp->tinfo.goal.width;
4019                         if (DEBUG_FLAGS & DEBUG_NEGO) {
4020                                 PRINT_ADDR(ccb);
4021                                 printf ("wide msgout: ");
4022                                 ncr_show_msg (&cp->scsi_smsg [msglen-4]);
4023                                 printf (".\n");
4024                         };
4025                         break;
4026                 };
4027
4028                 /*----------------------------------------------------
4029                 **
4030                 **      Build the identify message for getcc.
4031                 **
4032                 **----------------------------------------------------
4033                 */
4034
4035                 cp->scsi_smsg2 [0] = idmsg;
4036                 msglen2 = 1;
4037
4038                 /*----------------------------------------------------
4039                 **
4040                 **      Build the data descriptors
4041                 **
4042                 **----------------------------------------------------
4043                 */
4044
4045                 /* XXX JGibbs - Handle other types of I/O */
4046                 if ((ccb->ccb_h.flags & CAM_DIR_MASK) != CAM_DIR_NONE) {
4047                         segments = ncr_scatter(&cp->phys,
4048                                                (vm_offset_t)csio->data_ptr,
4049                                                (vm_size_t)csio->dxfer_len);
4050
4051                         if (segments < 0) {
4052                                 ccb->ccb_h.status = CAM_REQ_TOO_BIG;
4053                                 ncr_free_nccb(np, cp);
4054                                 splx(oldspl);
4055                                 xpt_done(ccb);
4056                                 return;
4057                         }
4058                         if ((ccb->ccb_h.flags & CAM_DIR_MASK) == CAM_DIR_IN) {
4059                                 cp->phys.header.savep = NCB_SCRIPT_PHYS (np, data_in);
4060                                 cp->phys.header.goalp = cp->phys.header.savep +20 +segments*16;
4061                         } else { /* CAM_DIR_OUT */
4062                                 cp->phys.header.savep = NCB_SCRIPT_PHYS (np, data_out);
4063                                 cp->phys.header.goalp = cp->phys.header.savep +20 +segments*16;
4064                         }
4065                 } else {
4066                         cp->phys.header.savep = NCB_SCRIPT_PHYS (np, no_data);
4067                         cp->phys.header.goalp = cp->phys.header.savep;
4068                 }
4069
4070                 cp->phys.header.lastp = cp->phys.header.savep;
4071
4072
4073                 /*----------------------------------------------------
4074                 **
4075                 **      fill in nccb
4076                 **
4077                 **----------------------------------------------------
4078                 **
4079                 **
4080                 **      physical -> virtual backlink
4081                 **      Generic SCSI command
4082                 */
4083                 cp->phys.header.cp              = cp;
4084                 /*
4085                 **      Startqueue
4086                 */
4087                 cp->phys.header.launch.l_paddr  = NCB_SCRIPT_PHYS (np, select);
4088                 cp->phys.header.launch.l_cmd    = SCR_JUMP;
4089                 /*
4090                 **      select
4091                 */
4092                 cp->phys.select.sel_id          = ccb->ccb_h.target_id;
4093                 cp->phys.select.sel_scntl3      = tp->tinfo.wval;
4094                 cp->phys.select.sel_sxfer       = tp->tinfo.sval;
4095                 /*
4096                 **      message
4097                 */
4098                 cp->phys.smsg.addr              = CCB_PHYS (cp, scsi_smsg);
4099                 cp->phys.smsg.size              = msglen;
4100         
4101                 cp->phys.smsg2.addr             = CCB_PHYS (cp, scsi_smsg2);
4102                 cp->phys.smsg2.size             = msglen2;
4103                 /*
4104                 **      command
4105                 */
4106                 /* XXX JGibbs - Support other command types */
4107                 cp->phys.cmd.addr               = vtophys (csio->cdb_io.cdb_bytes);
4108                 cp->phys.cmd.size               = csio->cdb_len;
4109                 /*
4110                 **      sense command
4111                 */
4112                 cp->phys.scmd.addr              = CCB_PHYS (cp, sensecmd);
4113                 cp->phys.scmd.size              = 6;
4114                 /*
4115                 **      patch requested size into sense command
4116                 */
4117                 cp->sensecmd[0]                 = 0x03;
4118                 cp->sensecmd[1]                 = ccb->ccb_h.target_lun << 5;
4119                 cp->sensecmd[4]                 = sizeof(struct scsi_sense_data);
4120                 cp->sensecmd[4]                 = csio->sense_len;
4121                 /*
4122                 **      sense data
4123                 */
4124                 cp->phys.sense.addr             = vtophys (&csio->sense_data);
4125                 cp->phys.sense.size             = csio->sense_len;
4126                 /*
4127                 **      status
4128                 */
4129                 cp->actualquirks                = QUIRK_NOMSG;
4130                 cp->host_status                 = nego ? HS_NEGOTIATE : HS_BUSY;
4131                 cp->s_status                    = SCSI_STATUS_ILLEGAL;
4132                 cp->parity_status               = 0;
4133         
4134                 cp->xerr_status                 = XE_OK;
4135                 cp->sync_status                 = tp->tinfo.sval;
4136                 cp->nego_status                 = nego;
4137                 cp->wide_status                 = tp->tinfo.wval;
4138
4139                 /*----------------------------------------------------
4140                 **
4141                 **      Critical region: start this job.
4142                 **
4143                 **----------------------------------------------------
4144                 */
4145
4146                 /*
4147                 **      reselect pattern and activate this job.
4148                 */
4149
4150                 cp->jump_nccb.l_cmd     = (SCR_JUMP ^ IFFALSE (DATA (cp->tag)));
4151                 cp->tlimit              = time_second
4152                                         + ccb->ccb_h.timeout / 1000 + 2;
4153                 cp->magic               = CCB_MAGIC;
4154
4155                 /*
4156                 **      insert into start queue.
4157                 */
4158
4159                 qidx = np->squeueput + 1;
4160                 if (qidx >= MAX_START)
4161                         qidx = 0;
4162                 np->squeue [qidx         ] = NCB_SCRIPT_PHYS (np, idle);
4163                 np->squeue [np->squeueput] = CCB_PHYS (cp, phys);
4164                 np->squeueput = qidx;
4165
4166                 if(DEBUG_FLAGS & DEBUG_QUEUE)
4167                         printf("%s: queuepos=%d tryoffset=%d.\n",
4168                                ncr_name (np), np->squeueput,
4169                                (unsigned)(READSCRIPT(startpos[0]) - 
4170                                (NCB_SCRIPTH_PHYS (np, tryloop))));
4171
4172                 /*
4173                 **      Script processor may be waiting for reselect.
4174                 **      Wake it up.
4175                 */
4176                 OUTB (nc_istat, SIGP);
4177
4178                 /*
4179                 **      and reenable interrupts
4180                 */
4181                 splx (oldspl);
4182                 break;
4183         }
4184         case XPT_RESET_DEV:     /* Bus Device Reset the specified SCSI device */
4185         case XPT_EN_LUN:                /* Enable LUN as a target */
4186         case XPT_TARGET_IO:             /* Execute target I/O request */
4187         case XPT_ACCEPT_TARGET_IO:      /* Accept Host Target Mode CDB */
4188         case XPT_CONT_TARGET_IO:        /* Continue Host Target I/O Connection*/
4189         case XPT_ABORT:                 /* Abort the specified CCB */
4190                 /* XXX Implement */
4191                 ccb->ccb_h.status = CAM_REQ_INVALID;
4192                 xpt_done(ccb);
4193                 break;
4194         case XPT_SET_TRAN_SETTINGS:
4195         {
4196                 struct  ccb_trans_settings *cts;
4197                 tcb_p   tp;
4198                 u_int   update_type;
4199                 int     s;
4200
4201                 cts = &ccb->cts;
4202                 update_type = 0;
4203                 if ((cts->flags & CCB_TRANS_CURRENT_SETTINGS) != 0)
4204                         update_type |= NCR_TRANS_GOAL;
4205                 if ((cts->flags & CCB_TRANS_USER_SETTINGS) != 0)
4206                         update_type |= NCR_TRANS_USER;
4207                 
4208                 s = splcam();
4209                 tp = &np->target[ccb->ccb_h.target_id];
4210                 /* Tag and disc enables */
4211                 if ((cts->valid & CCB_TRANS_DISC_VALID) != 0) {
4212                         if (update_type & NCR_TRANS_GOAL) {
4213                                 if ((cts->flags & CCB_TRANS_DISC_ENB) != 0)
4214                                         tp->tinfo.disc_tag |= NCR_CUR_DISCENB;
4215                                 else
4216                                         tp->tinfo.disc_tag &= ~NCR_CUR_DISCENB;
4217                         }
4218
4219                         if (update_type & NCR_TRANS_USER) {
4220                                 if ((cts->flags & CCB_TRANS_DISC_ENB) != 0)
4221                                         tp->tinfo.disc_tag |= NCR_USR_DISCENB;
4222                                 else
4223                                         tp->tinfo.disc_tag &= ~NCR_USR_DISCENB;
4224                         }
4225
4226                 }
4227
4228                 if ((cts->valid & CCB_TRANS_TQ_VALID) != 0) {
4229                         if (update_type & NCR_TRANS_GOAL) {
4230                                 if ((cts->flags & CCB_TRANS_TAG_ENB) != 0)
4231                                         tp->tinfo.disc_tag |= NCR_CUR_TAGENB;
4232                                 else
4233                                         tp->tinfo.disc_tag &= ~NCR_CUR_TAGENB;
4234                         }
4235
4236                         if (update_type & NCR_TRANS_USER) {
4237                                 if ((cts->flags & CCB_TRANS_TAG_ENB) != 0)
4238                                         tp->tinfo.disc_tag |= NCR_USR_TAGENB;
4239                                 else
4240                                         tp->tinfo.disc_tag &= ~NCR_USR_TAGENB;
4241                         }       
4242                 }
4243
4244                 /* Filter bus width and sync negotiation settings */
4245                 if ((cts->valid & CCB_TRANS_BUS_WIDTH_VALID) != 0) {
4246                         if (cts->bus_width > np->maxwide)
4247                                 cts->bus_width = np->maxwide;
4248                 }
4249
4250                 if (((cts->valid & CCB_TRANS_SYNC_RATE_VALID) != 0)
4251                  || ((cts->valid & CCB_TRANS_SYNC_OFFSET_VALID) != 0)) {
4252                         if ((cts->valid & CCB_TRANS_SYNC_RATE_VALID) != 0) {
4253                                 if (cts->sync_period != 0
4254                                  && (cts->sync_period < np->minsync))
4255                                         cts->sync_period = np->minsync;
4256                         }
4257                         if ((cts->valid & CCB_TRANS_SYNC_OFFSET_VALID) != 0) {
4258                                 if (cts->sync_offset == 0)
4259                                         cts->sync_period = 0;
4260                                 if (cts->sync_offset > np->maxoffs)
4261                                         cts->sync_offset = np->maxoffs;
4262                         }
4263                 }
4264                 if ((update_type & NCR_TRANS_USER) != 0) {
4265                         if ((cts->valid & CCB_TRANS_SYNC_RATE_VALID) != 0)
4266                                 tp->tinfo.user.period = cts->sync_period;
4267                         if ((cts->valid & CCB_TRANS_SYNC_OFFSET_VALID) != 0)
4268                                 tp->tinfo.user.offset = cts->sync_offset;
4269                         if ((cts->valid & CCB_TRANS_BUS_WIDTH_VALID) != 0)
4270                                 tp->tinfo.user.width = cts->bus_width;
4271                 }
4272                 if ((update_type & NCR_TRANS_GOAL) != 0) {
4273                         if ((cts->valid & CCB_TRANS_SYNC_RATE_VALID) != 0)
4274                                 tp->tinfo.goal.period = cts->sync_period;
4275
4276                         if ((cts->valid & CCB_TRANS_SYNC_OFFSET_VALID) != 0)
4277                                 tp->tinfo.goal.offset = cts->sync_offset;
4278
4279                         if ((cts->valid & CCB_TRANS_BUS_WIDTH_VALID) != 0)
4280                                 tp->tinfo.goal.width = cts->bus_width;
4281                 }
4282                 splx(s);
4283                 ccb->ccb_h.status = CAM_REQ_CMP;
4284                 xpt_done(ccb);
4285                 break;
4286         }
4287         case XPT_GET_TRAN_SETTINGS:
4288         /* Get default/user set transfer settings for the target */
4289         {
4290                 struct  ccb_trans_settings *cts;
4291                 struct  ncr_transinfo *tinfo;
4292                 tcb_p   tp;             
4293                 int     s;
4294
4295                 cts = &ccb->cts;
4296                 tp = &np->target[ccb->ccb_h.target_id];
4297                 
4298                 s = splcam();
4299                 if ((cts->flags & CCB_TRANS_CURRENT_SETTINGS) != 0) {
4300                         tinfo = &tp->tinfo.current;
4301                         if (tp->tinfo.disc_tag & NCR_CUR_DISCENB)
4302                                 cts->flags |= CCB_TRANS_DISC_ENB;
4303                         else
4304                                 cts->flags &= ~CCB_TRANS_DISC_ENB;
4305
4306                         if (tp->tinfo.disc_tag & NCR_CUR_TAGENB)
4307                                 cts->flags |= CCB_TRANS_TAG_ENB;
4308                         else
4309                                 cts->flags &= ~CCB_TRANS_TAG_ENB;
4310                 } else {
4311                         tinfo = &tp->tinfo.user;
4312                         if (tp->tinfo.disc_tag & NCR_USR_DISCENB)
4313                                 cts->flags |= CCB_TRANS_DISC_ENB;
4314                         else
4315                                 cts->flags &= ~CCB_TRANS_DISC_ENB;
4316
4317                         if (tp->tinfo.disc_tag & NCR_USR_TAGENB)
4318                                 cts->flags |= CCB_TRANS_TAG_ENB;
4319                         else
4320                                 cts->flags &= ~CCB_TRANS_TAG_ENB;
4321                 }
4322
4323                 cts->sync_period = tinfo->period;
4324                 cts->sync_offset = tinfo->offset;
4325                 cts->bus_width = tinfo->width;
4326
4327                 splx(s);
4328
4329                 cts->valid = CCB_TRANS_SYNC_RATE_VALID
4330                            | CCB_TRANS_SYNC_OFFSET_VALID
4331                            | CCB_TRANS_BUS_WIDTH_VALID
4332                            | CCB_TRANS_DISC_VALID
4333                            | CCB_TRANS_TQ_VALID;
4334
4335                 ccb->ccb_h.status = CAM_REQ_CMP;
4336                 xpt_done(ccb);
4337                 break;
4338         }
4339         case XPT_CALC_GEOMETRY:
4340         {
4341                 struct    ccb_calc_geometry *ccg;
4342                 u_int32_t size_mb;
4343                 u_int32_t secs_per_cylinder;
4344                 int       extended;
4345
4346                 /* XXX JGibbs - I'm sure the NCR uses a different strategy,
4347                  *              but it should be able to deal with Adaptec
4348                  *              geometry too.
4349                  */
4350                 extended = 1;
4351                 ccg = &ccb->ccg;
4352                 size_mb = ccg->volume_size
4353                         / ((1024L * 1024L) / ccg->block_size);
4354                 
4355                 if (size_mb > 1024 && extended) {
4356                         ccg->heads = 255;
4357                         ccg->secs_per_track = 63;
4358                 } else {
4359                         ccg->heads = 64;
4360                         ccg->secs_per_track = 32;
4361                 }
4362                 secs_per_cylinder = ccg->heads * ccg->secs_per_track;
4363                 ccg->cylinders = ccg->volume_size / secs_per_cylinder;
4364                 ccb->ccb_h.status = CAM_REQ_CMP;
4365                 xpt_done(ccb);
4366                 break;
4367         }
4368         case XPT_RESET_BUS:             /* Reset the specified SCSI bus */
4369         {
4370                 OUTB (nc_scntl1, CRST);
4371                 ccb->ccb_h.status = CAM_REQ_CMP;
4372                 DELAY(10000);   /* Wait until our interrupt handler sees it */ 
4373                 xpt_done(ccb);
4374                 break;
4375         }
4376         case XPT_TERM_IO:               /* Terminate the I/O process */
4377                 /* XXX Implement */
4378                 ccb->ccb_h.status = CAM_REQ_INVALID;
4379                 xpt_done(ccb);
4380                 break;
4381         case XPT_PATH_INQ:              /* Path routing inquiry */
4382         {
4383                 struct ccb_pathinq *cpi = &ccb->cpi;
4384                 
4385                 cpi->version_num = 1; /* XXX??? */
4386                 cpi->hba_inquiry = PI_SDTR_ABLE|PI_TAG_ABLE;
4387                 if ((np->features & FE_WIDE) != 0)
4388                         cpi->hba_inquiry |= PI_WIDE_16;
4389                 cpi->target_sprt = 0;
4390                 cpi->hba_misc = 0;
4391                 cpi->hba_eng_cnt = 0;
4392                 cpi->max_target = (np->features & FE_WIDE) ? 15 : 7;
4393                 cpi->max_lun = MAX_LUN - 1;
4394                 cpi->initiator_id = np->myaddr;
4395                 cpi->bus_id = cam_sim_bus(sim);
4396                 cpi->base_transfer_speed = 3300;
4397                 strncpy(cpi->sim_vid, "FreeBSD", SIM_IDLEN);
4398                 strncpy(cpi->hba_vid, "Symbios", HBA_IDLEN);
4399                 strncpy(cpi->dev_name, cam_sim_name(sim), DEV_IDLEN);
4400                 cpi->unit_number = cam_sim_unit(sim);
4401                 cpi->ccb_h.status = CAM_REQ_CMP;
4402                 xpt_done(ccb);
4403                 break;
4404         }
4405         default:
4406                 ccb->ccb_h.status = CAM_REQ_INVALID;
4407                 xpt_done(ccb);
4408                 break;
4409         }
4410 }
4411
4412 /*==========================================================
4413 **
4414 **
4415 **      Complete execution of a SCSI command.
4416 **      Signal completion to the generic SCSI driver.
4417 **
4418 **
4419 **==========================================================
4420 */
4421
4422 void
4423 ncr_complete (ncb_p np, nccb_p cp)
4424 {
4425         union ccb *ccb;
4426         tcb_p tp;
4427         lcb_p lp;
4428
4429         /*
4430         **      Sanity check
4431         */
4432
4433         if (!cp || (cp->magic!=CCB_MAGIC) || !cp->ccb) return;
4434         cp->magic = 1;
4435         cp->tlimit= 0;
4436
4437         /*
4438         **      No Reselect anymore.
4439         */
4440         cp->jump_nccb.l_cmd = (SCR_JUMP);
4441
4442         /*
4443         **      No starting.
4444         */
4445         cp->phys.header.launch.l_paddr= NCB_SCRIPT_PHYS (np, idle);
4446
4447         /*
4448         **      timestamp
4449         */
4450         ncb_profile (np, cp);
4451
4452         if (DEBUG_FLAGS & DEBUG_TINY)
4453                 printf ("CCB=%x STAT=%x/%x\n", (int)(intptr_t)cp & 0xfff,
4454                         cp->host_status,cp->s_status);
4455
4456         ccb = cp->ccb;
4457         cp->ccb = NULL;
4458         tp = &np->target[ccb->ccb_h.target_id];
4459         lp = tp->lp[ccb->ccb_h.target_lun];
4460
4461         /*
4462         **      We do not queue more than 1 nccb per target 
4463         **      with negotiation at any time. If this nccb was 
4464         **      used for negotiation, clear this info in the tcb.
4465         */
4466
4467         if (cp == tp->nego_cp)
4468                 tp->nego_cp = NULL;
4469
4470         /*
4471         **      Check for parity errors.
4472         */
4473         /* XXX JGibbs - What about reporting them??? */
4474
4475         if (cp->parity_status) {
4476                 PRINT_ADDR(ccb);
4477                 printf ("%d parity error(s), fallback.\n", cp->parity_status);
4478                 /*
4479                 **      fallback to asynch transfer.
4480                 */
4481                 tp->tinfo.goal.period = 0;
4482                 tp->tinfo.goal.offset = 0;
4483         };
4484
4485         /*
4486         **      Check for extended errors.
4487         */
4488
4489         if (cp->xerr_status != XE_OK) {
4490                 PRINT_ADDR(ccb);
4491                 switch (cp->xerr_status) {
4492                 case XE_EXTRA_DATA:
4493                         printf ("extraneous data discarded.\n");
4494                         break;
4495                 case XE_BAD_PHASE:
4496                         printf ("illegal scsi phase (4/5).\n");
4497                         break;
4498                 default:
4499                         printf ("extended error %d.\n", cp->xerr_status);
4500                         break;
4501                 };
4502                 if (cp->host_status==HS_COMPLETE)
4503                         cp->host_status = HS_FAIL;
4504         };
4505
4506         /*
4507         **      Check the status.
4508         */
4509         if (cp->host_status == HS_COMPLETE) {
4510
4511                 if (cp->s_status == SCSI_STATUS_OK) {
4512
4513                         /*
4514                         **      All went well.
4515                         */
4516                         /* XXX JGibbs - Properly calculate residual */
4517
4518                         tp->bytes     += ccb->csio.dxfer_len;
4519                         tp->transfers ++;
4520
4521                         ccb->ccb_h.status = CAM_REQ_CMP;
4522                 } else if ((cp->s_status & SCSI_STATUS_SENSE) != 0) {
4523
4524                         /*
4525                          * XXX Could be TERMIO too.  Should record
4526                          * original status.
4527                          */
4528                         ccb->csio.scsi_status = SCSI_STATUS_CHECK_COND;
4529                         cp->s_status &= ~SCSI_STATUS_SENSE;
4530                         if (cp->s_status == SCSI_STATUS_OK) {
4531                                 ccb->ccb_h.status =
4532                                     CAM_AUTOSNS_VALID|CAM_SCSI_STATUS_ERROR;
4533                         } else {
4534                                 ccb->ccb_h.status = CAM_AUTOSENSE_FAIL;
4535                         }
4536                 } else {
4537                         ccb->ccb_h.status = CAM_SCSI_STATUS_ERROR;                      
4538                         ccb->csio.scsi_status = cp->s_status;
4539                 }
4540                 
4541                 
4542         } else if (cp->host_status == HS_SEL_TIMEOUT) {
4543
4544                 /*
4545                 **   Device failed selection
4546                 */
4547                 ccb->ccb_h.status = CAM_SEL_TIMEOUT;
4548
4549         } else if (cp->host_status == HS_TIMEOUT) {
4550
4551                 /*
4552                 **   No response
4553                 */
4554                 ccb->ccb_h.status = CAM_CMD_TIMEOUT;
4555         } else if (cp->host_status == HS_STALL) {
4556                 ccb->ccb_h.status = CAM_REQUEUE_REQ;
4557         } else {
4558
4559                 /*
4560                 **  Other protocol messes
4561                 */
4562                 PRINT_ADDR(ccb);
4563                 printf ("COMMAND FAILED (%x %x) @%p.\n",
4564                         cp->host_status, cp->s_status, cp);
4565
4566                 ccb->ccb_h.status = CAM_CMD_TIMEOUT;
4567         }
4568
4569         if ((ccb->ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) {
4570                 xpt_freeze_devq(ccb->ccb_h.path, /*count*/1);
4571                 ccb->ccb_h.status |= CAM_DEV_QFRZN;
4572         }
4573
4574         /*
4575         **      Free this nccb
4576         */
4577         ncr_free_nccb (np, cp);
4578
4579         /*
4580         **      signal completion to generic driver.
4581         */
4582         xpt_done (ccb);
4583 }
4584
4585 /*==========================================================
4586 **
4587 **
4588 **      Signal all (or one) control block done.
4589 **
4590 **
4591 **==========================================================
4592 */
4593
4594 void
4595 ncr_wakeup (ncb_p np, u_long code)
4596 {
4597         /*
4598         **      Starting at the default nccb and following
4599         **      the links, complete all jobs with a
4600         **      host_status greater than "disconnect".
4601         **
4602         **      If the "code" parameter is not zero,
4603         **      complete all jobs that are not IDLE.
4604         */
4605
4606         nccb_p cp = np->link_nccb;
4607         while (cp) {
4608                 switch (cp->host_status) {
4609
4610                 case HS_IDLE:
4611                         break;
4612
4613                 case HS_DISCONNECT:
4614                         if(DEBUG_FLAGS & DEBUG_TINY) printf ("D");
4615                         /* fall through */
4616
4617                 case HS_BUSY:
4618                 case HS_NEGOTIATE:
4619                         if (!code) break;
4620                         cp->host_status = code;
4621
4622                         /* fall through */
4623
4624                 default:
4625                         ncr_complete (np, cp);
4626                         break;
4627                 };
4628                 cp = cp -> link_nccb;
4629         };
4630 }
4631
4632 static void
4633 ncr_freeze_devq (ncb_p np, struct cam_path *path)
4634 {
4635         nccb_p  cp;
4636         int     i;
4637         int     count;
4638         int     firstskip;
4639         /*
4640         **      Starting at the first nccb and following
4641         **      the links, complete all jobs that match
4642         **      the passed in path and are in the start queue.
4643         */
4644
4645         cp = np->link_nccb;
4646         count = 0;
4647         firstskip = 0;
4648         while (cp) {
4649                 switch (cp->host_status) {
4650
4651                 case HS_BUSY:
4652                 case HS_NEGOTIATE:
4653                         if ((cp->phys.header.launch.l_paddr
4654                             == NCB_SCRIPT_PHYS (np, select))
4655                          && (xpt_path_comp(path, cp->ccb->ccb_h.path) >= 0)) {
4656
4657                                 /* Mark for removal from the start queue */
4658                                 for (i = 1; i < MAX_START; i++) {
4659                                         int idx;
4660
4661                                         idx = np->squeueput - i;
4662                                 
4663                                         if (idx < 0)
4664                                                 idx = MAX_START + idx;
4665                                         if (np->squeue[idx]
4666                                          == CCB_PHYS(cp, phys)) {
4667                                                 np->squeue[idx] =
4668                                                     NCB_SCRIPT_PHYS (np, skip);
4669                                                 if (i > firstskip)
4670                                                         firstskip = i;
4671                                                 break;
4672                                         }
4673                                 }
4674                                 cp->host_status=HS_STALL;
4675                                 ncr_complete (np, cp);
4676                                 count++;
4677                         }
4678                         break;
4679                 default:
4680                         break;
4681                 }
4682                 cp = cp->link_nccb;
4683         }
4684
4685         if (count > 0) {
4686                 int j;
4687                 int bidx;
4688
4689                 /* Compress the start queue */
4690                 j = 0;
4691                 bidx = np->squeueput;
4692                 i = np->squeueput - firstskip;
4693                 if (i < 0)
4694                         i = MAX_START + i;
4695                 for (;;) {
4696
4697                         bidx = i - j;
4698                         if (bidx < 0)
4699                                 bidx = MAX_START + bidx;
4700                         
4701                         if (np->squeue[i] == NCB_SCRIPT_PHYS (np, skip)) {
4702                                 j++;
4703                         } else if (j != 0) {
4704                                 np->squeue[bidx] = np->squeue[i];
4705                                 if (np->squeue[bidx]
4706                                  == NCB_SCRIPT_PHYS(np, idle))
4707                                         break;
4708                         }
4709                         i = (i + 1) % MAX_START;
4710                 }
4711                 np->squeueput = bidx;
4712         }
4713 }
4714
4715 /*==========================================================
4716 **
4717 **
4718 **      Start NCR chip.
4719 **
4720 **
4721 **==========================================================
4722 */
4723
4724 void
4725 ncr_init(ncb_p np, char * msg, u_long code)
4726 {
4727         int     i;
4728
4729         /*
4730         **      Reset chip.
4731         */
4732
4733         OUTB (nc_istat,  SRST);
4734         DELAY (1000);
4735         OUTB (nc_istat, 0);
4736
4737         /*
4738         **      Message.
4739         */
4740
4741         if (msg) printf ("%s: restart (%s).\n", ncr_name (np), msg);
4742
4743         /*
4744         **      Clear Start Queue
4745         */
4746
4747         for (i=0;i<MAX_START;i++)
4748                 np -> squeue [i] = NCB_SCRIPT_PHYS (np, idle);
4749
4750         /*
4751         **      Start at first entry.
4752         */
4753
4754         np->squeueput = 0;
4755         WRITESCRIPT(startpos[0], NCB_SCRIPTH_PHYS (np, tryloop));
4756         WRITESCRIPT(start0  [0], SCR_INT ^ IFFALSE (0));
4757
4758         /*
4759         **      Wakeup all pending jobs.
4760         */
4761
4762         ncr_wakeup (np, code);
4763
4764         /*
4765         **      Init chip.
4766         */
4767
4768         OUTB (nc_istat,  0x00   );      /*  Remove Reset, abort ...          */
4769         OUTB (nc_scntl0, 0xca   );      /*  full arb., ena parity, par->ATN  */
4770         OUTB (nc_scntl1, 0x00   );      /*  odd parity, and remove CRST!!    */
4771         ncr_selectclock(np, np->rv_scntl3); /* Select SCSI clock             */
4772         OUTB (nc_scid  , RRE|np->myaddr);/*  host adapter SCSI address       */
4773         OUTW (nc_respid, 1ul<<np->myaddr);/*  id to respond to               */
4774         OUTB (nc_istat , SIGP   );      /*  Signal Process                   */
4775         OUTB (nc_dmode , np->rv_dmode); /* XXX modify burstlen ??? */
4776         OUTB (nc_dcntl , np->rv_dcntl);
4777         OUTB (nc_ctest3, np->rv_ctest3);
4778         OUTB (nc_ctest5, np->rv_ctest5);
4779         OUTB (nc_ctest4, np->rv_ctest4);/*  enable master parity checking    */
4780         OUTB (nc_stest2, np->rv_stest2|EXT); /* Extended Sreq/Sack filtering */
4781         OUTB (nc_stest3, TE     );      /*  TolerANT enable                  */
4782         OUTB (nc_stime0, 0x0b   );      /*  HTH = disabled, STO = 0.1 sec.   */
4783
4784         if (bootverbose >= 2) {
4785                 printf ("\tACTUAL values:SCNTL3:%02x DMODE:%02x  DCNTL:%02x\n",
4786                         np->rv_scntl3, np->rv_dmode, np->rv_dcntl);
4787                 printf ("\t              CTEST3:%02x CTEST4:%02x CTEST5:%02x\n",
4788                         np->rv_ctest3, np->rv_ctest4, np->rv_ctest5);
4789         }
4790
4791         /*
4792         **    Enable GPIO0 pin for writing if LED support.
4793         */
4794
4795         if (np->features & FE_LED0) {
4796                 OUTOFFB (nc_gpcntl, 0x01);
4797         }
4798
4799         /*
4800         **      Fill in target structure.
4801         */
4802         for (i=0;i<MAX_TARGET;i++) {
4803                 tcb_p tp = &np->target[i];
4804
4805                 tp->tinfo.sval    = 0;
4806                 tp->tinfo.wval    = np->rv_scntl3;
4807
4808                 tp->tinfo.current.period = 0;
4809                 tp->tinfo.current.offset = 0;
4810                 tp->tinfo.current.width = MSG_EXT_WDTR_BUS_8_BIT;
4811         }
4812
4813         /*
4814         **      enable ints
4815         */
4816
4817         OUTW (nc_sien , STO|HTH|MA|SGE|UDC|RST);
4818         OUTB (nc_dien , MDPE|BF|ABRT|SSI|SIR|IID);
4819
4820         /*
4821         **    Start script processor.
4822         */
4823
4824         OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, start));
4825
4826         /*
4827          * Notify the XPT of the event
4828          */
4829         if (code == HS_RESET)
4830                 xpt_async(AC_BUS_RESET, np->path, NULL);
4831 }
4832
4833 static void
4834 ncr_poll(struct cam_sim *sim)
4835 {       
4836         ncr_intr(cam_sim_softc(sim));  
4837 }
4838
4839
4840 /*==========================================================
4841 **
4842 **      Get clock factor and sync divisor for a given 
4843 **      synchronous factor period.
4844 **      Returns the clock factor (in sxfer) and scntl3 
4845 **      synchronous divisor field.
4846 **
4847 **==========================================================
4848 */
4849
4850 static void ncr_getsync(ncb_p np, u_char sfac, u_char *fakp, u_char *scntl3p)
4851 {
4852         u_long  clk = np->clock_khz;    /* SCSI clock frequency in kHz  */
4853         int     div = np->clock_divn;   /* Number of divisors supported */
4854         u_long  fak;                    /* Sync factor in sxfer         */
4855         u_long  per;                    /* Period in tenths of ns       */
4856         u_long  kpc;                    /* (per * clk)                  */
4857
4858         /*
4859         **      Compute the synchronous period in tenths of nano-seconds
4860         */
4861         if      (sfac <= 10)    per = 250;
4862         else if (sfac == 11)    per = 303;
4863         else if (sfac == 12)    per = 500;
4864         else                    per = 40 * sfac;
4865
4866         /*
4867         **      Look for the greatest clock divisor that allows an 
4868         **      input speed faster than the period.
4869         */
4870         kpc = per * clk;
4871         while (--div >= 0)
4872                 if (kpc >= (div_10M[div] * 4)) break;
4873
4874         /*
4875         **      Calculate the lowest clock factor that allows an output 
4876         **      speed not faster than the period.
4877         */
4878         fak = (kpc - 1) / div_10M[div] + 1;
4879
4880 #if 0   /* You can #if 1 if you think this optimization is usefull */
4881
4882         per = (fak * div_10M[div]) / clk;
4883
4884         /*
4885         **      Why not to try the immediate lower divisor and to choose 
4886         **      the one that allows the fastest output speed ?
4887         **      We dont want input speed too much greater than output speed.
4888         */
4889         if (div >= 1 && fak < 6) {
4890                 u_long fak2, per2;
4891                 fak2 = (kpc - 1) / div_10M[div-1] + 1;
4892                 per2 = (fak2 * div_10M[div-1]) / clk;
4893                 if (per2 < per && fak2 <= 6) {
4894                         fak = fak2;
4895                         per = per2;
4896                         --div;
4897                 }
4898         }
4899 #endif
4900
4901         if (fak < 4) fak = 4;   /* Should never happen, too bad ... */
4902
4903         /*
4904         **      Compute and return sync parameters for the ncr
4905         */
4906         *fakp           = fak - 4;
4907         *scntl3p        = ((div+1) << 4) + (sfac < 25 ? 0x80 : 0);
4908 }
4909
4910 /*==========================================================
4911 **
4912 **      Switch sync mode for current job and its target
4913 **
4914 **==========================================================
4915 */
4916
4917 static void
4918 ncr_setsync(ncb_p np, nccb_p cp, u_char scntl3, u_char sxfer, u_char period)
4919 {
4920         union   ccb *ccb;
4921         struct  ccb_trans_settings neg; 
4922         tcb_p   tp;
4923         int     div;
4924         u_int   target = INB (nc_sdid) & 0x0f;
4925         u_int   period_10ns;
4926
4927         assert (cp);
4928         if (!cp) return;
4929
4930         ccb = cp->ccb;
4931         assert (ccb);
4932         if (!ccb) return;
4933         assert (target == ccb->ccb_h.target_id);
4934
4935         tp = &np->target[target];
4936
4937         if (!scntl3 || !(sxfer & 0x1f))
4938                 scntl3 = np->rv_scntl3;
4939         scntl3 = (scntl3 & 0xf0) | (tp->tinfo.wval & EWS)
4940                | (np->rv_scntl3 & 0x07);
4941
4942         /*
4943         **      Deduce the value of controller sync period from scntl3.
4944         **      period is in tenths of nano-seconds.
4945         */
4946
4947         div = ((scntl3 >> 4) & 0x7);
4948         if ((sxfer & 0x1f) && div)
4949                 period_10ns =
4950                     (((sxfer>>5)+4)*div_10M[div-1])/np->clock_khz;
4951         else
4952                 period_10ns = 0;
4953
4954         tp->tinfo.goal.period = period;
4955         tp->tinfo.goal.offset = sxfer & 0x1f;
4956         tp->tinfo.current.period = period;
4957         tp->tinfo.current.offset = sxfer & 0x1f;
4958
4959         /*
4960         **       Stop there if sync parameters are unchanged
4961         */
4962         if (tp->tinfo.sval == sxfer && tp->tinfo.wval == scntl3) return;
4963         tp->tinfo.sval = sxfer;
4964         tp->tinfo.wval = scntl3;
4965
4966         if (sxfer & 0x1f) {
4967                 /*
4968                 **  Disable extended Sreq/Sack filtering
4969                 */
4970                 if (period_10ns <= 2000) OUTOFFB (nc_stest2, EXT);
4971         }
4972
4973         /*
4974         ** Tell the SCSI layer about the
4975         ** new transfer parameters.
4976         */
4977         neg.sync_period = period;
4978         neg.sync_offset = sxfer & 0x1f;
4979         neg.valid = CCB_TRANS_SYNC_RATE_VALID
4980                 | CCB_TRANS_SYNC_OFFSET_VALID;
4981         xpt_setup_ccb(&neg.ccb_h, ccb->ccb_h.path,
4982                       /*priority*/1);
4983         xpt_async(AC_TRANSFER_NEG, ccb->ccb_h.path, &neg);
4984         
4985         /*
4986         **      set actual value and sync_status
4987         */
4988         OUTB (nc_sxfer, sxfer);
4989         np->sync_st = sxfer;
4990         OUTB (nc_scntl3, scntl3);
4991         np->wide_st = scntl3;
4992
4993         /*
4994         **      patch ALL nccbs of this target.
4995         */
4996         for (cp = np->link_nccb; cp; cp = cp->link_nccb) {
4997                 if (!cp->ccb) continue;
4998                 if (cp->ccb->ccb_h.target_id != target) continue;
4999                 cp->sync_status = sxfer;
5000                 cp->wide_status = scntl3;
5001         };
5002 }
5003
5004 /*==========================================================
5005 **
5006 **      Switch wide mode for current job and its target
5007 **      SCSI specs say: a SCSI device that accepts a WDTR 
5008 **      message shall reset the synchronous agreement to 
5009 **      asynchronous mode.
5010 **
5011 **==========================================================
5012 */
5013
5014 static void ncr_setwide (ncb_p np, nccb_p cp, u_char wide, u_char ack)
5015 {
5016         union   ccb *ccb;
5017         struct  ccb_trans_settings neg;         
5018         u_int   target = INB (nc_sdid) & 0x0f;
5019         tcb_p   tp;
5020         u_char  scntl3;
5021         u_char  sxfer;
5022
5023         assert (cp);
5024         if (!cp) return;
5025
5026         ccb = cp->ccb;
5027         assert (ccb);
5028         if (!ccb) return;
5029         assert (target == ccb->ccb_h.target_id);
5030
5031         tp = &np->target[target];
5032         tp->tinfo.current.width = wide;
5033         tp->tinfo.goal.width = wide;
5034         tp->tinfo.current.period = 0;
5035         tp->tinfo.current.offset = 0;
5036
5037         scntl3 = (tp->tinfo.wval & (~EWS)) | (wide ? EWS : 0);
5038
5039         sxfer = ack ? 0 : tp->tinfo.sval;
5040
5041         /*
5042         **       Stop there if sync/wide parameters are unchanged
5043         */
5044         if (tp->tinfo.sval == sxfer && tp->tinfo.wval == scntl3) return;
5045         tp->tinfo.sval = sxfer;
5046         tp->tinfo.wval = scntl3;
5047
5048         /* Tell the SCSI layer about the new transfer params */
5049         neg.bus_width = (scntl3 & EWS) ? MSG_EXT_WDTR_BUS_16_BIT
5050                                        : MSG_EXT_WDTR_BUS_8_BIT;
5051         neg.sync_period = 0;
5052         neg.sync_offset = 0;
5053         neg.valid = CCB_TRANS_BUS_WIDTH_VALID
5054                   | CCB_TRANS_SYNC_RATE_VALID
5055                   | CCB_TRANS_SYNC_OFFSET_VALID;
5056         xpt_setup_ccb(&neg.ccb_h, ccb->ccb_h.path,
5057                       /*priority*/1);
5058         xpt_async(AC_TRANSFER_NEG, ccb->ccb_h.path, &neg);      
5059
5060         /*
5061         **      set actual value and sync_status
5062         */
5063         OUTB (nc_sxfer, sxfer);
5064         np->sync_st = sxfer;
5065         OUTB (nc_scntl3, scntl3);
5066         np->wide_st = scntl3;
5067
5068         /*
5069         **      patch ALL nccbs of this target.
5070         */
5071         for (cp = np->link_nccb; cp; cp = cp->link_nccb) {
5072                 if (!cp->ccb) continue;
5073                 if (cp->ccb->ccb_h.target_id != target) continue;
5074                 cp->sync_status = sxfer;
5075                 cp->wide_status = scntl3;
5076         };
5077 }
5078
5079 /*==========================================================
5080 **
5081 **
5082 **      ncr timeout handler.
5083 **
5084 **
5085 **==========================================================
5086 **
5087 **      Misused to keep the driver running when
5088 **      interrupts are not configured correctly.
5089 **
5090 **----------------------------------------------------------
5091 */
5092
5093 static void
5094 ncr_timeout (void *arg)
5095 {
5096         ncb_p   np = arg;
5097         time_t  thistime = time_second;
5098         ticks_t step  = np->ticks;
5099         u_long  count = 0;
5100         long signed   t;
5101         nccb_p cp;
5102
5103         if (np->lasttime != thistime) {
5104                 /*
5105                 **      block ncr interrupts
5106                 */
5107                 int oldspl = splcam();
5108                 np->lasttime = thistime;
5109
5110                 /*----------------------------------------------------
5111                 **
5112                 **      handle ncr chip timeouts
5113                 **
5114                 **      Assumption:
5115                 **      We have a chance to arbitrate for the
5116                 **      SCSI bus at least every 10 seconds.
5117                 **
5118                 **----------------------------------------------------
5119                 */
5120
5121                 t = thistime - np->heartbeat;
5122
5123                 if (t<2) np->latetime=0; else np->latetime++;
5124
5125                 if (np->latetime>2) {
5126                         /*
5127                         **      If there are no requests, the script
5128                         **      processor will sleep on SEL_WAIT_RESEL.
5129                         **      But we have to check whether it died.
5130                         **      Let's try to wake it up.
5131                         */
5132                         OUTB (nc_istat, SIGP);
5133                 };
5134
5135                 /*----------------------------------------------------
5136                 **
5137                 **      handle nccb timeouts
5138                 **
5139                 **----------------------------------------------------
5140                 */
5141
5142                 for (cp=np->link_nccb; cp; cp=cp->link_nccb) {
5143                         /*
5144                         **      look for timed out nccbs.
5145                         */
5146                         if (!cp->host_status) continue;
5147                         count++;
5148                         if (cp->tlimit > thistime) continue;
5149
5150                         /*
5151                         **      Disable reselect.
5152                         **      Remove it from startqueue.
5153                         */
5154                         cp->jump_nccb.l_cmd = (SCR_JUMP);
5155                         if (cp->phys.header.launch.l_paddr ==
5156                                 NCB_SCRIPT_PHYS (np, select)) {
5157                                 printf ("%s: timeout nccb=%p (skip)\n",
5158                                         ncr_name (np), cp);
5159                                 cp->phys.header.launch.l_paddr
5160                                 = NCB_SCRIPT_PHYS (np, skip);
5161                         };
5162
5163                         switch (cp->host_status) {
5164
5165                         case HS_BUSY:
5166                         case HS_NEGOTIATE:
5167                                 /* fall through */
5168                         case HS_DISCONNECT:
5169                                 cp->host_status=HS_TIMEOUT;
5170                         };
5171                         cp->tag = 0;
5172
5173                         /*
5174                         **      wakeup this nccb.
5175                         */
5176                         ncr_complete (np, cp);
5177                 };
5178                 splx (oldspl);
5179         }
5180
5181         np->timeout_ch =
5182                 timeout (ncr_timeout, (caddr_t) np, step ? step : 1);
5183
5184         if (INB(nc_istat) & (INTF|SIP|DIP)) {
5185
5186                 /*
5187                 **      Process pending interrupts.
5188                 */
5189
5190                 int     oldspl  = splcam();
5191                 if (DEBUG_FLAGS & DEBUG_TINY) printf ("{");
5192                 ncr_exception (np);
5193                 if (DEBUG_FLAGS & DEBUG_TINY) printf ("}");
5194                 splx (oldspl);
5195         };
5196 }
5197
5198 /*==========================================================
5199 **
5200 **      log message for real hard errors
5201 **
5202 **      "ncr0 targ 0?: ERROR (ds:si) (so-si-sd) (sxfer/scntl3) @ name (dsp:dbc)."
5203 **      "             reg: r0 r1 r2 r3 r4 r5 r6 ..... rf."
5204 **
5205 **      exception register:
5206 **              ds:     dstat
5207 **              si:     sist
5208 **
5209 **      SCSI bus lines:
5210 **              so:     control lines as driver by NCR.
5211 **              si:     control lines as seen by NCR.
5212 **              sd:     scsi data lines as seen by NCR.
5213 **
5214 **      wide/fastmode:
5215 **              sxfer:  (see the manual)
5216 **              scntl3: (see the manual)
5217 **
5218 **      current script command:
5219 **              dsp:    script adress (relative to start of script).
5220 **              dbc:    first word of script command.
5221 **
5222 **      First 16 register of the chip:
5223 **              r0..rf
5224 **
5225 **==========================================================
5226 */
5227
5228 static void ncr_log_hard_error(ncb_p np, u_short sist, u_char dstat)
5229 {
5230         u_int32_t dsp;
5231         int     script_ofs;
5232         int     script_size;
5233         char    *script_name;
5234         u_char  *script_base;
5235         int     i;
5236
5237         dsp     = INL (nc_dsp);
5238
5239         if (np->p_script < dsp && 
5240             dsp <= np->p_script + sizeof(struct script)) {
5241                 script_ofs      = dsp - np->p_script;
5242                 script_size     = sizeof(struct script);
5243                 script_base     = (u_char *) np->script;
5244                 script_name     = "script";
5245         }
5246         else if (np->p_scripth < dsp && 
5247                  dsp <= np->p_scripth + sizeof(struct scripth)) {
5248                 script_ofs      = dsp - np->p_scripth;
5249                 script_size     = sizeof(struct scripth);
5250                 script_base     = (u_char *) np->scripth;
5251                 script_name     = "scripth";
5252         } else {
5253                 script_ofs      = dsp;
5254                 script_size     = 0;
5255                 script_base     = 0;
5256                 script_name     = "mem";
5257         }
5258
5259         printf ("%s:%d: ERROR (%x:%x) (%x-%x-%x) (%x/%x) @ (%s %x:%08x).\n",
5260                 ncr_name (np), (unsigned)INB (nc_sdid)&0x0f, dstat, sist,
5261                 (unsigned)INB (nc_socl), (unsigned)INB (nc_sbcl), (unsigned)INB (nc_sbdl),
5262                 (unsigned)INB (nc_sxfer),(unsigned)INB (nc_scntl3), script_name, script_ofs,
5263                 (unsigned)INL (nc_dbc));
5264
5265         if (((script_ofs & 3) == 0) &&
5266             (unsigned)script_ofs < script_size) {
5267                 printf ("%s: script cmd = %08x\n", ncr_name(np),
5268                         (int)READSCRIPT_OFF(script_base, script_ofs));
5269         }
5270
5271         printf ("%s: regdump:", ncr_name(np));
5272         for (i=0; i<16;i++)
5273             printf (" %02x", (unsigned)INB_OFF(i));
5274         printf (".\n");
5275 }
5276
5277 /*==========================================================
5278 **
5279 **
5280 **      ncr chip exception handler.
5281 **
5282 **
5283 **==========================================================
5284 */
5285
5286 void ncr_exception (ncb_p np)
5287 {
5288         u_char  istat, dstat;
5289         u_short sist;
5290
5291         /*
5292         **      interrupt on the fly ?
5293         */
5294         while ((istat = INB (nc_istat)) & INTF) {
5295                 if (DEBUG_FLAGS & DEBUG_TINY) printf ("F ");
5296                 OUTB (nc_istat, INTF);
5297                 np->profile.num_fly++;
5298                 ncr_wakeup (np, 0);
5299         };
5300         if (!(istat & (SIP|DIP))) {
5301                 return;
5302         }
5303
5304         /*
5305         **      Steinbach's Guideline for Systems Programming:
5306         **      Never test for an error condition you don't know how to handle.
5307         */
5308
5309         sist  = (istat & SIP) ? INW (nc_sist)  : 0;
5310         dstat = (istat & DIP) ? INB (nc_dstat) : 0;
5311         np->profile.num_int++;
5312
5313         if (DEBUG_FLAGS & DEBUG_TINY)
5314                 printf ("<%d|%x:%x|%x:%x>",
5315                         INB(nc_scr0),
5316                         dstat,sist,
5317                         (unsigned)INL(nc_dsp),
5318                         (unsigned)INL(nc_dbc));
5319         if ((dstat==DFE) && (sist==PAR)) return;
5320
5321 /*==========================================================
5322 **
5323 **      First the normal cases.
5324 **
5325 **==========================================================
5326 */
5327         /*-------------------------------------------
5328         **      SCSI reset
5329         **-------------------------------------------
5330         */
5331
5332         if (sist & RST) {
5333                 ncr_init (np, bootverbose ? "scsi reset" : NULL, HS_RESET);
5334                 return;
5335         };
5336
5337         /*-------------------------------------------
5338         **      selection timeout
5339         **
5340         **      IID excluded from dstat mask!
5341         **      (chip bug)
5342         **-------------------------------------------
5343         */
5344
5345         if ((sist  & STO) &&
5346                 !(sist  & (GEN|HTH|MA|SGE|UDC|RST|PAR)) &&
5347                 !(dstat & (MDPE|BF|ABRT|SIR))) {
5348                 ncr_int_sto (np);
5349                 return;
5350         };
5351
5352         /*-------------------------------------------
5353         **      Phase mismatch.
5354         **-------------------------------------------
5355         */
5356
5357         if ((sist  & MA) &&
5358                 !(sist  & (STO|GEN|HTH|SGE|UDC|RST|PAR)) &&
5359                 !(dstat & (MDPE|BF|ABRT|SIR|IID))) {
5360                 ncr_int_ma (np, dstat);
5361                 return;
5362         };
5363
5364         /*----------------------------------------
5365         **      move command with length 0
5366         **----------------------------------------
5367         */
5368
5369         if ((dstat & IID) &&
5370                 !(sist  & (STO|GEN|HTH|MA|SGE|UDC|RST|PAR)) &&
5371                 !(dstat & (MDPE|BF|ABRT|SIR)) &&
5372                 ((INL(nc_dbc) & 0xf8000000) == SCR_MOVE_TBL)) {
5373                 /*
5374                 **      Target wants more data than available.
5375                 **      The "no_data" script will do it.
5376                 */
5377                 OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, no_data));
5378                 return;
5379         };
5380
5381         /*-------------------------------------------
5382         **      Programmed interrupt
5383         **-------------------------------------------
5384         */
5385
5386         if ((dstat & SIR) &&
5387                 !(sist  & (STO|GEN|HTH|MA|SGE|UDC|RST|PAR)) &&
5388                 !(dstat & (MDPE|BF|ABRT|IID)) &&
5389                 (INB(nc_dsps) <= SIR_MAX)) {
5390                 ncr_int_sir (np);
5391                 return;
5392         };
5393
5394         /*========================================
5395         **      log message for real hard errors
5396         **========================================
5397         */
5398
5399         ncr_log_hard_error(np, sist, dstat);
5400
5401         /*========================================
5402         **      do the register dump
5403         **========================================
5404         */
5405
5406         if (time_second - np->regtime > 10) {
5407                 int i;
5408                 np->regtime = time_second;
5409                 for (i=0; i<sizeof(np->regdump); i++)
5410                         ((volatile char*)&np->regdump)[i] = INB_OFF(i);
5411                 np->regdump.nc_dstat = dstat;
5412                 np->regdump.nc_sist  = sist;
5413         };
5414
5415
5416         /*----------------------------------------
5417         **      clean up the dma fifo
5418         **----------------------------------------
5419         */
5420
5421         if ( (INB(nc_sstat0) & (ILF|ORF|OLF)   ) ||
5422              (INB(nc_sstat1) & (FF3210) ) ||
5423              (INB(nc_sstat2) & (ILF1|ORF1|OLF1)) ||     /* wide .. */
5424              !(dstat & DFE)) {
5425                 printf ("%s: have to clear fifos.\n", ncr_name (np));
5426                 OUTB (nc_stest3, TE|CSF);       /* clear scsi fifo */
5427                 OUTB (nc_ctest3, np->rv_ctest3 | CLF);
5428                                                 /* clear dma fifo  */
5429         }
5430
5431         /*----------------------------------------
5432         **      handshake timeout
5433         **----------------------------------------
5434         */
5435
5436         if (sist & HTH) {
5437                 printf ("%s: handshake timeout\n", ncr_name(np));
5438                 OUTB (nc_scntl1, CRST);
5439                 DELAY (1000);
5440                 OUTB (nc_scntl1, 0x00);
5441                 OUTB (nc_scr0, HS_FAIL);
5442                 OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, cleanup));
5443                 return;
5444         }
5445
5446         /*----------------------------------------
5447         **      unexpected disconnect
5448         **----------------------------------------
5449         */
5450
5451         if ((sist  & UDC) &&
5452                 !(sist  & (STO|GEN|HTH|MA|SGE|RST|PAR)) &&
5453                 !(dstat & (MDPE|BF|ABRT|SIR|IID))) {
5454                 OUTB (nc_scr0, HS_UNEXPECTED);
5455                 OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, cleanup));
5456                 return;
5457         };
5458
5459         /*----------------------------------------
5460         **      cannot disconnect
5461         **----------------------------------------
5462         */
5463
5464         if ((dstat & IID) &&
5465                 !(sist  & (STO|GEN|HTH|MA|SGE|UDC|RST|PAR)) &&
5466                 !(dstat & (MDPE|BF|ABRT|SIR)) &&
5467                 ((INL(nc_dbc) & 0xf8000000) == SCR_WAIT_DISC)) {
5468                 /*
5469                 **      Unexpected data cycle while waiting for disconnect.
5470                 */
5471                 if (INB(nc_sstat2) & LDSC) {
5472                         /*
5473                         **      It's an early reconnect.
5474                         **      Let's continue ...
5475                         */
5476                         OUTB (nc_dcntl, np->rv_dcntl | STD);
5477                         /*
5478                         **      info message
5479                         */
5480                         printf ("%s: INFO: LDSC while IID.\n",
5481                                 ncr_name (np));
5482                         return;
5483                 };
5484                 printf ("%s: target %d doesn't release the bus.\n",
5485                         ncr_name (np), INB (nc_sdid)&0x0f);
5486                 /*
5487                 **      return without restarting the NCR.
5488                 **      timeout will do the real work.
5489                 */
5490                 return;
5491         };
5492
5493         /*----------------------------------------
5494         **      single step
5495         **----------------------------------------
5496         */
5497
5498         if ((dstat & SSI) &&
5499                 !(sist  & (STO|GEN|HTH|MA|SGE|UDC|RST|PAR)) &&
5500                 !(dstat & (MDPE|BF|ABRT|SIR|IID))) {
5501                 OUTB (nc_dcntl, np->rv_dcntl | STD);
5502                 return;
5503         };
5504
5505 /*
5506 **      @RECOVER@ HTH, SGE, ABRT.
5507 **
5508 **      We should try to recover from these interrupts.
5509 **      They may occur if there are problems with synch transfers, or 
5510 **      if targets are switched on or off while the driver is running.
5511 */
5512
5513         if (sist & SGE) {
5514                 /* clear scsi offsets */
5515                 OUTB (nc_ctest3, np->rv_ctest3 | CLF);
5516         }
5517
5518         /*
5519         **      Freeze controller to be able to read the messages.
5520         */
5521
5522         if (DEBUG_FLAGS & DEBUG_FREEZE) {
5523                 int i;
5524                 unsigned char val;
5525                 for (i=0; i<0x60; i++) {
5526                         switch (i%16) {
5527
5528                         case 0:
5529                                 printf ("%s: reg[%d0]: ",
5530                                         ncr_name(np),i/16);
5531                                 break;
5532                         case 4:
5533                         case 8:
5534                         case 12:
5535                                 printf (" ");
5536                                 break;
5537                         };
5538                         val = bus_space_read_1(np->bst, np->bsh, i);
5539                         printf (" %x%x", val/16, val%16);
5540                         if (i%16==15) printf (".\n");
5541                 };
5542
5543                 untimeout (ncr_timeout, (caddr_t) np, np->timeout_ch);
5544
5545                 printf ("%s: halted!\n", ncr_name(np));
5546                 /*
5547                 **      don't restart controller ...
5548                 */
5549                 OUTB (nc_istat,  SRST);
5550                 return;
5551         };
5552
5553 #ifdef NCR_FREEZE
5554         /*
5555         **      Freeze system to be able to read the messages.
5556         */
5557         printf ("ncr: fatal error: system halted - press reset to reboot ...");
5558         (void) splhigh();
5559         for (;;);
5560 #endif
5561
5562         /*
5563         **      sorry, have to kill ALL jobs ...
5564         */
5565
5566         ncr_init (np, "fatal error", HS_FAIL);
5567 }
5568
5569 /*==========================================================
5570 **
5571 **      ncr chip exception handler for selection timeout
5572 **
5573 **==========================================================
5574 **
5575 **      There seems to be a bug in the 53c810.
5576 **      Although a STO-Interrupt is pending,
5577 **      it continues executing script commands.
5578 **      But it will fail and interrupt (IID) on
5579 **      the next instruction where it's looking
5580 **      for a valid phase.
5581 **
5582 **----------------------------------------------------------
5583 */
5584
5585 void ncr_int_sto (ncb_p np)
5586 {
5587         u_long dsa, scratcha, diff;
5588         nccb_p cp;
5589         if (DEBUG_FLAGS & DEBUG_TINY) printf ("T");
5590
5591         /*
5592         **      look for nccb and set the status.
5593         */
5594
5595         dsa = INL (nc_dsa);
5596         cp = np->link_nccb;
5597         while (cp && (CCB_PHYS (cp, phys) != dsa))
5598                 cp = cp->link_nccb;
5599
5600         if (cp) {
5601                 cp-> host_status = HS_SEL_TIMEOUT;
5602                 ncr_complete (np, cp);
5603         };
5604
5605         /*
5606         **      repair start queue
5607         */
5608
5609         scratcha = INL (nc_scratcha);
5610         diff = scratcha - NCB_SCRIPTH_PHYS (np, tryloop);
5611
5612 /*      assert ((diff <= MAX_START * 20) && !(diff % 20));*/
5613
5614         if ((diff <= MAX_START * 20) && !(diff % 20)) {
5615                 WRITESCRIPT(startpos[0], scratcha);
5616                 OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, start));
5617                 return;
5618         };
5619         ncr_init (np, "selection timeout", HS_FAIL);
5620 }
5621
5622 /*==========================================================
5623 **
5624 **
5625 **      ncr chip exception handler for phase errors.
5626 **
5627 **
5628 **==========================================================
5629 **
5630 **      We have to construct a new transfer descriptor,
5631 **      to transfer the rest of the current block.
5632 **
5633 **----------------------------------------------------------
5634 */
5635
5636 static void ncr_int_ma (ncb_p np, u_char dstat)
5637 {
5638         u_int32_t       dbc;
5639         u_int32_t       rest;
5640         u_int32_t       dsa;
5641         u_int32_t       dsp;
5642         u_int32_t       nxtdsp;
5643         volatile void   *vdsp_base;
5644         size_t          vdsp_off;
5645         u_int32_t       oadr, olen;
5646         u_int32_t       *tblp, *newcmd;
5647         u_char  cmd, sbcl, ss0, ss2, ctest5;
5648         u_short delta;
5649         nccb_p  cp;
5650
5651         dsp = INL (nc_dsp);
5652         dsa = INL (nc_dsa);
5653         dbc = INL (nc_dbc);
5654         ss0 = INB (nc_sstat0);
5655         ss2 = INB (nc_sstat2);
5656         sbcl= INB (nc_sbcl);
5657
5658         cmd = dbc >> 24;
5659         rest= dbc & 0xffffff;
5660
5661         ctest5 = (np->rv_ctest5 & DFS) ? INB (nc_ctest5) : 0;
5662         if (ctest5 & DFS)
5663                 delta=(((ctest5<<8) | (INB (nc_dfifo) & 0xff)) - rest) & 0x3ff;
5664         else
5665                 delta=(INB (nc_dfifo) - rest) & 0x7f;
5666
5667
5668         /*
5669         **      The data in the dma fifo has not been transfered to
5670         **      the target -> add the amount to the rest
5671         **      and clear the data.
5672         **      Check the sstat2 register in case of wide transfer.
5673         */
5674
5675         if (!(dstat & DFE)) rest += delta;
5676         if (ss0 & OLF) rest++;
5677         if (ss0 & ORF) rest++;
5678         if (INB(nc_scntl3) & EWS) {
5679                 if (ss2 & OLF1) rest++;
5680                 if (ss2 & ORF1) rest++;
5681         };
5682         OUTB (nc_ctest3, np->rv_ctest3 | CLF);  /* clear dma fifo  */
5683         OUTB (nc_stest3, TE|CSF);               /* clear scsi fifo */
5684
5685         /*
5686         **      locate matching cp
5687         */
5688         cp = np->link_nccb;
5689         while (cp && (CCB_PHYS (cp, phys) != dsa))
5690                 cp = cp->link_nccb;
5691
5692         if (!cp) {
5693             printf ("%s: SCSI phase error fixup: CCB already dequeued (%p)\n", 
5694                     ncr_name (np), (void *) np->header.cp);
5695             return;
5696         }
5697         if (cp != np->header.cp) {
5698             printf ("%s: SCSI phase error fixup: CCB address mismatch "
5699                     "(%p != %p) np->nccb = %p\n", 
5700                     ncr_name (np), (void *)cp, (void *)np->header.cp,
5701                     (void *)np->link_nccb);
5702 /*          return;*/
5703         }
5704
5705         /*
5706         **      find the interrupted script command,
5707         **      and the address at which to continue.
5708         */
5709
5710         if (dsp == vtophys (&cp->patch[2])) {
5711                 vdsp_base = cp;
5712                 vdsp_off = offsetof(struct nccb, patch[0]);
5713                 nxtdsp = READSCRIPT_OFF(vdsp_base, vdsp_off + 3*4);
5714         } else if (dsp == vtophys (&cp->patch[6])) {
5715                 vdsp_base = cp;
5716                 vdsp_off = offsetof(struct nccb, patch[4]);
5717                 nxtdsp = READSCRIPT_OFF(vdsp_base, vdsp_off + 3*4);
5718         } else if (dsp > np->p_script &&
5719                    dsp <= np->p_script + sizeof(struct script)) {
5720                 vdsp_base = np->script;
5721                 vdsp_off = dsp - np->p_script - 8;
5722                 nxtdsp = dsp;
5723         } else {
5724                 vdsp_base = np->scripth;
5725                 vdsp_off = dsp - np->p_scripth - 8;
5726                 nxtdsp = dsp;
5727         };
5728
5729         /*
5730         **      log the information
5731         */
5732         if (DEBUG_FLAGS & (DEBUG_TINY|DEBUG_PHASE)) {
5733                 printf ("P%x%x ",cmd&7, sbcl&7);
5734                 printf ("RL=%d D=%d SS0=%x ",
5735                         (unsigned) rest, (unsigned) delta, ss0);
5736         };
5737         if (DEBUG_FLAGS & DEBUG_PHASE) {
5738                 printf ("\nCP=%p CP2=%p DSP=%x NXT=%x VDSP=%p CMD=%x ",
5739                         cp, np->header.cp,
5740                         dsp,
5741                         nxtdsp, (volatile char*)vdsp_base+vdsp_off, cmd);
5742         };
5743
5744         /*
5745         **      get old startaddress and old length.
5746         */
5747
5748         oadr = READSCRIPT_OFF(vdsp_base, vdsp_off + 1*4);
5749
5750         if (cmd & 0x10) {       /* Table indirect */
5751                 tblp = (u_int32_t *) ((char*) &cp->phys + oadr);
5752                 olen = tblp[0];
5753                 oadr = tblp[1];
5754         } else {
5755                 tblp = (u_int32_t *) 0;
5756                 olen = READSCRIPT_OFF(vdsp_base, vdsp_off) & 0xffffff;
5757         };
5758
5759         if (DEBUG_FLAGS & DEBUG_PHASE) {
5760                 printf ("OCMD=%x\nTBLP=%p OLEN=%lx OADR=%lx\n",
5761                         (unsigned) (READSCRIPT_OFF(vdsp_base, vdsp_off) >> 24),
5762                         (void *) tblp,
5763                         (u_long) olen,
5764                         (u_long) oadr);
5765         };
5766
5767         /*
5768         **      if old phase not dataphase, leave here.
5769         */
5770
5771         if (cmd != (READSCRIPT_OFF(vdsp_base, vdsp_off) >> 24)) {
5772                 PRINT_ADDR(cp->ccb);
5773                 printf ("internal error: cmd=%02x != %02x=(vdsp[0] >> 24)\n",
5774                         (unsigned)cmd,
5775                         (unsigned)READSCRIPT_OFF(vdsp_base, vdsp_off) >> 24);
5776                 
5777                 return;
5778         }
5779         if (cmd & 0x06) {
5780                 PRINT_ADDR(cp->ccb);
5781                 printf ("phase change %x-%x %d@%08x resid=%d.\n",
5782                         cmd&7, sbcl&7, (unsigned)olen,
5783                         (unsigned)oadr, (unsigned)rest);
5784
5785                 OUTB (nc_dcntl, np->rv_dcntl | STD);
5786                 return;
5787         };
5788
5789         /*
5790         **      choose the correct patch area.
5791         **      if savep points to one, choose the other.
5792         */
5793
5794         newcmd = cp->patch;
5795         if (cp->phys.header.savep == vtophys (newcmd)) newcmd+=4;
5796
5797         /*
5798         **      fillin the commands
5799         */
5800
5801         newcmd[0] = ((cmd & 0x0f) << 24) | rest;
5802         newcmd[1] = oadr + olen - rest;
5803         newcmd[2] = SCR_JUMP;
5804         newcmd[3] = nxtdsp;
5805
5806         if (DEBUG_FLAGS & DEBUG_PHASE) {
5807                 PRINT_ADDR(cp->ccb);
5808                 printf ("newcmd[%d] %x %x %x %x.\n",
5809                         (int)(newcmd - cp->patch),
5810                         (unsigned)newcmd[0],
5811                         (unsigned)newcmd[1],
5812                         (unsigned)newcmd[2],
5813                         (unsigned)newcmd[3]);
5814         }
5815         /*
5816         **      fake the return address (to the patch).
5817         **      and restart script processor at dispatcher.
5818         */
5819         np->profile.num_break++;
5820         OUTL (nc_temp, vtophys (newcmd));
5821         if ((cmd & 7) == 0)
5822                 OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, dispatch));
5823         else
5824                 OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, checkatn));
5825 }
5826
5827 /*==========================================================
5828 **
5829 **
5830 **      ncr chip exception handler for programmed interrupts.
5831 **
5832 **
5833 **==========================================================
5834 */
5835
5836 static int ncr_show_msg (u_char * msg)
5837 {
5838         u_char i;
5839         printf ("%x",*msg);
5840         if (*msg==MSG_EXTENDED) {
5841                 for (i=1;i<8;i++) {
5842                         if (i-1>msg[1]) break;
5843                         printf ("-%x",msg[i]);
5844                 };
5845                 return (i+1);
5846         } else if ((*msg & 0xf0) == 0x20) {
5847                 printf ("-%x",msg[1]);
5848                 return (2);
5849         };
5850         return (1);
5851 }
5852
5853 void ncr_int_sir (ncb_p np)
5854 {
5855         u_char scntl3;
5856         u_char chg, ofs, per, fak, wide;
5857         u_char num = INB (nc_dsps);
5858         nccb_p  cp=0;
5859         u_long  dsa;
5860         u_int   target = INB (nc_sdid) & 0x0f;
5861         tcb_p   tp     = &np->target[target];
5862         int     i;
5863         if (DEBUG_FLAGS & DEBUG_TINY) printf ("I#%d", num);
5864
5865         switch (num) {
5866         case SIR_SENSE_RESTART:
5867         case SIR_STALL_RESTART:
5868                 break;
5869
5870         default:
5871                 /*
5872                 **      lookup the nccb
5873                 */
5874                 dsa = INL (nc_dsa);
5875                 cp = np->link_nccb;
5876                 while (cp && (CCB_PHYS (cp, phys) != dsa))
5877                         cp = cp->link_nccb;
5878
5879                 assert (cp);
5880                 if (!cp)
5881                         goto out;
5882                 assert (cp == np->header.cp);
5883                 if (cp != np->header.cp)
5884                         goto out;
5885         }
5886
5887         switch (num) {
5888
5889 /*--------------------------------------------------------------------
5890 **
5891 **      Processing of interrupted getcc selects
5892 **
5893 **--------------------------------------------------------------------
5894 */
5895
5896         case SIR_SENSE_RESTART:
5897                 /*------------------------------------------
5898                 **      Script processor is idle.
5899                 **      Look for interrupted "check cond"
5900                 **------------------------------------------
5901                 */
5902
5903                 if (DEBUG_FLAGS & DEBUG_RESTART)
5904                         printf ("%s: int#%d",ncr_name (np),num);
5905                 cp = (nccb_p) 0;
5906                 for (i=0; i<MAX_TARGET; i++) {
5907                         if (DEBUG_FLAGS & DEBUG_RESTART) printf (" t%d", i);
5908                         tp = &np->target[i];
5909                         if (DEBUG_FLAGS & DEBUG_RESTART) printf ("+");
5910                         cp = tp->hold_cp;
5911                         if (!cp) continue;
5912                         if (DEBUG_FLAGS & DEBUG_RESTART) printf ("+");
5913                         if ((cp->host_status==HS_BUSY) &&
5914                                 (cp->s_status==SCSI_STATUS_CHECK_COND))
5915                                 break;
5916                         if (DEBUG_FLAGS & DEBUG_RESTART) printf ("- (remove)");
5917                         tp->hold_cp = cp = (nccb_p) 0;
5918                 };
5919
5920                 if (cp) {
5921                         if (DEBUG_FLAGS & DEBUG_RESTART)
5922                                 printf ("+ restart job ..\n");
5923                         OUTL (nc_dsa, CCB_PHYS (cp, phys));
5924                         OUTL (nc_dsp, NCB_SCRIPTH_PHYS (np, getcc));
5925                         return;
5926                 };
5927
5928                 /*
5929                 **      no job, resume normal processing
5930                 */
5931                 if (DEBUG_FLAGS & DEBUG_RESTART) printf (" -- remove trap\n");
5932                 WRITESCRIPT(start0[0], SCR_INT ^ IFFALSE (0));
5933                 break;
5934
5935         case SIR_SENSE_FAILED:
5936                 /*-------------------------------------------
5937                 **      While trying to select for
5938                 **      getting the condition code,
5939                 **      a target reselected us.
5940                 **-------------------------------------------
5941                 */
5942                 if (DEBUG_FLAGS & DEBUG_RESTART) {
5943                         PRINT_ADDR(cp->ccb);
5944                         printf ("in getcc reselect by t%d.\n",
5945                                 INB(nc_ssid) & 0x0f);
5946                 }
5947
5948                 /*
5949                 **      Mark this job
5950                 */
5951                 cp->host_status = HS_BUSY;
5952                 cp->s_status = SCSI_STATUS_CHECK_COND;
5953                 np->target[cp->ccb->ccb_h.target_id].hold_cp = cp;
5954
5955                 /*
5956                 **      And patch code to restart it.
5957                 */
5958                 WRITESCRIPT(start0[0], SCR_INT);
5959                 break;
5960
5961 /*-----------------------------------------------------------------------------
5962 **
5963 **      Was Sie schon immer ueber transfermode negotiation wissen wollten ...
5964 **
5965 **      We try to negotiate sync and wide transfer only after
5966 **      a successfull inquire command. We look at byte 7 of the
5967 **      inquire data to determine the capabilities if the target.
5968 **
5969 **      When we try to negotiate, we append the negotiation message
5970 **      to the identify and (maybe) simple tag message.
5971 **      The host status field is set to HS_NEGOTIATE to mark this
5972 **      situation.
5973 **
5974 **      If the target doesn't answer this message immidiately
5975 **      (as required by the standard), the SIR_NEGO_FAIL interrupt
5976 **      will be raised eventually.
5977 **      The handler removes the HS_NEGOTIATE status, and sets the
5978 **      negotiated value to the default (async / nowide).
5979 **
5980 **      If we receive a matching answer immediately, we check it
5981 **      for validity, and set the values.
5982 **
5983 **      If we receive a Reject message immediately, we assume the
5984 **      negotiation has failed, and fall back to standard values.
5985 **
5986 **      If we receive a negotiation message while not in HS_NEGOTIATE
5987 **      state, it's a target initiated negotiation. We prepare a
5988 **      (hopefully) valid answer, set our parameters, and send back 
5989 **      this answer to the target.
5990 **
5991 **      If the target doesn't fetch the answer (no message out phase),
5992 **      we assume the negotiation has failed, and fall back to default
5993 **      settings.
5994 **
5995 **      When we set the values, we adjust them in all nccbs belonging 
5996 **      to this target, in the controller's register, and in the "phys"
5997 **      field of the controller's struct ncb.
5998 **
5999 **      Possible cases:            hs  sir   msg_in value  send   goto
6000 **      We try try to negotiate:
6001 **      -> target doesnt't msgin   NEG FAIL  noop   defa.  -      dispatch
6002 **      -> target rejected our msg NEG FAIL  reject defa.  -      dispatch
6003 **      -> target answered  (ok)   NEG SYNC  sdtr   set    -      clrack
6004 **      -> target answered (!ok)   NEG SYNC  sdtr   defa.  REJ--->msg_bad
6005 **      -> target answered  (ok)   NEG WIDE  wdtr   set    -      clrack
6006 **      -> target answered (!ok)   NEG WIDE  wdtr   defa.  REJ--->msg_bad
6007 **      -> any other msgin         NEG FAIL  noop   defa.  -      dispatch
6008 **
6009 **      Target tries to negotiate:
6010 **      -> incoming message        --- SYNC  sdtr   set    SDTR   -
6011 **      -> incoming message        --- WIDE  wdtr   set    WDTR   -
6012 **      We sent our answer:
6013 **      -> target doesn't msgout   --- PROTO ?      defa.  -      dispatch
6014 **
6015 **-----------------------------------------------------------------------------
6016 */
6017
6018         case SIR_NEGO_FAILED:
6019                 /*-------------------------------------------------------
6020                 **
6021                 **      Negotiation failed.
6022                 **      Target doesn't send an answer message,
6023                 **      or target rejected our message.
6024                 **
6025                 **      Remove negotiation request.
6026                 **
6027                 **-------------------------------------------------------
6028                 */
6029                 OUTB (HS_PRT, HS_BUSY);
6030
6031                 /* fall through */
6032
6033         case SIR_NEGO_PROTO:
6034                 /*-------------------------------------------------------
6035                 **
6036                 **      Negotiation failed.
6037                 **      Target doesn't fetch the answer message.
6038                 **
6039                 **-------------------------------------------------------
6040                 */
6041
6042                 if (DEBUG_FLAGS & DEBUG_NEGO) {
6043                         PRINT_ADDR(cp->ccb);
6044                         printf ("negotiation failed sir=%x status=%x.\n",
6045                                 num, cp->nego_status);
6046                 };
6047
6048                 /*
6049                 **      any error in negotiation:
6050                 **      fall back to default mode.
6051                 */
6052                 switch (cp->nego_status) {
6053
6054                 case NS_SYNC:
6055                         ncr_setsync (np, cp, 0, 0xe0, 0);
6056                         break;
6057
6058                 case NS_WIDE:
6059                         ncr_setwide (np, cp, 0, 0);
6060                         break;
6061
6062                 };
6063                 np->msgin [0] = MSG_NOOP;
6064                 np->msgout[0] = MSG_NOOP;
6065                 cp->nego_status = 0;
6066                 OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, dispatch));
6067                 break;
6068
6069         case SIR_NEGO_SYNC:
6070                 /*
6071                 **      Synchronous request message received.
6072                 */
6073
6074                 if (DEBUG_FLAGS & DEBUG_NEGO) {
6075                         PRINT_ADDR(cp->ccb);
6076                         printf ("sync msgin: ");
6077                         (void) ncr_show_msg (np->msgin);
6078                         printf (".\n");
6079                 };
6080
6081                 /*
6082                 **      get requested values.
6083                 */
6084
6085                 chg = 0;
6086                 per = np->msgin[3];
6087                 ofs = np->msgin[4];
6088                 if (ofs==0) per=255;
6089
6090                 /*
6091                 **      check values against driver limits.
6092                 */
6093                 if (per < np->minsync)
6094                         {chg = 1; per = np->minsync;}
6095                 if (per < tp->tinfo.user.period)
6096                         {chg = 1; per = tp->tinfo.user.period;}
6097                 if (ofs > tp->tinfo.user.offset)
6098                         {chg = 1; ofs = tp->tinfo.user.offset;}
6099
6100                 /*
6101                 **      Check against controller limits.
6102                 */
6103
6104                 fak     = 7;
6105                 scntl3  = 0;
6106                 if (ofs != 0) {
6107                         ncr_getsync(np, per, &fak, &scntl3);
6108                         if (fak > 7) {
6109                                 chg = 1;
6110                                 ofs = 0;
6111                         }
6112                 }
6113                 if (ofs == 0) {
6114                         fak     = 7;
6115                         per     = 0;
6116                         scntl3  = 0;
6117                 }
6118
6119                 if (DEBUG_FLAGS & DEBUG_NEGO) {
6120                         PRINT_ADDR(cp->ccb);
6121                         printf ("sync: per=%d scntl3=0x%x ofs=%d fak=%d chg=%d.\n",
6122                                 per, scntl3, ofs, fak, chg);
6123                 }
6124
6125                 if (INB (HS_PRT) == HS_NEGOTIATE) {
6126                         OUTB (HS_PRT, HS_BUSY);
6127                         switch (cp->nego_status) {
6128
6129                         case NS_SYNC:
6130                                 /*
6131                                 **      This was an answer message
6132                                 */
6133                                 if (chg) {
6134                                         /*
6135                                         **      Answer wasn't acceptable.
6136                                         */
6137                                         ncr_setsync (np, cp, 0, 0xe0, 0);
6138                                         OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, msg_bad));
6139                                 } else {
6140                                         /*
6141                                         **      Answer is ok.
6142                                         */
6143                                         ncr_setsync (np,cp,scntl3,(fak<<5)|ofs, per);
6144                                         OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, clrack));
6145                                 };
6146                                 return;
6147
6148                         case NS_WIDE:
6149                                 ncr_setwide (np, cp, 0, 0);
6150                                 break;
6151                         };
6152                 };
6153
6154                 /*
6155                 **      It was a request. Set value and
6156                 **      prepare an answer message
6157                 */
6158
6159                 ncr_setsync (np, cp, scntl3, (fak<<5)|ofs, per);
6160
6161                 np->msgout[0] = MSG_EXTENDED;
6162                 np->msgout[1] = 3;
6163                 np->msgout[2] = MSG_EXT_SDTR;
6164                 np->msgout[3] = per;
6165                 np->msgout[4] = ofs;
6166
6167                 cp->nego_status = NS_SYNC;
6168
6169                 if (DEBUG_FLAGS & DEBUG_NEGO) {
6170                         PRINT_ADDR(cp->ccb);
6171                         printf ("sync msgout: ");
6172                         (void) ncr_show_msg (np->msgout);
6173                         printf (".\n");
6174                 }
6175
6176                 if (!ofs) {
6177                         OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, msg_bad));
6178                         return;
6179                 }
6180                 np->msgin [0] = MSG_NOOP;
6181
6182                 break;
6183
6184         case SIR_NEGO_WIDE:
6185                 /*
6186                 **      Wide request message received.
6187                 */
6188                 if (DEBUG_FLAGS & DEBUG_NEGO) {
6189                         PRINT_ADDR(cp->ccb);
6190                         printf ("wide msgin: ");
6191                         (void) ncr_show_msg (np->msgin);
6192                         printf (".\n");
6193                 };
6194
6195                 /*
6196                 **      get requested values.
6197                 */
6198
6199                 chg  = 0;
6200                 wide = np->msgin[3];
6201
6202                 /*
6203                 **      check values against driver limits.
6204                 */
6205
6206                 if (wide > tp->tinfo.user.width)
6207                         {chg = 1; wide = tp->tinfo.user.width;}
6208
6209                 if (DEBUG_FLAGS & DEBUG_NEGO) {
6210                         PRINT_ADDR(cp->ccb);
6211                         printf ("wide: wide=%d chg=%d.\n", wide, chg);
6212                 }
6213
6214                 if (INB (HS_PRT) == HS_NEGOTIATE) {
6215                         OUTB (HS_PRT, HS_BUSY);
6216                         switch (cp->nego_status) {
6217
6218                         case NS_WIDE:
6219                                 /*
6220                                 **      This was an answer message
6221                                 */
6222                                 if (chg) {
6223                                         /*
6224                                         **      Answer wasn't acceptable.
6225                                         */
6226                                         ncr_setwide (np, cp, 0, 1);
6227                                         OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, msg_bad));
6228                                 } else {
6229                                         /*
6230                                         **      Answer is ok.
6231                                         */
6232                                         ncr_setwide (np, cp, wide, 1);
6233                                         OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, clrack));
6234                                 };
6235                                 return;
6236
6237                         case NS_SYNC:
6238                                 ncr_setsync (np, cp, 0, 0xe0, 0);
6239                                 break;
6240                         };
6241                 };
6242
6243                 /*
6244                 **      It was a request, set value and
6245                 **      prepare an answer message
6246                 */
6247
6248                 ncr_setwide (np, cp, wide, 1);
6249
6250                 np->msgout[0] = MSG_EXTENDED;
6251                 np->msgout[1] = 2;
6252                 np->msgout[2] = MSG_EXT_WDTR;
6253                 np->msgout[3] = wide;
6254
6255                 np->msgin [0] = MSG_NOOP;
6256
6257                 cp->nego_status = NS_WIDE;
6258
6259                 if (DEBUG_FLAGS & DEBUG_NEGO) {
6260                         PRINT_ADDR(cp->ccb);
6261                         printf ("wide msgout: ");
6262                         (void) ncr_show_msg (np->msgout);
6263                         printf (".\n");
6264                 }
6265                 break;
6266
6267 /*--------------------------------------------------------------------
6268 **
6269 **      Processing of special messages
6270 **
6271 **--------------------------------------------------------------------
6272 */
6273
6274         case SIR_REJECT_RECEIVED:
6275                 /*-----------------------------------------------
6276                 **
6277                 **      We received a MSG_MESSAGE_REJECT message.
6278                 **
6279                 **-----------------------------------------------
6280                 */
6281
6282                 PRINT_ADDR(cp->ccb);
6283                 printf ("MSG_MESSAGE_REJECT received (%x:%x).\n",
6284                         (unsigned)np->lastmsg, np->msgout[0]);
6285                 break;
6286
6287         case SIR_REJECT_SENT:
6288                 /*-----------------------------------------------
6289                 **
6290                 **      We received an unknown message
6291                 **
6292                 **-----------------------------------------------
6293                 */
6294
6295                 PRINT_ADDR(cp->ccb);
6296                 printf ("MSG_MESSAGE_REJECT sent for ");
6297                 (void) ncr_show_msg (np->msgin);
6298                 printf (".\n");
6299                 break;
6300
6301 /*--------------------------------------------------------------------
6302 **
6303 **      Processing of special messages
6304 **
6305 **--------------------------------------------------------------------
6306 */
6307
6308         case SIR_IGN_RESIDUE:
6309                 /*-----------------------------------------------
6310                 **
6311                 **      We received an IGNORE RESIDUE message,
6312                 **      which couldn't be handled by the script.
6313                 **
6314                 **-----------------------------------------------
6315                 */
6316
6317                 PRINT_ADDR(cp->ccb);
6318                 printf ("MSG_IGN_WIDE_RESIDUE received, but not yet implemented.\n");
6319                 break;
6320
6321         case SIR_MISSING_SAVE:
6322                 /*-----------------------------------------------
6323                 **
6324                 **      We received an DISCONNECT message,
6325                 **      but the datapointer wasn't saved before.
6326                 **
6327                 **-----------------------------------------------
6328                 */
6329
6330                 PRINT_ADDR(cp->ccb);
6331                 printf ("MSG_DISCONNECT received, but datapointer not saved:\n"
6332                         "\tdata=%x save=%x goal=%x.\n",
6333                         (unsigned) INL (nc_temp),
6334                         (unsigned) np->header.savep,
6335                         (unsigned) np->header.goalp);
6336                 break;
6337
6338 /*--------------------------------------------------------------------
6339 **
6340 **      Processing of a "SCSI_STATUS_QUEUE_FULL" status.
6341 **
6342 **      XXX JGibbs - We should do the same thing for BUSY status.
6343 **
6344 **      The current command has been rejected,
6345 **      because there are too many in the command queue.
6346 **      We have started too many commands for that target.
6347 **
6348 **--------------------------------------------------------------------
6349 */
6350         case SIR_STALL_QUEUE:
6351                 cp->xerr_status = XE_OK;
6352                 cp->host_status = HS_COMPLETE;
6353                 cp->s_status = SCSI_STATUS_QUEUE_FULL;
6354                 ncr_freeze_devq(np, cp->ccb->ccb_h.path);
6355                 ncr_complete(np, cp);
6356
6357                 /* FALL THROUGH */
6358
6359         case SIR_STALL_RESTART:
6360                 /*-----------------------------------------------
6361                 **
6362                 **      Enable selecting again,
6363                 **      if NO disconnected jobs.
6364                 **
6365                 **-----------------------------------------------
6366                 */
6367                 /*
6368                 **      Look for a disconnected job.
6369                 */
6370                 cp = np->link_nccb;
6371                 while (cp && cp->host_status != HS_DISCONNECT)
6372                         cp = cp->link_nccb;
6373
6374                 /*
6375                 **      if there is one, ...
6376                 */
6377                 if (cp) {
6378                         /*
6379                         **      wait for reselection
6380                         */
6381                         OUTL (nc_dsp, NCB_SCRIPT_PHYS (np, reselect));
6382                         return;
6383                 };
6384
6385                 /*
6386                 **      else remove the interrupt.
6387                 */
6388
6389                 printf ("%s: queue empty.\n", ncr_name (np));
6390                 WRITESCRIPT(start1[0], SCR_INT ^ IFFALSE (0));
6391                 break;
6392         };
6393
6394 out:
6395         OUTB (nc_dcntl, np->rv_dcntl | STD);
6396 }
6397
6398 /*==========================================================
6399 **
6400 **
6401 **      Aquire a control block
6402 **
6403 **
6404 **==========================================================
6405 */
6406
6407 static  nccb_p ncr_get_nccb
6408         (ncb_p np, u_long target, u_long lun)
6409 {
6410         lcb_p lp;
6411         int s;
6412         nccb_p cp = NULL;
6413
6414         /* Keep our timeout handler out */
6415         s = splsoftclock();
6416         
6417         /*
6418         **      Lun structure available ?
6419         */
6420
6421         lp = np->target[target].lp[lun];
6422         if (lp) {
6423                 cp = lp->next_nccb;
6424
6425                 /*
6426                 **      Look for free CCB
6427                 */
6428
6429                 while (cp && cp->magic) {
6430                         cp = cp->next_nccb;
6431                 }
6432         }
6433
6434         /*
6435         **      if nothing available, create one.
6436         */
6437
6438         if (cp == NULL)
6439                 cp = ncr_alloc_nccb(np, target, lun);
6440
6441         if (cp != NULL) {
6442                 if (cp->magic) {
6443                         printf("%s: Bogus free cp found\n", ncr_name(np));
6444                         splx(s);
6445                         return (NULL);
6446                 }
6447                 cp->magic = 1;
6448         }
6449         splx(s);
6450         return (cp);
6451 }
6452
6453 /*==========================================================
6454 **
6455 **
6456 **      Release one control block
6457 **
6458 **
6459 **==========================================================
6460 */
6461
6462 void ncr_free_nccb (ncb_p np, nccb_p cp)
6463 {
6464         /*
6465         **    sanity
6466         */
6467
6468         assert (cp != NULL);
6469
6470         cp -> host_status = HS_IDLE;
6471         cp -> magic = 0;
6472 }
6473
6474 /*==========================================================
6475 **
6476 **
6477 **      Allocation of resources for Targets/Luns/Tags.
6478 **
6479 **
6480 **==========================================================
6481 */
6482
6483 static nccb_p
6484 ncr_alloc_nccb (ncb_p np, u_long target, u_long lun)
6485 {
6486         tcb_p tp;
6487         lcb_p lp;
6488         nccb_p cp;
6489
6490         assert (np != NULL);
6491
6492         if (target>=MAX_TARGET) return(NULL);
6493         if (lun   >=MAX_LUN   ) return(NULL);
6494
6495         tp=&np->target[target];
6496
6497         if (!tp->jump_tcb.l_cmd) {
6498
6499                 /*
6500                 **      initialize it.
6501                 */
6502                 tp->jump_tcb.l_cmd   = (SCR_JUMP^IFFALSE (DATA (0x80 + target)));
6503                 tp->jump_tcb.l_paddr = np->jump_tcb.l_paddr;
6504
6505                 tp->getscr[0] =
6506                         (np->features & FE_PFEN)? SCR_COPY(1) : SCR_COPY_F(1);
6507                 tp->getscr[1] = vtophys (&tp->tinfo.sval);
6508                 tp->getscr[2] = rman_get_start(np->reg_res) + offsetof (struct ncr_reg, nc_sxfer);
6509                 tp->getscr[3] =
6510                         (np->features & FE_PFEN)? SCR_COPY(1) : SCR_COPY_F(1);
6511                 tp->getscr[4] = vtophys (&tp->tinfo.wval);
6512                 tp->getscr[5] = rman_get_start(np->reg_res) + offsetof (struct ncr_reg, nc_scntl3);
6513
6514                 assert (((offsetof(struct ncr_reg, nc_sxfer) ^
6515                          (offsetof(struct tcb ,tinfo)
6516                         + offsetof(struct ncr_target_tinfo, sval))) & 3) == 0);
6517                 assert (((offsetof(struct ncr_reg, nc_scntl3) ^
6518                          (offsetof(struct tcb, tinfo)
6519                         + offsetof(struct ncr_target_tinfo, wval))) &3) == 0);
6520
6521                 tp->call_lun.l_cmd   = (SCR_CALL);
6522                 tp->call_lun.l_paddr = NCB_SCRIPT_PHYS (np, resel_lun);
6523
6524                 tp->jump_lcb.l_cmd   = (SCR_JUMP);
6525                 tp->jump_lcb.l_paddr = NCB_SCRIPTH_PHYS (np, abort);
6526                 np->jump_tcb.l_paddr = vtophys (&tp->jump_tcb);
6527         }
6528
6529         /*
6530         **      Logic unit control block
6531         */
6532         lp = tp->lp[lun];
6533         if (!lp) {
6534                 /*
6535                 **      Allocate a lcb
6536                 */
6537                 lp = malloc (sizeof (struct lcb), M_DEVBUF, M_WAITOK | M_ZERO);
6538
6539                 /*
6540                 **      Initialize it
6541                 */
6542                 lp->jump_lcb.l_cmd   = (SCR_JUMP ^ IFFALSE (DATA (lun)));
6543                 lp->jump_lcb.l_paddr = tp->jump_lcb.l_paddr;
6544
6545                 lp->call_tag.l_cmd   = (SCR_CALL);
6546                 lp->call_tag.l_paddr = NCB_SCRIPT_PHYS (np, resel_tag);
6547
6548                 lp->jump_nccb.l_cmd   = (SCR_JUMP);
6549                 lp->jump_nccb.l_paddr = NCB_SCRIPTH_PHYS (np, aborttag);
6550
6551                 lp->actlink = 1;
6552
6553                 /*
6554                 **   Chain into LUN list
6555                 */
6556                 tp->jump_lcb.l_paddr = vtophys (&lp->jump_lcb);
6557                 tp->lp[lun] = lp;
6558
6559         }
6560
6561         /*
6562         **      Allocate a nccb
6563         */
6564         cp = malloc (sizeof (struct nccb), M_DEVBUF, M_WAITOK | M_ZERO);
6565
6566         if (DEBUG_FLAGS & DEBUG_ALLOC) { 
6567                 printf ("new nccb @%p.\n", cp);
6568         }
6569
6570         /*
6571         **      Fill in physical addresses
6572         */
6573
6574         cp->p_nccb           = vtophys (cp);
6575
6576         /*
6577         **      Chain into reselect list
6578         */
6579         cp->jump_nccb.l_cmd   = SCR_JUMP;
6580         cp->jump_nccb.l_paddr = lp->jump_nccb.l_paddr;
6581         lp->jump_nccb.l_paddr = CCB_PHYS (cp, jump_nccb);
6582         cp->call_tmp.l_cmd   = SCR_CALL;
6583         cp->call_tmp.l_paddr = NCB_SCRIPT_PHYS (np, resel_tmp);
6584
6585         /*
6586         **      Chain into wakeup list
6587         */
6588         cp->link_nccb      = np->link_nccb;
6589         np->link_nccb      = cp;
6590
6591         /*
6592         **      Chain into CCB list
6593         */
6594         cp->next_nccb   = lp->next_nccb;
6595         lp->next_nccb   = cp;
6596
6597         return (cp);
6598 }
6599
6600 /*==========================================================
6601 **
6602 **
6603 **      Build Scatter Gather Block
6604 **
6605 **
6606 **==========================================================
6607 **
6608 **      The transfer area may be scattered among
6609 **      several non adjacent physical pages.
6610 **
6611 **      We may use MAX_SCATTER blocks.
6612 **
6613 **----------------------------------------------------------
6614 */
6615
6616 static  int     ncr_scatter
6617         (struct dsb* phys, vm_offset_t vaddr, vm_size_t datalen)
6618 {
6619         u_long  paddr, pnext;
6620
6621         u_short segment  = 0;
6622         u_long  segsize, segaddr;
6623         u_long  size, csize    = 0;
6624         u_long  chunk = MAX_SIZE;
6625         int     free;
6626
6627         bzero (&phys->data, sizeof (phys->data));
6628         if (!datalen) return (0);
6629
6630         paddr = vtophys (vaddr);
6631
6632         /*
6633         **      insert extra break points at a distance of chunk.
6634         **      We try to reduce the number of interrupts caused
6635         **      by unexpected phase changes due to disconnects.
6636         **      A typical harddisk may disconnect before ANY block.
6637         **      If we wanted to avoid unexpected phase changes at all
6638         **      we had to use a break point every 512 bytes.
6639         **      Of course the number of scatter/gather blocks is
6640         **      limited.
6641         */
6642
6643         free = MAX_SCATTER - 1;
6644
6645         if (vaddr & PAGE_MASK) free -= datalen / PAGE_SIZE;
6646
6647         if (free>1)
6648                 while ((chunk * free >= 2 * datalen) && (chunk>=1024))
6649                         chunk /= 2;
6650
6651         if(DEBUG_FLAGS & DEBUG_SCATTER)
6652                 printf("ncr?:\tscattering virtual=%p size=%d chunk=%d.\n",
6653                        (void *) vaddr, (unsigned) datalen, (unsigned) chunk);
6654
6655         /*
6656         **   Build data descriptors.
6657         */
6658         while (datalen && (segment < MAX_SCATTER)) {
6659
6660                 /*
6661                 **      this segment is empty
6662                 */
6663                 segsize = 0;
6664                 segaddr = paddr;
6665                 pnext   = paddr;
6666
6667                 if (!csize) csize = chunk;
6668
6669                 while ((datalen) && (paddr == pnext) && (csize)) {
6670
6671                         /*
6672                         **      continue this segment
6673                         */
6674                         pnext = (paddr & (~PAGE_MASK)) + PAGE_SIZE;
6675
6676                         /*
6677                         **      Compute max size
6678                         */
6679
6680                         size = pnext - paddr;           /* page size */
6681                         if (size > datalen) size = datalen;  /* data size */
6682                         if (size > csize  ) size = csize  ;  /* chunksize */
6683
6684                         segsize += size;
6685                         vaddr   += size;
6686                         csize   -= size;
6687                         datalen -= size;
6688                         paddr    = vtophys (vaddr);
6689                 };
6690
6691                 if(DEBUG_FLAGS & DEBUG_SCATTER)
6692                         printf ("\tseg #%d  addr=%x  size=%d  (rest=%d).\n",
6693                         segment,
6694                         (unsigned) segaddr,
6695                         (unsigned) segsize,
6696                         (unsigned) datalen);
6697
6698                 phys->data[segment].addr = segaddr;
6699                 phys->data[segment].size = segsize;
6700                 segment++;
6701         }
6702
6703         if (datalen) {
6704                 printf("ncr?: scatter/gather failed (residue=%d).\n",
6705                         (unsigned) datalen);
6706                 return (-1);
6707         };
6708
6709         return (segment);
6710 }
6711
6712 /*==========================================================
6713 **
6714 **
6715 **      Test the pci bus snoop logic :-(
6716 **
6717 **      Has to be called with interrupts disabled.
6718 **
6719 **
6720 **==========================================================
6721 */
6722
6723 #ifndef NCR_IOMAPPED
6724 static int ncr_regtest (struct ncb* np)
6725 {
6726         volatile u_int32_t data;
6727         /*
6728         **      ncr registers may NOT be cached.
6729         **      write 0xffffffff to a read only register area,
6730         **      and try to read it back.
6731         */
6732         data = 0xffffffff;
6733         OUTL_OFF(offsetof(struct ncr_reg, nc_dstat), data);
6734         data = INL_OFF(offsetof(struct ncr_reg, nc_dstat));
6735 #if 1
6736         if (data == 0xffffffff) {
6737 #else
6738         if ((data & 0xe2f0fffd) != 0x02000080) {
6739 #endif
6740                 printf ("CACHE TEST FAILED: reg dstat-sstat2 readback %x.\n",
6741                         (unsigned) data);
6742                 return (0x10);
6743         };
6744         return (0);
6745 }
6746 #endif
6747
6748 static int ncr_snooptest (struct ncb* np)
6749 {
6750         u_int32_t ncr_rd, ncr_wr, ncr_bk, host_rd, host_wr, pc;
6751         int     i, err=0;
6752 #ifndef NCR_IOMAPPED
6753         err |= ncr_regtest (np);
6754         if (err) return (err);
6755 #endif
6756         /*
6757         **      init
6758         */
6759         pc  = NCB_SCRIPTH_PHYS (np, snooptest);
6760         host_wr = 1;
6761         ncr_wr  = 2;
6762         /*
6763         **      Set memory and register.
6764         */
6765         ncr_cache = host_wr;
6766         OUTL (nc_temp, ncr_wr);
6767         /*
6768         **      Start script (exchange values)
6769         */
6770         OUTL (nc_dsp, pc);
6771         /*
6772         **      Wait 'til done (with timeout)
6773         */
6774         for (i=0; i<NCR_SNOOP_TIMEOUT; i++)
6775                 if (INB(nc_istat) & (INTF|SIP|DIP))
6776                         break;
6777         /*
6778         **      Save termination position.
6779         */
6780         pc = INL (nc_dsp);
6781         /*
6782         **      Read memory and register.
6783         */
6784         host_rd = ncr_cache;
6785         ncr_rd  = INL (nc_scratcha);
6786         ncr_bk  = INL (nc_temp);
6787         /*
6788         **      Reset ncr chip
6789         */
6790         OUTB (nc_istat,  SRST);
6791         DELAY (1000);
6792         OUTB (nc_istat,  0   );
6793         /*
6794         **      check for timeout
6795         */
6796         if (i>=NCR_SNOOP_TIMEOUT) {
6797                 printf ("CACHE TEST FAILED: timeout.\n");
6798                 return (0x20);
6799         };
6800         /*
6801         **      Check termination position.
6802         */
6803         if (pc != NCB_SCRIPTH_PHYS (np, snoopend)+8) {
6804                 printf ("CACHE TEST FAILED: script execution failed.\n");
6805                 printf ("start=%08lx, pc=%08lx, end=%08lx\n", 
6806                         (u_long) NCB_SCRIPTH_PHYS (np, snooptest), (u_long) pc,
6807                         (u_long) NCB_SCRIPTH_PHYS (np, snoopend) +8);
6808                 return (0x40);
6809         };
6810         /*
6811         **      Show results.
6812         */
6813         if (host_wr != ncr_rd) {
6814                 printf ("CACHE TEST FAILED: host wrote %d, ncr read %d.\n",
6815                         (int) host_wr, (int) ncr_rd);
6816                 err |= 1;
6817         };
6818         if (host_rd != ncr_wr) {
6819                 printf ("CACHE TEST FAILED: ncr wrote %d, host read %d.\n",
6820                         (int) ncr_wr, (int) host_rd);
6821                 err |= 2;
6822         };
6823         if (ncr_bk != ncr_wr) {
6824                 printf ("CACHE TEST FAILED: ncr wrote %d, read back %d.\n",
6825                         (int) ncr_wr, (int) ncr_bk);
6826                 err |= 4;
6827         };
6828         return (err);
6829 }
6830
6831 /*==========================================================
6832 **
6833 **
6834 **      Profiling the drivers and targets performance.
6835 **
6836 **
6837 **==========================================================
6838 */
6839
6840 /*
6841 **      Compute the difference in milliseconds.
6842 **/
6843
6844 static  int ncr_delta (int *from, int *to)
6845 {
6846         if (!from) return (-1);
6847         if (!to)   return (-2);
6848         return ((to - from) * 1000 / hz);
6849 }
6850
6851 #define PROFILE  cp->phys.header.stamp
6852 static  void ncb_profile (ncb_p np, nccb_p cp)
6853 {
6854         int co, da, st, en, di, se, post,work,disc;
6855         u_long diff;
6856
6857         PROFILE.end = ticks;
6858
6859         st = ncr_delta (&PROFILE.start,&PROFILE.status);
6860         if (st<0) return;       /* status  not reached  */
6861
6862         da = ncr_delta (&PROFILE.start,&PROFILE.data);
6863         if (da<0) return;       /* No data transfer phase */
6864
6865         co = ncr_delta (&PROFILE.start,&PROFILE.command);
6866         if (co<0) return;       /* command not executed */
6867
6868         en = ncr_delta (&PROFILE.start,&PROFILE.end),
6869         di = ncr_delta (&PROFILE.start,&PROFILE.disconnect),
6870         se = ncr_delta (&PROFILE.start,&PROFILE.select);
6871         post = en - st;
6872
6873         /*
6874         **      @PROFILE@  Disconnect time invalid if multiple disconnects
6875         */
6876
6877         if (di>=0) disc = se-di; else  disc = 0;
6878
6879         work = (st - co) - disc;
6880
6881         diff = (np->disc_phys - np->disc_ref) & 0xff;
6882         np->disc_ref += diff;
6883
6884         np->profile.num_trans   += 1;
6885         if (cp->ccb)
6886                 np->profile.num_bytes   += cp->ccb->csio.dxfer_len;
6887         np->profile.num_disc    += diff;
6888         np->profile.ms_setup    += co;
6889         np->profile.ms_data     += work;
6890         np->profile.ms_disc     += disc;
6891         np->profile.ms_post     += post;
6892 }
6893 #undef PROFILE
6894
6895 /*==========================================================
6896 **
6897 **      Determine the ncr's clock frequency.
6898 **      This is essential for the negotiation
6899 **      of the synchronous transfer rate.
6900 **
6901 **==========================================================
6902 **
6903 **      Note: we have to return the correct value.
6904 **      THERE IS NO SAVE DEFAULT VALUE.
6905 **
6906 **      Most NCR/SYMBIOS boards are delivered with a 40 Mhz clock.
6907 **      53C860 and 53C875 rev. 1 support fast20 transfers but 
6908 **      do not have a clock doubler and so are provided with a 
6909 **      80 MHz clock. All other fast20 boards incorporate a doubler 
6910 **      and so should be delivered with a 40 MHz clock.
6911 **      The future fast40 chips (895/895) use a 40 Mhz base clock 
6912 **      and provide a clock quadrupler (160 Mhz). The code below 
6913 **      tries to deal as cleverly as possible with all this stuff.
6914 **
6915 **----------------------------------------------------------
6916 */
6917
6918 /*
6919  *      Select NCR SCSI clock frequency
6920  */
6921 static void ncr_selectclock(ncb_p np, u_char scntl3)
6922 {
6923         if (np->multiplier < 2) {
6924                 OUTB(nc_scntl3, scntl3);
6925                 return;
6926         }
6927
6928         if (bootverbose >= 2)
6929                 printf ("%s: enabling clock multiplier\n", ncr_name(np));
6930
6931         OUTB(nc_stest1, DBLEN);    /* Enable clock multiplier             */
6932         if (np->multiplier > 2) {  /* Poll bit 5 of stest4 for quadrupler */
6933                 int i = 20;
6934                 while (!(INB(nc_stest4) & LCKFRQ) && --i > 0)
6935                         DELAY(20);
6936                 if (!i)
6937                         printf("%s: the chip cannot lock the frequency\n", ncr_name(np));
6938         } else                  /* Wait 20 micro-seconds for doubler    */
6939                 DELAY(20);
6940         OUTB(nc_stest3, HSC);           /* Halt the scsi clock          */
6941         OUTB(nc_scntl3, scntl3);
6942         OUTB(nc_stest1, (DBLEN|DBLSEL));/* Select clock multiplier      */
6943         OUTB(nc_stest3, 0x00);          /* Restart scsi clock           */
6944 }
6945
6946 /*
6947  *      calculate NCR SCSI clock frequency (in KHz)
6948  */
6949 static unsigned
6950 ncrgetfreq (ncb_p np, int gen)
6951 {
6952         int ms = 0;
6953         /*
6954          * Measure GEN timer delay in order 
6955          * to calculate SCSI clock frequency
6956          *
6957          * This code will never execute too
6958          * many loop iterations (if DELAY is 
6959          * reasonably correct). It could get
6960          * too low a delay (too high a freq.)
6961          * if the CPU is slow executing the 
6962          * loop for some reason (an NMI, for
6963          * example). For this reason we will
6964          * if multiple measurements are to be 
6965          * performed trust the higher delay 
6966          * (lower frequency returned).
6967          */
6968         OUTB (nc_stest1, 0);    /* make sure clock doubler is OFF           */
6969         OUTW (nc_sien , 0);     /* mask all scsi interrupts                 */
6970         (void) INW (nc_sist);   /* clear pending scsi interrupt             */
6971         OUTB (nc_dien , 0);     /* mask all dma interrupts                  */
6972         (void) INW (nc_sist);   /* another one, just to be sure :)          */
6973         OUTB (nc_scntl3, 4);    /* set pre-scaler to divide by 3            */
6974         OUTB (nc_stime1, 0);    /* disable general purpose timer            */
6975         OUTB (nc_stime1, gen);  /* set to nominal delay of (1<<gen) * 125us */
6976         while (!(INW(nc_sist) & GEN) && ms++ < 1000)
6977                 DELAY(1000);    /* count ms                                 */
6978         OUTB (nc_stime1, 0);    /* disable general purpose timer            */
6979         OUTB (nc_scntl3, 0);
6980         /*
6981          * Set prescaler to divide by whatever "0" means.
6982          * "0" ought to choose divide by 2, but appears
6983          * to set divide by 3.5 mode in my 53c810 ...
6984          */
6985         OUTB (nc_scntl3, 0);
6986
6987         if (bootverbose >= 2)
6988                 printf ("\tDelay (GEN=%d): %u msec\n", gen, ms);
6989         /*
6990          * adjust for prescaler, and convert into KHz 
6991          */
6992         return ms ? ((1 << gen) * 4440) / ms : 0;
6993 }
6994
6995 static void ncr_getclock (ncb_p np, u_char multiplier)
6996 {
6997         unsigned char scntl3;
6998         unsigned char stest1;
6999         scntl3 = INB(nc_scntl3);
7000         stest1 = INB(nc_stest1);
7001           
7002         np->multiplier = 1;
7003
7004         if (multiplier > 1) {
7005                 np->multiplier  = multiplier;
7006                 np->clock_khz   = 40000 * multiplier;
7007         } else {
7008                 if ((scntl3 & 7) == 0) {
7009                         unsigned f1, f2;
7010                         /* throw away first result */
7011                         (void) ncrgetfreq (np, 11);
7012                         f1 = ncrgetfreq (np, 11);
7013                         f2 = ncrgetfreq (np, 11);
7014
7015                         if (bootverbose >= 2)
7016                           printf ("\tNCR clock is %uKHz, %uKHz\n", f1, f2);
7017                         if (f1 > f2) f1 = f2;   /* trust lower result   */
7018                         if (f1 > 45000) {
7019                                 scntl3 = 5;     /* >45Mhz: assume 80MHz */
7020                         } else {
7021                                 scntl3 = 3;     /* <45Mhz: assume 40MHz */
7022                         }
7023                 }
7024                 else if ((scntl3 & 7) == 5)
7025                         np->clock_khz = 80000;  /* Probably a 875 rev. 1 ? */
7026         }
7027 }
7028
7029 /*=========================================================================*/
7030
7031 #ifdef NCR_TEKRAM_EEPROM
7032
7033 struct tekram_eeprom_dev {
7034   u_char        devmode;
7035 #define TKR_PARCHK      0x01
7036 #define TKR_TRYSYNC     0x02
7037 #define TKR_ENDISC      0x04
7038 #define TKR_STARTUNIT   0x08
7039 #define TKR_USETAGS     0x10
7040 #define TKR_TRYWIDE     0x20
7041   u_char        syncparam;      /* max. sync transfer rate (table ?) */
7042   u_char        filler1;
7043   u_char        filler2;
7044 };
7045
7046
7047 struct tekram_eeprom {
7048   struct tekram_eeprom_dev 
7049                 dev[16];
7050   u_char        adaptid;
7051   u_char        adaptmode;
7052 #define TKR_ADPT_GT2DRV 0x01
7053 #define TKR_ADPT_GT1GB  0x02
7054 #define TKR_ADPT_RSTBUS 0x04
7055 #define TKR_ADPT_ACTNEG 0x08
7056 #define TKR_ADPT_NOSEEK 0x10
7057 #define TKR_ADPT_MORLUN 0x20
7058   u_char        delay;          /* unit ? ( table ??? ) */
7059   u_char        tags;           /* use 4 times as many ... */
7060   u_char        filler[60];
7061 };
7062
7063 static void
7064 tekram_write_bit (ncb_p np, int bit)
7065 {
7066         u_char val = 0x10 + ((bit & 1) << 1);
7067
7068         DELAY(10);
7069         OUTB (nc_gpreg, val);
7070         DELAY(10);
7071         OUTB (nc_gpreg, val | 0x04);
7072         DELAY(10);
7073         OUTB (nc_gpreg, val);
7074         DELAY(10);
7075 }
7076
7077 static int
7078 tekram_read_bit (ncb_p np)
7079 {
7080         OUTB (nc_gpreg, 0x10);
7081         DELAY(10);
7082         OUTB (nc_gpreg, 0x14);
7083         DELAY(10);
7084         return INB (nc_gpreg) & 1;
7085 }
7086
7087 static u_short
7088 read_tekram_eeprom_reg (ncb_p np, int reg)
7089 {
7090         int bit;
7091         u_short result = 0;
7092         int cmd = 0x80 | reg;
7093
7094         OUTB (nc_gpreg, 0x10);
7095
7096         tekram_write_bit (np, 1);
7097         for (bit = 7; bit >= 0; bit--)
7098         {
7099                 tekram_write_bit (np, cmd >> bit);
7100         }
7101
7102         for (bit = 0; bit < 16; bit++)
7103         {
7104                 result <<= 1;
7105                 result |= tekram_read_bit (np);
7106         }
7107
7108         OUTB (nc_gpreg, 0x00);
7109         return result;
7110 }
7111
7112 static int 
7113 read_tekram_eeprom(ncb_p np, struct tekram_eeprom *buffer)
7114 {
7115         u_short *p = (u_short *) buffer;
7116         u_short sum = 0;
7117         int i;
7118
7119         if (INB (nc_gpcntl) != 0x09)
7120         {
7121                 return 0;
7122         }
7123         for (i = 0; i < 64; i++)
7124         {
7125                 u_short val;
7126 if((i&0x0f) == 0) printf ("%02x:", i*2);
7127                 val = read_tekram_eeprom_reg (np, i);
7128                 if (p)
7129                         *p++ = val;
7130                 sum += val;
7131 if((i&0x01) == 0x00) printf (" ");
7132                 printf ("%02x%02x", val & 0xff, (val >> 8) & 0xff);
7133 if((i&0x0f) == 0x0f) printf ("\n");
7134         }
7135 printf ("Sum = %04x\n", sum);
7136         return sum == 0x1234;
7137 }
7138 #endif /* NCR_TEKRAM_EEPROM */
7139
7140 static device_method_t ncr_methods[] = {
7141         /* Device interface */
7142         DEVMETHOD(device_probe,         ncr_probe),
7143         DEVMETHOD(device_attach,        ncr_attach),
7144
7145         { 0, 0 }
7146 };
7147
7148 static driver_t ncr_driver = {
7149         "ncr",
7150         ncr_methods,
7151         sizeof(struct ncb),
7152 };
7153
7154 static devclass_t ncr_devclass;
7155
7156 DRIVER_MODULE(if_ncr, pci, ncr_driver, ncr_devclass, 0, 0);
7157
7158 /*=========================================================================*/
7159 #endif /* _KERNEL */