The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/cam/scsi/scsi_low.c

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 /*      $NecBSD: scsi_low.c,v 1.24.10.8 2001/06/26 07:39:44 honda Exp $ */
    2 /*      $NetBSD$        */
    3 
    4 #include <sys/cdefs.h>
    5 __FBSDID("$FreeBSD: releng/10.0/sys/cam/scsi/scsi_low.c 240325 2012-09-10 18:49:49Z jhb $");
    6 
    7 #define SCSI_LOW_STATICS
    8 #define SCSI_LOW_DEBUG
    9 #define SCSI_LOW_NEGOTIATE_BEFORE_SENSE
   10 #define SCSI_LOW_START_UP_CHECK
   11 
   12 /* #define      SCSI_LOW_INFO_DETAIL */
   13 
   14 /* #define      SCSI_LOW_QCLEAR_AFTER_CA */
   15 /* #define      SCSI_LOW_FLAGS_QUIRKS_OK */
   16 
   17 #define SCSI_LOW_FLAGS_QUIRKS_OK
   18 
   19 /*-
   20  * [NetBSD for NEC PC-98 series]
   21  *  Copyright (c) 1995, 1996, 1997, 1998, 1999, 2000, 2001
   22  *      NetBSD/pc98 porting staff. All rights reserved.
   23  *  Copyright (c) 1995, 1996, 1997, 1998, 1999, 2000, 2001
   24  *      Naofumi HONDA. All rights reserved.
   25  *
   26  * [Ported for FreeBSD CAM]
   27  *  Copyright (c) 2000, 2001
   28  *      MITSUNAGA Noriaki, NOKUBI Hirotaka and TAKAHASHI Yoshihiro.
   29  *      All rights reserved.
   30  * 
   31  *  Redistribution and use in source and binary forms, with or without
   32  *  modification, are permitted provided that the following conditions
   33  *  are met:
   34  *  1. Redistributions of source code must retain the above copyright
   35  *     notice, this list of conditions and the following disclaimer.
   36  *  2. Redistributions in binary form must reproduce the above copyright
   37  *     notice, this list of conditions and the following disclaimer in the
   38  *     documentation and/or other materials provided with the distribution.
   39  *  3. The name of the author may not be used to endorse or promote products
   40  *     derived from this software without specific prior written permission.
   41  * 
   42  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
   43  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
   44  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
   45  * DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
   46  * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
   47  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
   48  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
   49  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
   50  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
   51  * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
   52  * POSSIBILITY OF SUCH DAMAGE.
   53  */
   54 
   55 /* <On the nexus establishment>
   56  * When our host is reselected, 
   57  * nexus establish processes are little complicated.
   58  * Normal steps are followings:
   59  * 1) Our host selected by target => target nexus (slp->sl_Tnexus) 
   60  * 2) Identify msgin => lun nexus (slp->sl_Lnexus)
   61  * 3) Qtag msg => ccb nexus (slp->sl_Qnexus)
   62  */
   63 #include "opt_ddb.h"
   64 
   65 #include <sys/param.h>
   66 #include <sys/systm.h>
   67 #include <sys/kernel.h>
   68 #include <sys/bio.h>
   69 #include <sys/buf.h>
   70 #include <sys/queue.h>
   71 #include <sys/malloc.h>
   72 #include <sys/errno.h>
   73 
   74 #include <cam/cam.h>
   75 #include <cam/cam_ccb.h>
   76 #include <cam/cam_sim.h>
   77 #include <cam/cam_debug.h>
   78 #include <cam/cam_periph.h>
   79 #include <cam/cam_xpt_periph.h>
   80 
   81 #include <cam/scsi/scsi_all.h>
   82 #include <cam/scsi/scsi_message.h>
   83 
   84 #include <cam/scsi/scsi_low.h>
   85 
   86 #include <sys/cons.h>
   87 
   88 /**************************************************************
   89  * Constants
   90  **************************************************************/
   91 #define SCSI_LOW_POLL_HZ        1000
   92 
   93 /* functions return values */
   94 #define SCSI_LOW_START_NO_QTAG  0
   95 #define SCSI_LOW_START_QTAG     1
   96 
   97 #define SCSI_LOW_DONE_COMPLETE  0
   98 #define SCSI_LOW_DONE_RETRY     1
   99 
  100 /* internal disk flags */
  101 #define SCSI_LOW_DISK_DISC      0x00000001
  102 #define SCSI_LOW_DISK_QTAG      0x00000002
  103 #define SCSI_LOW_DISK_LINK      0x00000004
  104 #define SCSI_LOW_DISK_PARITY    0x00000008
  105 #define SCSI_LOW_DISK_SYNC      0x00010000
  106 #define SCSI_LOW_DISK_WIDE_16   0x00020000
  107 #define SCSI_LOW_DISK_WIDE_32   0x00040000
  108 #define SCSI_LOW_DISK_WIDE      (SCSI_LOW_DISK_WIDE_16 | SCSI_LOW_DISK_WIDE_32)
  109 #define SCSI_LOW_DISK_LFLAGS    0x0000ffff
  110 #define SCSI_LOW_DISK_TFLAGS    0xffff0000
  111 
  112 static MALLOC_DEFINE(M_SCSILOW, "SCSI low", "SCSI low buffers");
  113 
  114 /**************************************************************
  115  * Declarations
  116  **************************************************************/
  117 /* static */ void scsi_low_info(struct scsi_low_softc *, struct targ_info *, u_char *);
  118 static void scsi_low_engage(void *);
  119 static struct slccb *scsi_low_establish_ccb(struct targ_info *, struct lun_info *, scsi_low_tag_t);
  120 static int scsi_low_done(struct scsi_low_softc *, struct slccb *);
  121 static int scsi_low_setup_done(struct scsi_low_softc *, struct slccb *);
  122 static void scsi_low_bus_release(struct scsi_low_softc *, struct targ_info *);
  123 static void scsi_low_twiddle_wait(void);
  124 static struct lun_info *scsi_low_alloc_li(struct targ_info *, int, int);
  125 static struct targ_info *scsi_low_alloc_ti(struct scsi_low_softc *, int);
  126 static void scsi_low_calcf_lun(struct lun_info *);
  127 static void scsi_low_calcf_target(struct targ_info *);
  128 static void scsi_low_calcf_show(struct lun_info *);
  129 static void scsi_low_reset_nexus(struct scsi_low_softc *, int);
  130 static void scsi_low_reset_nexus_target(struct scsi_low_softc *, struct targ_info *, int);
  131 static void scsi_low_reset_nexus_lun(struct scsi_low_softc *, struct lun_info *, int);
  132 static int scsi_low_init(struct scsi_low_softc *, u_int);
  133 static void scsi_low_start(struct scsi_low_softc *);
  134 static void scsi_low_free_ti(struct scsi_low_softc *);
  135 
  136 static int scsi_low_alloc_qtag(struct slccb *);
  137 static int scsi_low_dealloc_qtag(struct slccb *);
  138 static int scsi_low_enqueue(struct scsi_low_softc *, struct targ_info *, struct lun_info *, struct slccb *, u_int, u_int);
  139 static int scsi_low_message_enqueue(struct scsi_low_softc *, struct targ_info *, struct lun_info *, u_int);
  140 static void scsi_low_unit_ready_cmd(struct slccb *);
  141 static void scsi_low_timeout(void *);
  142 static int scsi_low_timeout_check(struct scsi_low_softc *);
  143 #ifdef  SCSI_LOW_START_UP_CHECK
  144 static int scsi_low_start_up(struct scsi_low_softc *);
  145 #endif  /* SCSI_LOW_START_UP_CHECK */
  146 static int scsi_low_abort_ccb(struct scsi_low_softc *, struct slccb *);
  147 static struct slccb *scsi_low_revoke_ccb(struct scsi_low_softc *, struct slccb *, int);
  148 
  149 int scsi_low_version_major = 2;
  150 int scsi_low_version_minor = 17;
  151 
  152 static struct scsi_low_softc_tab sl_tab = LIST_HEAD_INITIALIZER(sl_tab);
  153 
  154 /**************************************************************
  155  * Debug, Run test and Statics
  156  **************************************************************/
  157 #ifdef  SCSI_LOW_INFO_DETAIL
  158 #define SCSI_LOW_INFO(slp, ti, s) scsi_low_info((slp), (ti), (s))
  159 #else   /* !SCSI_LOW_INFO_DETAIL */
  160 #define SCSI_LOW_INFO(slp, ti, s) device_printf((slp)->sl_dev, "%s\n", (s))
  161 #endif  /* !SCSI_LOW_INFO_DETAIL */
  162 
  163 #ifdef  SCSI_LOW_STATICS
  164 static struct scsi_low_statics {
  165         int nexus_win;
  166         int nexus_fail;
  167         int nexus_disconnected;
  168         int nexus_reselected;
  169         int nexus_conflict;
  170 } scsi_low_statics;
  171 #endif  /* SCSI_LOW_STATICS */
  172 
  173 #ifdef  SCSI_LOW_DEBUG
  174 #define SCSI_LOW_DEBUG_DONE     0x00001
  175 #define SCSI_LOW_DEBUG_DISC     0x00002
  176 #define SCSI_LOW_DEBUG_SENSE    0x00004
  177 #define SCSI_LOW_DEBUG_CALCF    0x00008
  178 #define SCSI_LOW_DEBUG_ACTION   0x10000
  179 int scsi_low_debug = 0;
  180 
  181 #define SCSI_LOW_MAX_ATTEN_CHECK        32
  182 #define SCSI_LOW_ATTEN_CHECK    0x0001
  183 #define SCSI_LOW_CMDLNK_CHECK   0x0002
  184 #define SCSI_LOW_ABORT_CHECK    0x0004
  185 #define SCSI_LOW_NEXUS_CHECK    0x0008
  186 int scsi_low_test = 0;
  187 int scsi_low_test_id = 0;
  188 
  189 static void scsi_low_test_abort(struct scsi_low_softc *, struct targ_info *, struct lun_info *);
  190 static void scsi_low_test_cmdlnk(struct scsi_low_softc *, struct slccb *);
  191 static void scsi_low_test_atten(struct scsi_low_softc *, struct targ_info *, u_int);
  192 #define SCSI_LOW_DEBUG_TEST_GO(fl, id) \
  193         ((scsi_low_test & (fl)) != 0 && (scsi_low_test_id & (1 << (id))) == 0)
  194 #define SCSI_LOW_DEBUG_GO(fl, id) \
  195         ((scsi_low_debug & (fl)) != 0 && (scsi_low_test_id & (1 << (id))) == 0)
  196 #endif  /* SCSI_LOW_DEBUG */
  197 
  198 /**************************************************************
  199  * CCB
  200  **************************************************************/
  201 GENERIC_CCB_STATIC_ALLOC(scsi_low, slccb)
  202 GENERIC_CCB(scsi_low, slccb, ccb_chain)
  203 
  204 /**************************************************************
  205  * Inline functions
  206  **************************************************************/
  207 #define SCSI_LOW_INLINE static __inline
  208 SCSI_LOW_INLINE void scsi_low_activate_qtag(struct slccb *);
  209 SCSI_LOW_INLINE void scsi_low_deactivate_qtag(struct slccb *);
  210 SCSI_LOW_INLINE void scsi_low_ccb_message_assert(struct slccb *, u_int);
  211 SCSI_LOW_INLINE void scsi_low_ccb_message_exec(struct scsi_low_softc *, struct slccb *);
  212 SCSI_LOW_INLINE void scsi_low_ccb_message_retry(struct slccb *);
  213 SCSI_LOW_INLINE void scsi_low_ccb_message_clear(struct slccb *);
  214 SCSI_LOW_INLINE void scsi_low_init_msgsys(struct scsi_low_softc *, struct targ_info *);
  215 
  216 SCSI_LOW_INLINE void
  217 scsi_low_activate_qtag(cb)
  218         struct slccb *cb;
  219 {
  220         struct lun_info *li = cb->li;
  221 
  222         if (cb->ccb_tag != SCSI_LOW_UNKTAG)
  223                 return;
  224 
  225         li->li_nqio ++;
  226         cb->ccb_tag = cb->ccb_otag;
  227 }
  228         
  229 SCSI_LOW_INLINE void
  230 scsi_low_deactivate_qtag(cb)
  231         struct slccb *cb;
  232 {
  233         struct lun_info *li = cb->li;
  234 
  235         if (cb->ccb_tag == SCSI_LOW_UNKTAG)
  236                 return;
  237 
  238         li->li_nqio --;
  239         cb->ccb_tag = SCSI_LOW_UNKTAG;
  240 }
  241         
  242 SCSI_LOW_INLINE void
  243 scsi_low_ccb_message_exec(slp, cb)
  244         struct scsi_low_softc *slp;
  245         struct slccb *cb;
  246 {
  247 
  248         scsi_low_assert_msg(slp, cb->ti, cb->ccb_msgoutflag, 0);
  249         cb->ccb_msgoutflag = 0;
  250 }
  251 
  252 SCSI_LOW_INLINE void
  253 scsi_low_ccb_message_assert(cb, msg)
  254         struct slccb *cb;
  255         u_int msg;
  256 {
  257 
  258         cb->ccb_msgoutflag = cb->ccb_omsgoutflag = msg;
  259 }
  260 
  261 SCSI_LOW_INLINE void
  262 scsi_low_ccb_message_retry(cb)
  263         struct slccb *cb;
  264 {
  265         cb->ccb_msgoutflag = cb->ccb_omsgoutflag;
  266 }
  267 
  268 SCSI_LOW_INLINE void
  269 scsi_low_ccb_message_clear(cb)
  270         struct slccb *cb;
  271 {
  272         cb->ccb_msgoutflag = 0;
  273 }
  274 
  275 SCSI_LOW_INLINE void
  276 scsi_low_init_msgsys(slp, ti)
  277         struct scsi_low_softc *slp;
  278         struct targ_info *ti;
  279 {
  280 
  281         ti->ti_msginptr = 0;
  282         ti->ti_emsgflags = ti->ti_msgflags = ti->ti_omsgflags = 0;
  283         SCSI_LOW_DEASSERT_ATN(slp);
  284         SCSI_LOW_SETUP_MSGPHASE(slp, MSGPH_NULL);
  285 }
  286 
  287 /*=============================================================
  288  * START OF OS switch  (All OS depend fucntions should be here)
  289  =============================================================*/
  290 /* common os depend utitlities */
  291 #define SCSI_LOW_CMD_RESIDUAL_CHK       0x0001
  292 #define SCSI_LOW_CMD_ORDERED_QTAG       0x0002
  293 #define SCSI_LOW_CMD_ABORT_WARNING      0x0004
  294 
  295 static u_int8_t scsi_low_cmd_flags[256] = {
  296 /*      0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f */
  297 /**/   0, 0, 0, 0, 0, 0, 0, 0, 5, 0, 5, 0, 0, 0, 0, 0,
  298 /*1*/   0, 0, 0, 0, 0, 0, 2, 2, 0, 0, 0, 0, 0, 0, 0, 0,
  299 /*2*/   0, 0, 0, 0, 0, 0, 0, 0, 5, 0, 5, 0, 0, 0, 5, 5,
  300 /*3*/   0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 5,
  301 };
  302 
  303 struct scsi_low_error_code {
  304         int error_bits;
  305         int error_code;
  306 };
  307 
  308 static struct slccb *scsi_low_find_ccb(struct scsi_low_softc *, u_int, u_int, void *);
  309 static int scsi_low_translate_error_code(struct slccb *, struct scsi_low_error_code *);
  310 
  311 static struct slccb *
  312 scsi_low_find_ccb(slp, target, lun, osdep)
  313         struct scsi_low_softc *slp;
  314         u_int target, lun;
  315         void *osdep;
  316 {
  317         struct targ_info *ti;
  318         struct lun_info *li;
  319         struct slccb *cb;
  320 
  321         ti = slp->sl_ti[target];
  322         li = scsi_low_alloc_li(ti, lun, 0);
  323         if (li == NULL)
  324                 return NULL;
  325 
  326         if ((cb = slp->sl_Qnexus) != NULL && cb->osdep == osdep)
  327                 return cb;
  328 
  329         for (cb = TAILQ_FIRST(&slp->sl_start); cb != NULL;
  330              cb = TAILQ_NEXT(cb, ccb_chain))
  331         {
  332                 if (cb->osdep == osdep)
  333                         return cb;
  334         }
  335 
  336         for (cb = TAILQ_FIRST(&li->li_discq); cb != NULL;
  337              cb = TAILQ_NEXT(cb, ccb_chain))
  338         {
  339                 if (cb->osdep == osdep)
  340                         return cb;
  341         }
  342         return NULL;
  343 }
  344 
  345 static int 
  346 scsi_low_translate_error_code(cb, tp)
  347         struct slccb *cb;
  348         struct scsi_low_error_code *tp;
  349 {
  350 
  351         if (cb->ccb_error == 0)
  352                 return tp->error_code;
  353 
  354         for (tp ++; (cb->ccb_error & tp->error_bits) == 0; tp ++)
  355                 ;
  356         return tp->error_code;
  357 }
  358 
  359 /**************************************************************
  360  * SCSI INTERFACE (CAM)
  361  **************************************************************/
  362 #define SCSI_LOW_MALLOC(size)           malloc((size), M_SCSILOW, M_NOWAIT)
  363 #define SCSI_LOW_FREE(pt)               free((pt), M_SCSILOW)
  364 #define SCSI_LOW_ALLOC_CCB(flags)       scsi_low_get_ccb()
  365 
  366 static void scsi_low_poll_cam(struct cam_sim *);
  367 void scsi_low_scsi_action_cam(struct cam_sim *, union ccb *);
  368 
  369 static int scsi_low_attach_cam(struct scsi_low_softc *);
  370 static int scsi_low_world_start_cam(struct scsi_low_softc *);
  371 static int scsi_low_dettach_cam(struct scsi_low_softc *);
  372 static int scsi_low_ccb_setup_cam(struct scsi_low_softc *, struct slccb *);
  373 static int scsi_low_done_cam(struct scsi_low_softc *, struct slccb *);
  374 static void scsi_low_timeout_cam(struct scsi_low_softc *, int, int);
  375 
  376 struct scsi_low_osdep_funcs scsi_low_osdep_funcs_cam = {
  377         scsi_low_attach_cam,
  378         scsi_low_world_start_cam,
  379         scsi_low_dettach_cam,
  380         scsi_low_ccb_setup_cam,
  381         scsi_low_done_cam,
  382         scsi_low_timeout_cam
  383 };
  384         
  385 struct scsi_low_error_code scsi_low_error_code_cam[] = {
  386         {0,                     CAM_REQ_CMP},
  387         {SENSEIO,               CAM_AUTOSNS_VALID | CAM_REQ_CMP_ERR},
  388         {SENSEERR,              CAM_AUTOSENSE_FAIL},
  389         {UACAERR,               CAM_SCSI_STATUS_ERROR},
  390         {BUSYERR | STATERR,     CAM_SCSI_STATUS_ERROR},
  391         {SELTIMEOUTIO,          CAM_SEL_TIMEOUT},       
  392         {TIMEOUTIO,             CAM_CMD_TIMEOUT},
  393         {PDMAERR,               CAM_DATA_RUN_ERR},
  394         {PARITYERR,             CAM_UNCOR_PARITY},
  395         {UBFERR,                CAM_UNEXP_BUSFREE},
  396         {ABORTIO,               CAM_REQ_ABORTED},
  397         {-1,                    CAM_UNREC_HBA_ERROR}
  398 };
  399 
  400 #define SIM2SLP(sim)    ((struct scsi_low_softc *) cam_sim_softc((sim)))
  401 
  402 /* XXX:
  403  * Please check a polling hz, currently we assume scsi_low_poll() is
  404  * called each 1 ms.
  405  */
  406 #define SCSI_LOW_CAM_POLL_HZ    1000    /* OK ? */
  407 
  408 static void
  409 scsi_low_poll_cam(sim)
  410         struct cam_sim *sim;
  411 {
  412         struct scsi_low_softc *slp = SIM2SLP(sim);
  413 
  414         (*slp->sl_funcs->scsi_low_poll) (slp);
  415 
  416         if (slp->sl_si.si_poll_count ++ >= 
  417             SCSI_LOW_CAM_POLL_HZ / SCSI_LOW_TIMEOUT_HZ)
  418         {
  419                 slp->sl_si.si_poll_count = 0;
  420                 scsi_low_timeout_check(slp);
  421         }
  422 }
  423 
  424 void
  425 scsi_low_scsi_action_cam(sim, ccb)
  426         struct cam_sim *sim;
  427         union ccb *ccb;
  428 {
  429         struct scsi_low_softc *slp = SIM2SLP(sim);
  430         struct targ_info *ti;
  431         struct lun_info *li;
  432         struct slccb *cb;
  433         u_int lun, flags, msg, target;
  434         int s, rv;
  435 
  436         target = (u_int) (ccb->ccb_h.target_id);
  437         lun = (u_int) ccb->ccb_h.target_lun;
  438 
  439 #ifdef  SCSI_LOW_DEBUG
  440         if (SCSI_LOW_DEBUG_GO(SCSI_LOW_DEBUG_ACTION, target) != 0)
  441         {
  442                 device_printf(slp->sl_dev,
  443                     "cam_action: func code 0x%x target: %d, lun: %d\n",
  444                     ccb->ccb_h.func_code, target, lun);
  445         }
  446 #endif  /* SCSI_LOW_DEBUG */
  447 
  448         switch (ccb->ccb_h.func_code) {
  449         case XPT_SCSI_IO:       /* Execute the requested I/O operation */
  450 #ifdef  SCSI_LOW_DIAGNOSTIC
  451                 if (target == CAM_TARGET_WILDCARD || lun == CAM_LUN_WILDCARD)
  452                 {
  453                         device_printf(slp->sl_dev, "invalid target/lun\n");
  454                         ccb->ccb_h.status = CAM_REQ_INVALID;
  455                         xpt_done(ccb);
  456                         return;
  457                 }
  458 #endif  /* SCSI_LOW_DIAGNOSTIC */
  459 
  460                 if (((cb = SCSI_LOW_ALLOC_CCB(1)) == NULL)) {
  461                         ccb->ccb_h.status = CAM_RESRC_UNAVAIL;
  462                         xpt_done(ccb);
  463                         return;
  464                 }
  465 
  466                 ti = slp->sl_ti[target];
  467                 cb->osdep = ccb;
  468                 cb->bp = NULL;
  469                 if ((ccb->ccb_h.flags & CAM_DIS_AUTOSENSE) == 0)
  470                         flags = CCB_AUTOSENSE | CCB_SCSIIO;
  471                 else
  472                         flags = CCB_SCSIIO;
  473 
  474                 s = splcam();
  475                 li = scsi_low_alloc_li(ti, lun, 1);
  476 
  477                 if (ti->ti_setup_msg != 0)
  478                 {
  479                         scsi_low_message_enqueue(slp, ti, li, CCB_AUTOSENSE);
  480                 }
  481 
  482                 scsi_low_enqueue(slp, ti, li, cb, flags, 0);
  483 
  484 #ifdef  SCSI_LOW_DEBUG
  485                 if (SCSI_LOW_DEBUG_TEST_GO(SCSI_LOW_ABORT_CHECK, target) != 0)
  486                 {
  487                         scsi_low_test_abort(slp, ti, li);
  488                 }
  489 #endif  /* SCSI_LOW_DEBUG */
  490                 splx(s);
  491                 break;
  492 
  493         case XPT_EN_LUN:                /* Enable LUN as a target */
  494         case XPT_TARGET_IO:             /* Execute target I/O request */
  495         case XPT_ACCEPT_TARGET_IO:      /* Accept Host Target Mode CDB */
  496         case XPT_CONT_TARGET_IO:        /* Continue Host Target I/O Connection*/
  497                 /* XXX Implement */
  498                 ccb->ccb_h.status = CAM_REQ_INVALID;
  499                 xpt_done(ccb);
  500                 break;
  501 
  502         case XPT_ABORT:                 /* Abort the specified CCB */
  503 #ifdef  SCSI_LOW_DIAGNOSTIC
  504                 if (target == CAM_TARGET_WILDCARD || lun == CAM_LUN_WILDCARD)
  505                 {
  506                         device_printf(slp->sl_dev, "invalid target/lun\n");
  507                         ccb->ccb_h.status = CAM_REQ_INVALID;
  508                         xpt_done(ccb);
  509                         return;
  510                 }
  511 #endif  /* SCSI_LOW_DIAGNOSTIC */
  512 
  513                 s = splcam();
  514                 cb = scsi_low_find_ccb(slp, target, lun, ccb->cab.abort_ccb);
  515                 rv = scsi_low_abort_ccb(slp, cb);
  516                 splx(s);
  517 
  518                 if (rv == 0)
  519                         ccb->ccb_h.status = CAM_REQ_CMP;
  520                 else
  521                         ccb->ccb_h.status = CAM_REQ_INVALID;
  522                 xpt_done(ccb);
  523                 break;
  524 
  525         case XPT_SET_TRAN_SETTINGS: {
  526                 struct ccb_trans_settings_scsi *scsi;
  527                 struct ccb_trans_settings_spi *spi;
  528                 struct ccb_trans_settings *cts;
  529                 u_int val;
  530 
  531 #ifdef  SCSI_LOW_DIAGNOSTIC
  532                 if (target == CAM_TARGET_WILDCARD)
  533                 {
  534                         device_printf(slp->sl_dev, "invalid target\n");
  535                         ccb->ccb_h.status = CAM_REQ_INVALID;
  536                         xpt_done(ccb);
  537                         return;
  538                 }
  539 #endif  /* SCSI_LOW_DIAGNOSTIC */
  540                 cts = &ccb->cts;
  541                 ti = slp->sl_ti[target];
  542                 if (lun == CAM_LUN_WILDCARD)
  543                         lun = 0;
  544 
  545                 s = splcam();
  546                 scsi = &cts->proto_specific.scsi;
  547                 spi = &cts->xport_specific.spi;
  548                 if ((spi->valid & (CTS_SPI_VALID_BUS_WIDTH |
  549                                    CTS_SPI_VALID_SYNC_RATE |
  550                                    CTS_SPI_VALID_SYNC_OFFSET)) != 0)
  551                 {
  552                         if (spi->valid & CTS_SPI_VALID_BUS_WIDTH) {
  553                                 val = spi->bus_width;
  554                                 if (val < ti->ti_width)
  555                                         ti->ti_width = val;
  556                         }
  557                         if (spi->valid & CTS_SPI_VALID_SYNC_RATE) {
  558                                 val = spi->sync_period;
  559                                 if (val == 0 || val > ti->ti_maxsynch.period)
  560                                         ti->ti_maxsynch.period = val;
  561                         }
  562                         if (spi->valid & CTS_SPI_VALID_SYNC_OFFSET) {
  563                                 val = spi->sync_offset;
  564                                 if (val < ti->ti_maxsynch.offset)
  565                                         ti->ti_maxsynch.offset = val;
  566                         }
  567                         ti->ti_flags_valid |= SCSI_LOW_TARG_FLAGS_QUIRKS_VALID;
  568                         scsi_low_calcf_target(ti);
  569                 }
  570 
  571                 if ((spi->valid & CTS_SPI_FLAGS_DISC_ENB) != 0 ||
  572                     (scsi->flags & CTS_SCSI_FLAGS_TAG_ENB) != 0) {
  573 
  574                         li = scsi_low_alloc_li(ti, lun, 1);
  575                         if (spi->valid & CTS_SPI_FLAGS_DISC_ENB) {
  576                                 li->li_quirks |= SCSI_LOW_DISK_DISC;
  577                         } else {
  578                                 li->li_quirks &= ~SCSI_LOW_DISK_DISC;
  579                         }
  580 
  581                         if (scsi->flags & CTS_SCSI_FLAGS_TAG_ENB) {
  582                                 li->li_quirks |= SCSI_LOW_DISK_QTAG;
  583                         } else {
  584                                 li->li_quirks &= ~SCSI_LOW_DISK_QTAG;
  585                         }
  586                         li->li_flags_valid |= SCSI_LOW_LUN_FLAGS_QUIRKS_VALID;
  587                         scsi_low_calcf_target(ti);
  588                         scsi_low_calcf_lun(li);
  589                         if ((slp->sl_show_result & SHOW_CALCF_RES) != 0)
  590                                 scsi_low_calcf_show(li);
  591                 }
  592                 splx(s);
  593 
  594                 ccb->ccb_h.status = CAM_REQ_CMP;
  595                 xpt_done(ccb);
  596                 break;
  597         }
  598 
  599         case XPT_GET_TRAN_SETTINGS: {
  600                 struct ccb_trans_settings *cts;
  601                 u_int diskflags;
  602 
  603                 cts = &ccb->cts;
  604 #ifdef  SCSI_LOW_DIAGNOSTIC
  605                 if (target == CAM_TARGET_WILDCARD)
  606                 {
  607                         device_printf(slp->sl_dev, "invalid target\n");
  608                         ccb->ccb_h.status = CAM_REQ_INVALID;
  609                         xpt_done(ccb);
  610                         return;
  611                 }
  612 #endif  /* SCSI_LOW_DIAGNOSTIC */
  613                 ti = slp->sl_ti[target];
  614                 if (lun == CAM_LUN_WILDCARD)
  615                         lun = 0;
  616 
  617                 s = splcam();
  618                 li = scsi_low_alloc_li(ti, lun, 1);
  619                 if (li != NULL && cts->type == CTS_TYPE_CURRENT_SETTINGS) {
  620                         struct ccb_trans_settings_scsi *scsi =
  621                                 &cts->proto_specific.scsi;
  622                         struct ccb_trans_settings_spi *spi =
  623                                 &cts->xport_specific.spi;
  624 #ifdef  SCSI_LOW_DIAGNOSTIC
  625                         if (li->li_flags_valid != SCSI_LOW_LUN_FLAGS_ALL_VALID)
  626                         {
  627                                 ccb->ccb_h.status = CAM_FUNC_NOTAVAIL;
  628                                 device_printf(slp->sl_dev,
  629                                     "invalid GET_TRANS_CURRENT_SETTINGS call\n");
  630                                 goto settings_out;
  631                         }
  632 #endif  /* SCSI_LOW_DIAGNOSTIC */
  633                         cts->protocol = PROTO_SCSI;
  634                         cts->protocol_version = SCSI_REV_2;
  635                         cts->transport = XPORT_SPI;
  636                         cts->transport_version = 2;
  637 
  638                         scsi->flags &= ~CTS_SCSI_FLAGS_TAG_ENB;
  639                         spi->flags &= ~CTS_SPI_FLAGS_DISC_ENB;
  640 
  641                         diskflags = li->li_diskflags & li->li_cfgflags;
  642                         if (diskflags & SCSI_LOW_DISK_DISC)
  643                                 spi->flags |= CTS_SPI_FLAGS_DISC_ENB;
  644                         if (diskflags & SCSI_LOW_DISK_QTAG)
  645                                 scsi->flags |= CTS_SCSI_FLAGS_TAG_ENB;
  646 
  647                         spi->sync_period = ti->ti_maxsynch.period;
  648                         spi->valid |= CTS_SPI_VALID_SYNC_RATE;
  649                         spi->sync_offset = ti->ti_maxsynch.offset;
  650                         spi->valid |= CTS_SPI_VALID_SYNC_OFFSET;
  651 
  652                         spi->valid |= CTS_SPI_VALID_BUS_WIDTH;
  653                         spi->bus_width = ti->ti_width;
  654 
  655                         if (cts->ccb_h.target_lun != CAM_LUN_WILDCARD) {
  656                                 scsi->valid = CTS_SCSI_VALID_TQ;
  657                                 spi->valid |= CTS_SPI_VALID_DISC;
  658                         } else
  659                                 scsi->valid = 0;
  660                 } else
  661                         ccb->ccb_h.status = CAM_FUNC_NOTAVAIL;
  662 settings_out:
  663                 splx(s);
  664                 xpt_done(ccb);
  665                 break;
  666         }
  667 
  668         case XPT_CALC_GEOMETRY: { /* not yet HN2 */
  669                 cam_calc_geometry(&ccb->ccg, /*extended*/1);
  670                 xpt_done(ccb);
  671                 break;
  672         }
  673 
  674         case XPT_RESET_BUS:             /* Reset the specified SCSI bus */
  675                 s = splcam();
  676                 scsi_low_restart(slp, SCSI_LOW_RESTART_HARD, NULL);
  677                 splx(s);
  678                 ccb->ccb_h.status = CAM_REQ_CMP;
  679                 xpt_done(ccb);
  680                 break;
  681 
  682         case XPT_TERM_IO:       /* Terminate the I/O process */
  683                 ccb->ccb_h.status = CAM_REQ_INVALID;
  684                 xpt_done(ccb);
  685                 break;
  686 
  687         case XPT_RESET_DEV:     /* Bus Device Reset the specified SCSI device */
  688 #ifdef  SCSI_LOW_DIAGNOSTIC
  689                 if (target == CAM_TARGET_WILDCARD)
  690                 {
  691                         device_printf(slp->sl_dev, "invalid target\n");
  692                         ccb->ccb_h.status = CAM_REQ_INVALID;
  693                         xpt_done(ccb);
  694                         return;
  695                 }
  696 #endif  /* SCSI_LOW_DIAGNOSTIC */
  697 
  698                 msg = SCSI_LOW_MSG_RESET;
  699                 if (((cb = SCSI_LOW_ALLOC_CCB(1)) == NULL))
  700                 {
  701                         ccb->ccb_h.status = CAM_RESRC_UNAVAIL;
  702                         xpt_done(ccb);
  703                         return;
  704                 }
  705 
  706                 ti = slp->sl_ti[target];
  707                 if (lun == CAM_LUN_WILDCARD)
  708                         lun = 0;
  709                 cb->osdep = ccb;
  710                 cb->bp = NULL;
  711                 if ((ccb->ccb_h.flags & CAM_DIS_AUTOSENSE) == 0)
  712                         flags = CCB_AUTOSENSE | CCB_NORETRY | CCB_URGENT;
  713                 else
  714                         flags = CCB_NORETRY | CCB_URGENT;
  715 
  716                 s = splcam();
  717                 li = scsi_low_alloc_li(ti, lun, 1);
  718                 scsi_low_enqueue(slp, ti, li, cb, flags, msg);
  719                 splx(s);
  720                 break;
  721 
  722         case XPT_PATH_INQ: {            /* Path routing inquiry */
  723                 struct ccb_pathinq *cpi = &ccb->cpi;
  724                 
  725                 cpi->version_num = scsi_low_version_major;
  726                 cpi->hba_inquiry = PI_TAG_ABLE | PI_LINKED_CDB;
  727                 ti = slp->sl_ti[slp->sl_hostid];        /* host id */
  728                 if (ti->ti_width > SCSI_LOW_BUS_WIDTH_8)
  729                         cpi->hba_inquiry |= PI_WIDE_16;
  730                 if (ti->ti_width > SCSI_LOW_BUS_WIDTH_16)
  731                         cpi->hba_inquiry |= PI_WIDE_32;
  732                 if (ti->ti_maxsynch.offset > 0)
  733                         cpi->hba_inquiry |= PI_SDTR_ABLE;
  734                 cpi->target_sprt = 0;
  735                 cpi->hba_misc = 0;
  736                 cpi->hba_eng_cnt = 0;
  737                 cpi->max_target = slp->sl_ntargs - 1;
  738                 cpi->max_lun = slp->sl_nluns - 1;
  739                 cpi->initiator_id = slp->sl_hostid;
  740                 cpi->bus_id = cam_sim_bus(sim);
  741                 cpi->base_transfer_speed = 3300;
  742                 cpi->transport = XPORT_SPI;
  743                 cpi->transport_version = 2;
  744                 cpi->protocol = PROTO_SCSI;
  745                 cpi->protocol_version = SCSI_REV_2;
  746                 strncpy(cpi->sim_vid, "FreeBSD", SIM_IDLEN);
  747                 strncpy(cpi->hba_vid, "SCSI_LOW", HBA_IDLEN);
  748                 strncpy(cpi->dev_name, cam_sim_name(sim), DEV_IDLEN);
  749                 cpi->unit_number = cam_sim_unit(sim);
  750                 cpi->ccb_h.status = CAM_REQ_CMP;
  751                 xpt_done(ccb);
  752                 break;
  753         }
  754 
  755         default:
  756                 printf("scsi_low: non support func_code = %d ",
  757                         ccb->ccb_h.func_code);
  758                 ccb->ccb_h.status = CAM_REQ_INVALID;
  759                 xpt_done(ccb);
  760                 break;
  761         }
  762 }
  763 
  764 static int
  765 scsi_low_attach_cam(slp)
  766         struct scsi_low_softc *slp;
  767 {
  768         struct cam_devq *devq;
  769         int tagged_openings;
  770 
  771         devq = cam_simq_alloc(SCSI_LOW_NCCB);
  772         if (devq == NULL)
  773                 return (ENOMEM);
  774 
  775         /*
  776          * ask the adapter what subunits are present
  777          */
  778         tagged_openings = min(slp->sl_openings, SCSI_LOW_MAXNEXUS);
  779         slp->sl_si.sim = cam_sim_alloc(scsi_low_scsi_action_cam,
  780                                 scsi_low_poll_cam,
  781                                 device_get_name(slp->sl_dev), slp,
  782                                 device_get_unit(slp->sl_dev), &Giant,
  783                                 slp->sl_openings, tagged_openings, devq);
  784 
  785         if (slp->sl_si.sim == NULL) {
  786                 cam_simq_free(devq);
  787                 return ENODEV;
  788         }
  789 
  790         if (xpt_bus_register(slp->sl_si.sim, NULL, 0) != CAM_SUCCESS) {
  791                 free(slp->sl_si.sim, M_SCSILOW);
  792                 return ENODEV;
  793         }
  794        
  795         if (xpt_create_path(&slp->sl_si.path, /*periph*/NULL,
  796                         cam_sim_path(slp->sl_si.sim), CAM_TARGET_WILDCARD,
  797                         CAM_LUN_WILDCARD) != CAM_REQ_CMP) {
  798                 xpt_bus_deregister(cam_sim_path(slp->sl_si.sim));
  799                 cam_sim_free(slp->sl_si.sim, /*free_simq*/TRUE);
  800                 return ENODEV;
  801         }
  802 
  803         slp->sl_show_result = SHOW_CALCF_RES;           /* OK ? */
  804         return 0;
  805 }
  806 
  807 static int
  808 scsi_low_world_start_cam(slp)
  809         struct scsi_low_softc *slp;
  810 {
  811 
  812         return 0;
  813 }
  814 
  815 static int
  816 scsi_low_dettach_cam(slp)
  817         struct scsi_low_softc *slp;
  818 {
  819 
  820         xpt_async(AC_LOST_DEVICE, slp->sl_si.path, NULL);
  821         xpt_free_path(slp->sl_si.path);
  822         xpt_bus_deregister(cam_sim_path(slp->sl_si.sim));
  823         cam_sim_free(slp->sl_si.sim, /* free_devq */ TRUE);
  824         return 0;
  825 }
  826 
  827 static int
  828 scsi_low_ccb_setup_cam(slp, cb)
  829         struct scsi_low_softc *slp;
  830         struct slccb *cb;
  831 {
  832         union ccb *ccb = (union ccb *) cb->osdep;
  833 
  834         if ((cb->ccb_flags & CCB_SCSIIO) != 0)
  835         {
  836                 cb->ccb_scp.scp_cmd = ccb->csio.cdb_io.cdb_bytes;
  837                 cb->ccb_scp.scp_cmdlen = (int) ccb->csio.cdb_len;
  838                 cb->ccb_scp.scp_data = ccb->csio.data_ptr;
  839                 cb->ccb_scp.scp_datalen = (int) ccb->csio.dxfer_len;
  840                 if((ccb->ccb_h.flags & CAM_DIR_MASK) == CAM_DIR_OUT)
  841                         cb->ccb_scp.scp_direction = SCSI_LOW_WRITE;
  842                 else /* if((ccb->ccb_h.flags & CAM_DIR_MASK) == CAM_DIR_IN) */
  843                         cb->ccb_scp.scp_direction = SCSI_LOW_READ;
  844                 cb->ccb_tcmax = ccb->ccb_h.timeout / 1000;
  845         }
  846         else
  847         {
  848                 scsi_low_unit_ready_cmd(cb);
  849         }
  850         return SCSI_LOW_START_QTAG;
  851 }
  852 
  853 static int
  854 scsi_low_done_cam(slp, cb)
  855         struct scsi_low_softc *slp;
  856         struct slccb *cb;
  857 {
  858         union ccb *ccb;
  859 
  860         ccb = (union ccb *) cb->osdep;
  861         if (cb->ccb_error == 0)
  862         {
  863                 ccb->ccb_h.status = CAM_REQ_CMP;
  864                 ccb->csio.resid = 0;
  865         }
  866         else    
  867         {
  868                 if (cb->ccb_rcnt >= slp->sl_max_retry)
  869                         cb->ccb_error |= ABORTIO;
  870 
  871                 if ((cb->ccb_flags & CCB_NORETRY) == 0 &&
  872                     (cb->ccb_error & ABORTIO) == 0)
  873                         return EJUSTRETURN;
  874 
  875                 if ((cb->ccb_error & SENSEIO) != 0)
  876                 {
  877                         memcpy(&ccb->csio.sense_data,
  878                                &cb->ccb_sense,
  879                                sizeof(ccb->csio.sense_data));
  880                 }
  881 
  882                 ccb->ccb_h.status = scsi_low_translate_error_code(cb,
  883                                         &scsi_low_error_code_cam[0]);
  884         
  885 #ifdef  SCSI_LOW_DIAGNOSTIC
  886                 if ((cb->ccb_flags & CCB_SILENT) == 0 &&
  887                     cb->ccb_scp.scp_cmdlen > 0 &&
  888                     (scsi_low_cmd_flags[cb->ccb_scp.scp_cmd[0]] &
  889                      SCSI_LOW_CMD_ABORT_WARNING) != 0)
  890                 {
  891                         device_printf(slp->sl_dev,
  892                             "WARNING: scsi_low IO abort\n");
  893                         scsi_low_print(slp, NULL);
  894                 }
  895 #endif  /* SCSI_LOW_DIAGNOSTIC */
  896         }
  897 
  898         if ((ccb->ccb_h.status & CAM_STATUS_MASK) == 0)
  899                 ccb->ccb_h.status |= CAM_REQ_CMP_ERR;
  900 
  901         if (cb->ccb_scp.scp_status == ST_UNKNOWN)
  902                 ccb->csio.scsi_status = 0;      /* XXX */
  903         else
  904                 ccb->csio.scsi_status = cb->ccb_scp.scp_status;
  905 
  906         if ((cb->ccb_flags & CCB_NOSDONE) == 0)
  907                 xpt_done(ccb);
  908         return 0;
  909 }
  910 
  911 static void
  912 scsi_low_timeout_cam(slp, ch, action)
  913         struct scsi_low_softc *slp;
  914         int ch;
  915         int action;
  916 {
  917 
  918         switch (ch)
  919         {
  920         case SCSI_LOW_TIMEOUT_CH_IO:
  921                 switch (action)
  922                 {
  923                 case SCSI_LOW_TIMEOUT_START:
  924                         slp->sl_si.timeout_ch = timeout(scsi_low_timeout, slp,
  925                                 hz / SCSI_LOW_TIMEOUT_HZ);
  926                         break;
  927                 case SCSI_LOW_TIMEOUT_STOP:
  928                         untimeout(scsi_low_timeout, slp, slp->sl_si.timeout_ch);
  929                         break;
  930                 }
  931                 break;
  932 
  933         case SCSI_LOW_TIMEOUT_CH_ENGAGE:
  934                 switch (action)
  935                 {
  936                 case SCSI_LOW_TIMEOUT_START:
  937                         slp->sl_si.engage_ch = timeout(scsi_low_engage, slp, 1);
  938                         break;
  939                 case SCSI_LOW_TIMEOUT_STOP:
  940                         untimeout(scsi_low_engage, slp, slp->sl_si.engage_ch);
  941                         break;
  942                 }
  943                 break;
  944         case SCSI_LOW_TIMEOUT_CH_RECOVER:
  945                 break;
  946         }
  947 }
  948 
  949 /*=============================================================
  950  * END OF OS switch  (All OS depend fucntions should be above)
  951  =============================================================*/
  952 
  953 /**************************************************************
  954  * scsi low deactivate and activate
  955  **************************************************************/
  956 int
  957 scsi_low_is_busy(slp)
  958         struct scsi_low_softc *slp;
  959 {
  960 
  961         if (slp->sl_nio > 0)
  962                 return EBUSY;
  963         return 0;
  964 }
  965 
  966 int
  967 scsi_low_deactivate(slp)
  968         struct scsi_low_softc *slp;
  969 {
  970         int s;
  971 
  972         s = splcam();
  973         slp->sl_flags |= HW_INACTIVE;
  974         (*slp->sl_osdep_fp->scsi_low_osdep_timeout)
  975                 (slp, SCSI_LOW_TIMEOUT_CH_IO, SCSI_LOW_TIMEOUT_STOP);
  976         (*slp->sl_osdep_fp->scsi_low_osdep_timeout)
  977                 (slp, SCSI_LOW_TIMEOUT_CH_ENGAGE, SCSI_LOW_TIMEOUT_STOP);
  978         splx(s);
  979         return 0;
  980 }
  981 
  982 int
  983 scsi_low_activate(slp)
  984         struct scsi_low_softc *slp;
  985 {
  986         int error, s;
  987 
  988         s = splcam();
  989         slp->sl_flags &= ~HW_INACTIVE;
  990         if ((error = scsi_low_restart(slp, SCSI_LOW_RESTART_HARD, NULL)) != 0)
  991         {
  992                 slp->sl_flags |= HW_INACTIVE;
  993                 splx(s);
  994                 return error;
  995         }
  996 
  997         slp->sl_timeout_count = 0;
  998         (*slp->sl_osdep_fp->scsi_low_osdep_timeout)
  999                 (slp, SCSI_LOW_TIMEOUT_CH_IO, SCSI_LOW_TIMEOUT_START);
 1000         splx(s);
 1001         return 0;
 1002 }
 1003 
 1004 /**************************************************************
 1005  * scsi low log
 1006  **************************************************************/
 1007 #ifdef  SCSI_LOW_DIAGNOSTIC
 1008 static void scsi_low_msg_log_init(struct scsi_low_msg_log *);
 1009 static void scsi_low_msg_log_write(struct scsi_low_msg_log *, u_int8_t *, int);
 1010 static void scsi_low_msg_log_show(struct scsi_low_msg_log *, char *, int);
 1011 
 1012 static void
 1013 scsi_low_msg_log_init(slmlp)
 1014         struct scsi_low_msg_log *slmlp;
 1015 {
 1016 
 1017         slmlp->slml_ptr = 0;
 1018 }
 1019 
 1020 static void
 1021 scsi_low_msg_log_write(slmlp, datap, len)
 1022         struct scsi_low_msg_log *slmlp;
 1023         u_int8_t *datap;
 1024         int len;
 1025 {
 1026         int ptr, ind;
 1027 
 1028         if (slmlp->slml_ptr >= SCSI_LOW_MSG_LOG_DATALEN)
 1029                 return;
 1030 
 1031         ptr = slmlp->slml_ptr ++;
 1032         for (ind = 0; ind < sizeof(slmlp->slml_msg[0]) && ind < len; ind ++)
 1033                 slmlp->slml_msg[ptr].msg[ind] = datap[ind];
 1034         for ( ; ind < sizeof(slmlp->slml_msg[0]); ind ++)
 1035                 slmlp->slml_msg[ptr].msg[ind] = 0;
 1036 }
 1037         
 1038 static void
 1039 scsi_low_msg_log_show(slmlp, s, len)
 1040         struct scsi_low_msg_log *slmlp;
 1041         char *s;
 1042         int len;
 1043 {
 1044         int ptr, ind;
 1045 
 1046         printf("%s: (%d) ", s, slmlp->slml_ptr);
 1047         for (ptr = 0; ptr < slmlp->slml_ptr; ptr ++)
 1048         {
 1049                 for (ind = 0; ind < len && ind < sizeof(slmlp->slml_msg[0]);
 1050                      ind ++)
 1051                 {
 1052                         printf("[%x]", (u_int) slmlp->slml_msg[ptr].msg[ind]);
 1053                 }
 1054                 printf(">");
 1055         }
 1056         printf("\n");
 1057 }
 1058 #endif  /* SCSI_LOW_DIAGNOSTIC */
 1059 
 1060 /**************************************************************
 1061  * power control
 1062  **************************************************************/
 1063 static void
 1064 scsi_low_engage(arg)
 1065         void *arg;
 1066 {
 1067         struct scsi_low_softc *slp = arg;
 1068         int s = splcam();
 1069 
 1070         switch (slp->sl_rstep)
 1071         {
 1072         case 0:
 1073                 slp->sl_rstep ++;
 1074                 (*slp->sl_funcs->scsi_low_power) (slp, SCSI_LOW_ENGAGE);
 1075                 (*slp->sl_osdep_fp->scsi_low_osdep_timeout) (slp, 
 1076                         SCSI_LOW_TIMEOUT_CH_ENGAGE, SCSI_LOW_TIMEOUT_START);
 1077                 break;
 1078 
 1079         case 1:
 1080                 slp->sl_rstep ++;
 1081                 slp->sl_flags &= ~HW_RESUME;
 1082                 scsi_low_start(slp);
 1083                 break;
 1084 
 1085         case 2:
 1086                 break;
 1087         }
 1088         splx(s);
 1089 }
 1090 
 1091 static int
 1092 scsi_low_init(slp, flags)
 1093         struct scsi_low_softc *slp;
 1094         u_int flags;
 1095 {
 1096         int rv = 0;
 1097 
 1098         slp->sl_flags |= HW_INITIALIZING;
 1099 
 1100         /* clear power control timeout */
 1101         if ((slp->sl_flags & HW_POWERCTRL) != 0)
 1102         {
 1103                 (*slp->sl_osdep_fp->scsi_low_osdep_timeout) (slp, 
 1104                         SCSI_LOW_TIMEOUT_CH_ENGAGE, SCSI_LOW_TIMEOUT_STOP);
 1105                 slp->sl_flags &= ~(HW_POWDOWN | HW_RESUME);
 1106                 slp->sl_active = 1;
 1107                 slp->sl_powc = SCSI_LOW_POWDOWN_TC;
 1108         }
 1109 
 1110         /* reset current nexus */
 1111         scsi_low_reset_nexus(slp, flags);
 1112         if ((slp->sl_flags & HW_INACTIVE) != 0)
 1113         {
 1114                 rv = EBUSY;
 1115                 goto out;
 1116         }
 1117 
 1118         if (flags != SCSI_LOW_RESTART_SOFT)
 1119         {
 1120                 rv = ((*slp->sl_funcs->scsi_low_init) (slp, flags));
 1121         }
 1122 
 1123 out:
 1124         slp->sl_flags &= ~HW_INITIALIZING;
 1125         return rv;
 1126 }
 1127 
 1128 /**************************************************************
 1129  * allocate lun_info
 1130  **************************************************************/
 1131 static struct lun_info *
 1132 scsi_low_alloc_li(ti, lun, alloc)
 1133         struct targ_info *ti;
 1134         int lun;
 1135         int alloc;
 1136 {
 1137         struct scsi_low_softc *slp = ti->ti_sc;
 1138         struct lun_info *li;
 1139 
 1140         li = LIST_FIRST(&ti->ti_litab); 
 1141         if (li != NULL)
 1142         { 
 1143                 if (li->li_lun == lun)
 1144                         return li;
 1145 
 1146                 while ((li = LIST_NEXT(li, lun_chain)) != NULL)
 1147                 {
 1148                         if (li->li_lun == lun)
 1149                         {
 1150                                 LIST_REMOVE(li, lun_chain);
 1151                                 LIST_INSERT_HEAD(&ti->ti_litab, li, lun_chain);
 1152                                 return li;
 1153                         }
 1154                 }
 1155         }
 1156 
 1157         if (alloc == 0)
 1158                 return li;
 1159 
 1160         li = SCSI_LOW_MALLOC(ti->ti_lunsize);
 1161         if (li == NULL)
 1162                 panic("no lun info mem");
 1163 
 1164         bzero(li, ti->ti_lunsize);
 1165         li->li_lun = lun;
 1166         li->li_ti = ti;
 1167 
 1168         li->li_cfgflags = SCSI_LOW_SYNC | SCSI_LOW_LINK | SCSI_LOW_DISC |
 1169                           SCSI_LOW_QTAG;
 1170         li->li_quirks = li->li_diskflags = SCSI_LOW_DISK_LFLAGS;
 1171         li->li_flags_valid = SCSI_LOW_LUN_FLAGS_USER_VALID;
 1172 #ifdef  SCSI_LOW_FLAGS_QUIRKS_OK
 1173         li->li_flags_valid |= SCSI_LOW_LUN_FLAGS_QUIRKS_VALID;
 1174 #endif  /* SCSI_LOW_FLAGS_QUIRKS_OK */
 1175 
 1176         li->li_qtagbits = (u_int) -1;
 1177 
 1178         TAILQ_INIT(&li->li_discq);
 1179         LIST_INSERT_HEAD(&ti->ti_litab, li, lun_chain);
 1180 
 1181         /* host specific structure initialization per lun */
 1182         if (slp->sl_funcs->scsi_low_lun_init != NULL)
 1183                 (*slp->sl_funcs->scsi_low_lun_init)
 1184                         (slp, ti, li, SCSI_LOW_INFO_ALLOC);
 1185         scsi_low_calcf_lun(li);
 1186         return li;
 1187 }
 1188 
 1189 /**************************************************************
 1190  * allocate targ_info
 1191  **************************************************************/
 1192 static struct targ_info *
 1193 scsi_low_alloc_ti(slp, targ)
 1194         struct scsi_low_softc *slp;
 1195         int targ;
 1196 {
 1197         struct targ_info *ti;
 1198 
 1199         if (TAILQ_FIRST(&slp->sl_titab) == NULL)
 1200                 TAILQ_INIT(&slp->sl_titab);
 1201 
 1202         ti = SCSI_LOW_MALLOC(slp->sl_targsize);
 1203         if (ti == NULL)
 1204                 panic("%s short of memory", device_get_nameunit(slp->sl_dev));
 1205 
 1206         bzero(ti, slp->sl_targsize);
 1207         ti->ti_id = targ;
 1208         ti->ti_sc = slp;
 1209 
 1210         slp->sl_ti[targ] = ti;
 1211         TAILQ_INSERT_TAIL(&slp->sl_titab, ti, ti_chain);
 1212         LIST_INIT(&ti->ti_litab);
 1213 
 1214         ti->ti_quirks = ti->ti_diskflags = SCSI_LOW_DISK_TFLAGS;
 1215         ti->ti_owidth = SCSI_LOW_BUS_WIDTH_8;
 1216         ti->ti_flags_valid = SCSI_LOW_TARG_FLAGS_USER_VALID;
 1217 #ifdef  SCSI_LOW_FLAGS_QUIRKS_OK
 1218         ti->ti_flags_valid |= SCSI_LOW_TARG_FLAGS_QUIRKS_VALID;
 1219 #endif  /* SCSI_LOW_FLAGS_QUIRKS_OK */
 1220 
 1221         if (slp->sl_funcs->scsi_low_targ_init != NULL)
 1222         {
 1223                 (*slp->sl_funcs->scsi_low_targ_init)
 1224                         (slp, ti, SCSI_LOW_INFO_ALLOC);
 1225         }
 1226         scsi_low_calcf_target(ti);
 1227         return ti;
 1228 }
 1229 
 1230 static void
 1231 scsi_low_free_ti(slp)
 1232         struct scsi_low_softc *slp;
 1233 {
 1234         struct targ_info *ti, *tib;
 1235         struct lun_info *li, *nli;
 1236 
 1237         for (ti = TAILQ_FIRST(&slp->sl_titab); ti; ti = tib)
 1238         {
 1239                 for (li = LIST_FIRST(&ti->ti_litab); li != NULL; li = nli)
 1240                 {
 1241                         if (slp->sl_funcs->scsi_low_lun_init != NULL)
 1242                         {
 1243                                 (*slp->sl_funcs->scsi_low_lun_init)
 1244                                         (slp, ti, li, SCSI_LOW_INFO_DEALLOC);
 1245                         }
 1246                         nli = LIST_NEXT(li, lun_chain);
 1247                         SCSI_LOW_FREE(li);
 1248                 }
 1249 
 1250                 if (slp->sl_funcs->scsi_low_targ_init != NULL)
 1251                 {
 1252                         (*slp->sl_funcs->scsi_low_targ_init)
 1253                                 (slp, ti, SCSI_LOW_INFO_DEALLOC);
 1254                 }
 1255                 tib = TAILQ_NEXT(ti, ti_chain);
 1256                 SCSI_LOW_FREE(ti);
 1257         }
 1258 }
 1259 
 1260 /**************************************************************
 1261  * timeout
 1262  **************************************************************/
 1263 void
 1264 scsi_low_bus_idle(slp)
 1265         struct scsi_low_softc *slp;
 1266 {
 1267 
 1268         slp->sl_retry_sel = 0;
 1269         if (slp->sl_Tnexus == NULL)
 1270                 scsi_low_start(slp);
 1271 }
 1272 
 1273 static void
 1274 scsi_low_timeout(arg)
 1275         void *arg;
 1276 {
 1277         struct scsi_low_softc *slp = arg;
 1278         int s;
 1279 
 1280         s = splcam();
 1281         (void) scsi_low_timeout_check(slp);
 1282         (*slp->sl_osdep_fp->scsi_low_osdep_timeout)
 1283                 (slp, SCSI_LOW_TIMEOUT_CH_IO, SCSI_LOW_TIMEOUT_START);
 1284         splx(s);
 1285 }
 1286 
 1287 static int
 1288 scsi_low_timeout_check(slp)
 1289         struct scsi_low_softc *slp;
 1290 {
 1291         struct targ_info *ti;
 1292         struct lun_info *li;
 1293         struct slccb *cb = NULL;                /* XXX */
 1294 
 1295         /* selection restart */
 1296         if (slp->sl_retry_sel != 0)
 1297         {
 1298                 slp->sl_retry_sel = 0;
 1299                 if (slp->sl_Tnexus != NULL)
 1300                         goto step1;
 1301 
 1302                 cb = TAILQ_FIRST(&slp->sl_start);
 1303                 if (cb == NULL)
 1304                         goto step1;
 1305 
 1306                 if (cb->ccb_selrcnt >= SCSI_LOW_MAX_SELECTION_RETRY)
 1307                 {
 1308                         cb->ccb_flags |= CCB_NORETRY;
 1309                         cb->ccb_error |= SELTIMEOUTIO;
 1310                         if (scsi_low_revoke_ccb(slp, cb, 1) != NULL)
 1311                                 panic("%s: ccb not finished",
 1312                                     device_get_nameunit(slp->sl_dev));
 1313                 }
 1314 
 1315                 if (slp->sl_Tnexus == NULL)
 1316                         scsi_low_start(slp);
 1317         }
 1318 
 1319         /* call hardware timeout */
 1320 step1:
 1321         if (slp->sl_funcs->scsi_low_timeout != NULL)
 1322         {
 1323                 (*slp->sl_funcs->scsi_low_timeout) (slp);
 1324         }
 1325         
 1326         if (slp->sl_timeout_count ++ < 
 1327             SCSI_LOW_TIMEOUT_CHECK_INTERVAL * SCSI_LOW_TIMEOUT_HZ)
 1328                 return 0;
 1329 
 1330         slp->sl_timeout_count = 0;
 1331         if (slp->sl_nio > 0)
 1332         {
 1333                 if ((cb = slp->sl_Qnexus) != NULL)
 1334                 {
 1335                         cb->ccb_tc -= SCSI_LOW_TIMEOUT_CHECK_INTERVAL;
 1336                         if (cb->ccb_tc < 0)
 1337                                 goto bus_reset;
 1338                 }
 1339                 else if (slp->sl_disc == 0)
 1340                 {
 1341                         if ((cb = TAILQ_FIRST(&slp->sl_start)) == NULL)
 1342                                 return 0;
 1343 
 1344                         cb->ccb_tc -= SCSI_LOW_TIMEOUT_CHECK_INTERVAL;
 1345                         if (cb->ccb_tc < 0)
 1346                                 goto bus_reset;
 1347                 }
 1348                 else for (ti = TAILQ_FIRST(&slp->sl_titab); ti != NULL;
 1349                           ti = TAILQ_NEXT(ti, ti_chain))
 1350                 {
 1351                         if (ti->ti_disc == 0)
 1352                                 continue;
 1353 
 1354                         for (li = LIST_FIRST(&ti->ti_litab); li != NULL;
 1355                              li = LIST_NEXT(li, lun_chain))
 1356                         {
 1357                                 for (cb = TAILQ_FIRST(&li->li_discq); 
 1358                                      cb != NULL;
 1359                                      cb = TAILQ_NEXT(cb, ccb_chain))
 1360                                 {
 1361                                         cb->ccb_tc -=
 1362                                                 SCSI_LOW_TIMEOUT_CHECK_INTERVAL;
 1363                                         if (cb->ccb_tc < 0)
 1364                                                 goto bus_reset;
 1365                                 }
 1366                         }
 1367                 }
 1368 
 1369         }
 1370         else if ((slp->sl_flags & HW_POWERCTRL) != 0)
 1371         {
 1372                 if ((slp->sl_flags & (HW_POWDOWN | HW_RESUME)) != 0)
 1373                         return 0;
 1374 
 1375                 if (slp->sl_active != 0)
 1376                 {
 1377                         slp->sl_powc = SCSI_LOW_POWDOWN_TC;
 1378                         slp->sl_active = 0;
 1379                         return 0;
 1380                 }
 1381 
 1382                 slp->sl_powc --;
 1383                 if (slp->sl_powc < 0)
 1384                 {
 1385                         slp->sl_powc = SCSI_LOW_POWDOWN_TC;
 1386                         slp->sl_flags |= HW_POWDOWN;
 1387                         (*slp->sl_funcs->scsi_low_power)
 1388                                         (slp, SCSI_LOW_POWDOWN);
 1389                 }
 1390         }
 1391         return 0;
 1392 
 1393 bus_reset:
 1394         cb->ccb_error |= TIMEOUTIO;
 1395         device_printf(slp->sl_dev, "slccb (0x%lx) timeout!\n", (u_long) cb);
 1396         scsi_low_info(slp, NULL, "scsi bus hangup. try to recover.");
 1397         scsi_low_init(slp, SCSI_LOW_RESTART_HARD);
 1398         scsi_low_start(slp);
 1399         return ERESTART;
 1400 }
 1401 
 1402 
 1403 static int
 1404 scsi_low_abort_ccb(slp, cb)
 1405         struct scsi_low_softc *slp;
 1406         struct slccb *cb;
 1407 {
 1408         struct targ_info *ti;
 1409         struct lun_info *li;
 1410         u_int msg;
 1411 
 1412         if (cb == NULL)
 1413                 return EINVAL;
 1414         if ((cb->ccb_omsgoutflag & 
 1415              (SCSI_LOW_MSG_ABORT | SCSI_LOW_MSG_ABORT_QTAG)) != 0)
 1416                 return EBUSY;
 1417 
 1418         ti = cb->ti;
 1419         li = cb->li;
 1420         if (cb->ccb_tag == SCSI_LOW_UNKTAG)
 1421                 msg = SCSI_LOW_MSG_ABORT;
 1422         else
 1423                 msg = SCSI_LOW_MSG_ABORT_QTAG;
 1424 
 1425         cb->ccb_error |= ABORTIO;
 1426         cb->ccb_flags |= CCB_NORETRY;
 1427         scsi_low_ccb_message_assert(cb, msg);
 1428 
 1429         if (cb == slp->sl_Qnexus)
 1430         {
 1431                 scsi_low_assert_msg(slp, ti, msg, 1);
 1432         }
 1433         else if ((cb->ccb_flags & CCB_DISCQ) != 0)
 1434         {
 1435                 if (scsi_low_revoke_ccb(slp, cb, 0) == NULL)
 1436                         panic("%s: revoked ccb done",
 1437                             device_get_nameunit(slp->sl_dev));
 1438 
 1439                 cb->ccb_flags |= CCB_STARTQ;
 1440                 TAILQ_INSERT_HEAD(&slp->sl_start, cb, ccb_chain);
 1441 
 1442                 if (slp->sl_Tnexus == NULL)
 1443                         scsi_low_start(slp);
 1444         }
 1445         else
 1446         {
 1447                 if (scsi_low_revoke_ccb(slp, cb, 1) != NULL)
 1448                         panic("%s: revoked ccb retried",
 1449                             device_get_nameunit(slp->sl_dev));
 1450         }
 1451         return 0;
 1452 }
 1453 
 1454 /**************************************************************
 1455  * Generic SCSI INTERFACE
 1456  **************************************************************/
 1457 int
 1458 scsi_low_attach(slp, openings, ntargs, nluns, targsize, lunsize)
 1459         struct scsi_low_softc *slp;
 1460         int openings, ntargs, nluns, targsize, lunsize;
 1461 {
 1462         struct targ_info *ti;
 1463         struct lun_info *li;
 1464         int s, i, nccb, rv;
 1465 
 1466         slp->sl_osdep_fp = &scsi_low_osdep_funcs_cam;
 1467 
 1468         if (slp->sl_osdep_fp == NULL)
 1469                 panic("scsi_low: interface not spcified");
 1470 
 1471         if (ntargs > SCSI_LOW_NTARGETS)
 1472         {
 1473                 printf("scsi_low: %d targets are too large\n", ntargs);
 1474                 printf("change kernel options SCSI_LOW_NTARGETS");
 1475                 return EINVAL;
 1476         }
 1477 
 1478         if (openings <= 0)
 1479                 slp->sl_openings = (SCSI_LOW_NCCB / ntargs);
 1480         else
 1481                 slp->sl_openings = openings;
 1482         slp->sl_ntargs = ntargs;
 1483         slp->sl_nluns = nluns;
 1484         slp->sl_max_retry = SCSI_LOW_MAX_RETRY;
 1485 
 1486         if (lunsize < sizeof(struct lun_info))
 1487                 lunsize = sizeof(struct lun_info);
 1488 
 1489         if (targsize < sizeof(struct targ_info))
 1490                 targsize = sizeof(struct targ_info);
 1491 
 1492         slp->sl_targsize = targsize;
 1493         for (i = 0; i < ntargs; i ++)
 1494         {
 1495                 ti = scsi_low_alloc_ti(slp, i);
 1496                 ti->ti_lunsize = lunsize;
 1497                 li = scsi_low_alloc_li(ti, 0, 1);
 1498         }
 1499 
 1500         /* initialize queue */
 1501         nccb = openings * ntargs;
 1502         if (nccb >= SCSI_LOW_NCCB || nccb <= 0)
 1503                 nccb = SCSI_LOW_NCCB;
 1504         scsi_low_init_ccbque(nccb);
 1505         TAILQ_INIT(&slp->sl_start);
 1506 
 1507         /* call os depend attach */
 1508         s = splcam();
 1509         rv = (*slp->sl_osdep_fp->scsi_low_osdep_attach) (slp);
 1510         if (rv != 0)
 1511         {
 1512                 splx(s);
 1513                 device_printf(slp->sl_dev,
 1514                     "scsi_low_attach: osdep attach failed\n");
 1515                 return EINVAL;
 1516         }
 1517 
 1518         /* check hardware */
 1519         DELAY(1000);    /* wait for 1ms */
 1520         if (scsi_low_init(slp, SCSI_LOW_RESTART_HARD) != 0)
 1521         {
 1522                 splx(s);
 1523                 device_printf(slp->sl_dev,
 1524                     "scsi_low_attach: initialization failed\n");
 1525                 return EINVAL;
 1526         }
 1527 
 1528         /* start watch dog */
 1529         slp->sl_timeout_count = 0;
 1530         (*slp->sl_osdep_fp->scsi_low_osdep_timeout)
 1531                  (slp, SCSI_LOW_TIMEOUT_CH_IO, SCSI_LOW_TIMEOUT_START);
 1532         LIST_INSERT_HEAD(&sl_tab, slp, sl_chain);
 1533 
 1534         /* fake call */
 1535         scsi_low_abort_ccb(slp, scsi_low_find_ccb(slp, 0, 0, NULL));
 1536 
 1537 #ifdef  SCSI_LOW_START_UP_CHECK
 1538         /* probing devices */
 1539         scsi_low_start_up(slp);
 1540 #endif  /* SCSI_LOW_START_UP_CHECK */
 1541 
 1542         /* call os depend attach done*/
 1543         (*slp->sl_osdep_fp->scsi_low_osdep_world_start) (slp);
 1544         splx(s);
 1545         return 0;
 1546 }
 1547 
 1548 int
 1549 scsi_low_dettach(slp)
 1550         struct scsi_low_softc *slp;
 1551 {
 1552         int s, rv;
 1553 
 1554         s = splcam();
 1555         if (scsi_low_is_busy(slp) != 0)
 1556         {
 1557                 splx(s);
 1558                 return EBUSY;
 1559         }
 1560 
 1561         scsi_low_deactivate(slp);
 1562 
 1563         rv = (*slp->sl_osdep_fp->scsi_low_osdep_dettach) (slp);
 1564         if (rv != 0)
 1565         {
 1566                 splx(s);
 1567                 return EBUSY;
 1568         }
 1569 
 1570         scsi_low_free_ti(slp);
 1571         LIST_REMOVE(slp, sl_chain);
 1572         splx(s);
 1573         return 0;
 1574 }
 1575 
 1576 /**************************************************************
 1577  * Generic enqueue
 1578  **************************************************************/
 1579 static int
 1580 scsi_low_enqueue(slp, ti, li, cb, flags, msg)
 1581         struct scsi_low_softc *slp;
 1582         struct targ_info *ti;
 1583         struct lun_info *li;
 1584         struct slccb *cb;
 1585         u_int flags, msg;
 1586 {       
 1587 
 1588         cb->ti = ti;
 1589         cb->li = li;
 1590 
 1591         scsi_low_ccb_message_assert(cb, msg);
 1592 
 1593         cb->ccb_otag = cb->ccb_tag = SCSI_LOW_UNKTAG;
 1594         scsi_low_alloc_qtag(cb);
 1595 
 1596         cb->ccb_flags = flags | CCB_STARTQ;
 1597         cb->ccb_tc = cb->ccb_tcmax = SCSI_LOW_MIN_TOUT;
 1598         cb->ccb_error |= PENDINGIO;
 1599 
 1600         if ((flags & CCB_URGENT) != 0)
 1601         {
 1602                 TAILQ_INSERT_HEAD(&slp->sl_start, cb, ccb_chain);
 1603         }
 1604         else
 1605         {
 1606                 TAILQ_INSERT_TAIL(&slp->sl_start, cb, ccb_chain);
 1607         }
 1608 
 1609         slp->sl_nio ++;
 1610 
 1611         if (slp->sl_Tnexus == NULL)
 1612                 scsi_low_start(slp);
 1613         return 0;
 1614 }
 1615 
 1616 static int
 1617 scsi_low_message_enqueue(slp, ti, li, flags)
 1618         struct scsi_low_softc *slp;
 1619         struct targ_info *ti;
 1620         struct lun_info *li;
 1621         u_int flags;
 1622 {
 1623         struct slccb *cb;
 1624         u_int tmsgflags;
 1625 
 1626         tmsgflags = ti->ti_setup_msg;
 1627         ti->ti_setup_msg = 0;
 1628 
 1629         flags |= CCB_NORETRY;
 1630         if ((cb = SCSI_LOW_ALLOC_CCB(1)) == NULL)
 1631                 return ENOMEM;
 1632 
 1633         cb->osdep = NULL;
 1634         cb->bp = NULL;
 1635         scsi_low_enqueue(slp, ti, li, cb, flags, tmsgflags);
 1636         return 0;
 1637 }
 1638 
 1639 /**************************************************************
 1640  * Generic Start & Done
 1641  **************************************************************/
 1642 #define SLSC_MODE_SENSE_SHORT   0x1a
 1643 static u_int8_t ss_cmd[6] = {START_STOP, 0, 0, 0, SSS_START, 0}; 
 1644 static u_int8_t sms_cmd[6] = {SLSC_MODE_SENSE_SHORT, 0x08, 0x0a, 0, 
 1645                               sizeof(struct scsi_low_mode_sense_data), 0}; 
 1646 static u_int8_t inq_cmd[6] = {INQUIRY, 0, 0, 0, 
 1647                               sizeof(struct scsi_low_inq_data), 0}; 
 1648 static u_int8_t unit_ready_cmd[6];
 1649 static int scsi_low_setup_start(struct scsi_low_softc *, struct targ_info *, struct lun_info *, struct slccb *);
 1650 static int scsi_low_sense_abort_start(struct scsi_low_softc *, struct targ_info *, struct lun_info *, struct slccb *);
 1651 static int scsi_low_resume(struct scsi_low_softc *);
 1652 
 1653 static void
 1654 scsi_low_unit_ready_cmd(cb)
 1655         struct slccb *cb;
 1656 {
 1657 
 1658         cb->ccb_scp.scp_cmd = unit_ready_cmd;
 1659         cb->ccb_scp.scp_cmdlen = sizeof(unit_ready_cmd);
 1660         cb->ccb_scp.scp_datalen = 0;
 1661         cb->ccb_scp.scp_direction = SCSI_LOW_READ;
 1662         cb->ccb_tcmax = 15;
 1663 }
 1664 
 1665 static int
 1666 scsi_low_sense_abort_start(slp, ti, li, cb)
 1667         struct scsi_low_softc *slp;
 1668         struct targ_info *ti;
 1669         struct lun_info *li;
 1670         struct slccb *cb;
 1671 {
 1672 
 1673         cb->ccb_scp.scp_cmdlen = 6;
 1674         bzero(cb->ccb_scsi_cmd, cb->ccb_scp.scp_cmdlen);
 1675         cb->ccb_scsi_cmd[0] = REQUEST_SENSE;
 1676         cb->ccb_scsi_cmd[4] = sizeof(cb->ccb_sense);
 1677         cb->ccb_scp.scp_cmd = cb->ccb_scsi_cmd;
 1678         cb->ccb_scp.scp_data = (u_int8_t *) &cb->ccb_sense;
 1679         cb->ccb_scp.scp_datalen = sizeof(cb->ccb_sense);
 1680         cb->ccb_scp.scp_direction = SCSI_LOW_READ;
 1681         cb->ccb_tcmax = 15;
 1682         scsi_low_ccb_message_clear(cb);
 1683         if ((cb->ccb_flags & CCB_CLEARQ) != 0)
 1684         {
 1685                 scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_ABORT, 0);
 1686         }
 1687         else
 1688         {
 1689                 bzero(&cb->ccb_sense, sizeof(cb->ccb_sense));
 1690 #ifdef  SCSI_LOW_NEGOTIATE_BEFORE_SENSE
 1691                 scsi_low_assert_msg(slp, ti, ti->ti_setup_msg_done, 0);
 1692 #endif  /* SCSI_LOW_NEGOTIATE_BEFORE_SENSE */
 1693         }
 1694 
 1695         return SCSI_LOW_START_NO_QTAG;
 1696 }
 1697 
 1698 static int
 1699 scsi_low_setup_start(slp, ti, li, cb)
 1700         struct scsi_low_softc *slp;
 1701         struct targ_info *ti;
 1702         struct lun_info *li;
 1703         struct slccb *cb;
 1704 {
 1705 
 1706         switch(li->li_state)
 1707         {
 1708         case SCSI_LOW_LUN_SLEEP:
 1709                 scsi_low_unit_ready_cmd(cb);
 1710                 break;
 1711 
 1712         case SCSI_LOW_LUN_START:
 1713                 cb->ccb_scp.scp_cmd = ss_cmd;
 1714                 cb->ccb_scp.scp_cmdlen = sizeof(ss_cmd);
 1715                 cb->ccb_scp.scp_datalen = 0;
 1716                 cb->ccb_scp.scp_direction = SCSI_LOW_READ;
 1717                 cb->ccb_tcmax = 30;
 1718                 break;
 1719 
 1720         case SCSI_LOW_LUN_INQ:
 1721                 cb->ccb_scp.scp_cmd = inq_cmd;
 1722                 cb->ccb_scp.scp_cmdlen = sizeof(inq_cmd);
 1723                 cb->ccb_scp.scp_data = (u_int8_t *)&li->li_inq;
 1724                 cb->ccb_scp.scp_datalen = sizeof(li->li_inq);
 1725                 cb->ccb_scp.scp_direction = SCSI_LOW_READ;
 1726                 cb->ccb_tcmax = 15;
 1727                 break;
 1728 
 1729         case SCSI_LOW_LUN_MODEQ:
 1730                 cb->ccb_scp.scp_cmd = sms_cmd;
 1731                 cb->ccb_scp.scp_cmdlen = sizeof(sms_cmd);
 1732                 cb->ccb_scp.scp_data = (u_int8_t *)&li->li_sms;
 1733                 cb->ccb_scp.scp_datalen = sizeof(li->li_sms);
 1734                 cb->ccb_scp.scp_direction = SCSI_LOW_READ;
 1735                 cb->ccb_tcmax = 15;
 1736                 return SCSI_LOW_START_QTAG;
 1737 
 1738         default:
 1739                 panic("%s: no setup phase", device_get_nameunit(slp->sl_dev));
 1740         }
 1741 
 1742         return SCSI_LOW_START_NO_QTAG;
 1743 }
 1744 
 1745 static int
 1746 scsi_low_resume(slp)
 1747         struct scsi_low_softc *slp;
 1748 {
 1749 
 1750         if (slp->sl_flags & HW_RESUME)
 1751                 return EJUSTRETURN;
 1752         slp->sl_flags &= ~HW_POWDOWN;
 1753         if (slp->sl_funcs->scsi_low_power != NULL)
 1754         {
 1755                 slp->sl_flags |= HW_RESUME;
 1756                 slp->sl_rstep = 0;
 1757                 (*slp->sl_funcs->scsi_low_power) (slp, SCSI_LOW_ENGAGE);
 1758                 (*slp->sl_osdep_fp->scsi_low_osdep_timeout)
 1759                                         (slp, SCSI_LOW_TIMEOUT_CH_ENGAGE,
 1760                                          SCSI_LOW_TIMEOUT_START);
 1761                 return EJUSTRETURN;
 1762         }
 1763         return 0;
 1764 }
 1765 
 1766 static void
 1767 scsi_low_start(slp)
 1768         struct scsi_low_softc *slp;
 1769 {
 1770         struct targ_info *ti;
 1771         struct lun_info *li;
 1772         struct slccb *cb;
 1773         int rv;
 1774 
 1775         /* check hardware exists or under initializations ? */
 1776         if ((slp->sl_flags & (HW_INACTIVE | HW_INITIALIZING)) != 0)
 1777                 return;
 1778 
 1779         /* check hardware power up ? */
 1780         if ((slp->sl_flags & HW_POWERCTRL) != 0)
 1781         {
 1782                 slp->sl_active ++;
 1783                 if (slp->sl_flags & (HW_POWDOWN | HW_RESUME))
 1784                 {
 1785                         if (scsi_low_resume(slp) == EJUSTRETURN)
 1786                                 return;
 1787                 }
 1788         }
 1789 
 1790         /* setup nexus */
 1791 #ifdef  SCSI_LOW_DIAGNOSTIC
 1792         if (slp->sl_Tnexus || slp->sl_Lnexus || slp->sl_Qnexus)
 1793         {
 1794                 scsi_low_info(slp, NULL, "NEXUS INCOSISTENT");
 1795                 panic("%s: inconsistent", device_get_nameunit(slp->sl_dev));
 1796         }
 1797 #endif  /* SCSI_LOW_DIAGNOSTIC */
 1798 
 1799         for (cb = TAILQ_FIRST(&slp->sl_start); cb != NULL;
 1800              cb = TAILQ_NEXT(cb, ccb_chain))
 1801         {
 1802                 li = cb->li;
 1803 
 1804                 if (li->li_disc == 0)
 1805                 {
 1806                         goto scsi_low_cmd_start;
 1807                 }
 1808                 else if (li->li_nqio > 0)
 1809                 {
 1810                         if (li->li_nqio < li->li_maxnqio ||
 1811                             (cb->ccb_flags & (CCB_SENSE | CCB_CLEARQ)) != 0)
 1812                                 goto scsi_low_cmd_start;
 1813                 }
 1814         }
 1815         return;
 1816 
 1817 scsi_low_cmd_start:
 1818         cb->ccb_flags &= ~CCB_STARTQ;
 1819         TAILQ_REMOVE(&slp->sl_start, cb, ccb_chain);
 1820         ti = cb->ti;
 1821 
 1822         /* clear all error flag bits (for restart) */
 1823         cb->ccb_error = 0;
 1824         cb->ccb_datalen = -1;
 1825         cb->ccb_scp.scp_status = ST_UNKNOWN;
 1826 
 1827         /* setup nexus pointer */
 1828         slp->sl_Qnexus = cb;
 1829         slp->sl_Lnexus = li;
 1830         slp->sl_Tnexus = ti;
 1831 
 1832         /* initialize msgsys */
 1833         scsi_low_init_msgsys(slp, ti);
 1834 
 1835         /* exec cmd */
 1836         if ((cb->ccb_flags & (CCB_SENSE | CCB_CLEARQ)) != 0)
 1837         {
 1838                 /* CA state or forced abort */
 1839                 rv = scsi_low_sense_abort_start(slp, ti, li, cb);
 1840         }
 1841         else if (li->li_state >= SCSI_LOW_LUN_OK)
 1842         {
 1843                 cb->ccb_flags &= ~CCB_INTERNAL;
 1844                 rv = (*slp->sl_osdep_fp->scsi_low_osdep_ccb_setup) (slp, cb);
 1845                 if (cb->ccb_msgoutflag != 0)
 1846                 {
 1847                         scsi_low_ccb_message_exec(slp, cb);
 1848                 }
 1849         }
 1850         else
 1851         {
 1852                 cb->ccb_flags |= CCB_INTERNAL;
 1853                 rv = scsi_low_setup_start(slp, ti, li, cb);
 1854         }
 1855 
 1856         /* allocate qtag */
 1857 #define SCSI_LOW_QTAG_OK (SCSI_LOW_QTAG | SCSI_LOW_DISC)
 1858 
 1859         if (rv == SCSI_LOW_START_QTAG &&
 1860             (li->li_flags & SCSI_LOW_QTAG_OK) == SCSI_LOW_QTAG_OK &&
 1861             li->li_maxnqio > 0)
 1862         {
 1863                 u_int qmsg;
 1864 
 1865                 scsi_low_activate_qtag(cb);
 1866                 if ((scsi_low_cmd_flags[cb->ccb_scp.scp_cmd[0]] &
 1867                      SCSI_LOW_CMD_ORDERED_QTAG) != 0)
 1868                         qmsg = SCSI_LOW_MSG_ORDERED_QTAG;
 1869                 else if ((cb->ccb_flags & CCB_URGENT) != 0)
 1870                         qmsg = SCSI_LOW_MSG_HEAD_QTAG;
 1871                 else
 1872                         qmsg = SCSI_LOW_MSG_SIMPLE_QTAG;
 1873                 scsi_low_assert_msg(slp, ti, qmsg, 0);
 1874         }
 1875 
 1876         /* timeout */
 1877         if (cb->ccb_tcmax < SCSI_LOW_MIN_TOUT)
 1878                 cb->ccb_tcmax = SCSI_LOW_MIN_TOUT;
 1879         cb->ccb_tc = cb->ccb_tcmax;
 1880 
 1881         /* setup saved scsi data pointer */
 1882         cb->ccb_sscp = cb->ccb_scp;
 1883 
 1884         /* setup current scsi pointer */ 
 1885         slp->sl_scp = cb->ccb_sscp;
 1886         slp->sl_error = cb->ccb_error;
 1887 
 1888         /* assert always an identify msg */
 1889         scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_IDENTIFY, 0);
 1890 
 1891         /* debug section */
 1892 #ifdef  SCSI_LOW_DIAGNOSTIC
 1893         scsi_low_msg_log_init(&ti->ti_log_msgin);
 1894         scsi_low_msg_log_init(&ti->ti_log_msgout);
 1895 #endif  /* SCSI_LOW_DIAGNOSTIC */
 1896 
 1897         /* selection start */
 1898         slp->sl_selid = cb;
 1899         rv = ((*slp->sl_funcs->scsi_low_start_bus) (slp, cb));
 1900         if (rv == SCSI_LOW_START_OK)
 1901         {
 1902 #ifdef  SCSI_LOW_STATICS
 1903                 scsi_low_statics.nexus_win ++;
 1904 #endif  /* SCSI_LOW_STATICS */
 1905                 return;
 1906         }
 1907 
 1908         scsi_low_arbit_fail(slp, cb);
 1909 #ifdef  SCSI_LOW_STATICS
 1910         scsi_low_statics.nexus_fail ++;
 1911 #endif  /* SCSI_LOW_STATICS */
 1912 }
 1913 
 1914 void
 1915 scsi_low_arbit_fail(slp, cb)
 1916         struct scsi_low_softc *slp;
 1917         struct slccb *cb;
 1918 {
 1919         struct targ_info *ti = cb->ti;
 1920 
 1921         scsi_low_deactivate_qtag(cb);
 1922         scsi_low_ccb_message_retry(cb);
 1923         cb->ccb_flags |= CCB_STARTQ;
 1924         TAILQ_INSERT_HEAD(&slp->sl_start, cb, ccb_chain);
 1925 
 1926         scsi_low_bus_release(slp, ti);
 1927 
 1928         cb->ccb_selrcnt ++;
 1929         if (slp->sl_disc == 0)
 1930         {
 1931 #ifdef  SCSI_LOW_DIAGNOSTIC
 1932                 device_printf(slp->sl_dev, "try selection again\n");
 1933 #endif  /* SCSI_LOW_DIAGNOSTIC */
 1934                 slp->sl_retry_sel = 1;
 1935         }
 1936 }
 1937 
 1938 static void
 1939 scsi_low_bus_release(slp, ti)
 1940         struct scsi_low_softc *slp;
 1941         struct targ_info *ti;
 1942 {
 1943 
 1944         if (ti->ti_disc > 0)
 1945         {
 1946                 SCSI_LOW_SETUP_PHASE(ti, PH_DISC);
 1947         }
 1948         else
 1949         {
 1950                 SCSI_LOW_SETUP_PHASE(ti, PH_NULL);
 1951         }
 1952 
 1953         /* clear all nexus pointer */
 1954         slp->sl_Qnexus = NULL;
 1955         slp->sl_Lnexus = NULL;
 1956         slp->sl_Tnexus = NULL;
 1957 
 1958         /* clear selection assert */
 1959         slp->sl_selid = NULL;
 1960 
 1961         /* clear nexus data */
 1962         slp->sl_scp.scp_direction = SCSI_LOW_RWUNK;
 1963 
 1964         /* clear phase change counter */
 1965         slp->sl_ph_count = 0;
 1966 }
 1967 
 1968 static int
 1969 scsi_low_setup_done(slp, cb)
 1970         struct scsi_low_softc *slp;
 1971         struct slccb *cb;
 1972 {
 1973         struct targ_info *ti;
 1974         struct lun_info *li;
 1975 
 1976         ti = cb->ti;
 1977         li = cb->li;
 1978 
 1979         if (cb->ccb_rcnt >= slp->sl_max_retry)
 1980         {
 1981                 cb->ccb_error |= ABORTIO;
 1982                 return SCSI_LOW_DONE_COMPLETE;
 1983         }
 1984 
 1985         /* XXX: special huck for selection timeout */
 1986         if (li->li_state == SCSI_LOW_LUN_SLEEP &&
 1987             (cb->ccb_error & SELTIMEOUTIO) != 0)
 1988         {
 1989                 cb->ccb_error |= ABORTIO;
 1990                 return SCSI_LOW_DONE_COMPLETE;
 1991         }
 1992 
 1993         switch(li->li_state)
 1994         {
 1995         case SCSI_LOW_LUN_INQ:
 1996                 if (cb->ccb_error != 0)
 1997                 {
 1998                         li->li_diskflags &= 
 1999                                 ~(SCSI_LOW_DISK_LINK | SCSI_LOW_DISK_QTAG);
 2000                         if (li->li_lun > 0)
 2001                                 goto resume;
 2002                         ti->ti_diskflags &=
 2003                                 ~(SCSI_LOW_DISK_SYNC | SCSI_LOW_DISK_WIDE);
 2004                 }
 2005                 else if ((li->li_inq.sd_version & 7) >= 2 ||
 2006                          (li->li_inq.sd_len >= 4))
 2007                 {
 2008                         if ((li->li_inq.sd_support & 0x2) == 0)
 2009                                 li->li_diskflags &= ~SCSI_LOW_DISK_QTAG;
 2010                         if ((li->li_inq.sd_support & 0x8) == 0)
 2011                                 li->li_diskflags &= ~SCSI_LOW_DISK_LINK;
 2012                         if (li->li_lun > 0)
 2013                                 goto resume;
 2014                         if ((li->li_inq.sd_support & 0x10) == 0)
 2015                                 ti->ti_diskflags &= ~SCSI_LOW_DISK_SYNC;
 2016                         if ((li->li_inq.sd_support & 0x20) == 0)
 2017                                 ti->ti_diskflags &= ~SCSI_LOW_DISK_WIDE_16;
 2018                         if ((li->li_inq.sd_support & 0x40) == 0)
 2019                                 ti->ti_diskflags &= ~SCSI_LOW_DISK_WIDE_32;
 2020                 }
 2021                 else
 2022                 {
 2023                         li->li_diskflags &= 
 2024                                 ~(SCSI_LOW_DISK_QTAG | SCSI_LOW_DISK_LINK);
 2025                         if (li->li_lun > 0)
 2026                                 goto resume;
 2027                         ti->ti_diskflags &= ~SCSI_LOW_DISK_WIDE;
 2028                 }
 2029                 ti->ti_flags_valid |= SCSI_LOW_TARG_FLAGS_DISK_VALID;
 2030 resume:
 2031                 scsi_low_calcf_target(ti);
 2032                 scsi_low_calcf_lun(li);
 2033                 break;
 2034 
 2035         case SCSI_LOW_LUN_MODEQ:
 2036                 if (cb->ccb_error != 0)
 2037                 {
 2038                         if (cb->ccb_error & SENSEIO)
 2039                         {
 2040 #ifdef  SCSI_LOW_DEBUG
 2041                                 if (scsi_low_debug & SCSI_LOW_DEBUG_SENSE)
 2042                                 {
 2043                                         int error_code, sense_key, asc, ascq;
 2044 
 2045                                         scsi_extract_sense(&cb->ccb_sense,
 2046                                                            &error_code,
 2047                                                            &sense_key,
 2048                                                            &asc,
 2049                                                            &ascq);
 2050                                         printf("SENSE: [%x][%x][%x][%x]\n",
 2051                                                error_code, sense_key, asc,
 2052                                                ascq);
 2053                                 }
 2054 #endif  /* SCSI_LOW_DEBUG */
 2055                         }
 2056                         else
 2057                         {
 2058                                 li->li_diskflags &= ~SCSI_LOW_DISK_QTAG;
 2059                         }
 2060                 }
 2061                 else if ((li->li_sms.sms_cmp.cmp_page & 0x3f) == 0x0a)
 2062                 {       
 2063                         if (li->li_sms.sms_cmp.cmp_qc & 0x02)
 2064                                 li->li_qflags |= SCSI_LOW_QFLAG_CA_QCLEAR;
 2065                         else
 2066                                 li->li_qflags &= ~SCSI_LOW_QFLAG_CA_QCLEAR;
 2067                         if ((li->li_sms.sms_cmp.cmp_qc & 0x01) != 0)
 2068                                 li->li_diskflags &= ~SCSI_LOW_DISK_QTAG;
 2069                 }
 2070                 li->li_flags_valid |= SCSI_LOW_LUN_FLAGS_DISK_VALID;
 2071                 scsi_low_calcf_lun(li);
 2072                 break;
 2073 
 2074         default:
 2075                 break;
 2076         }
 2077 
 2078         li->li_state ++;
 2079         if (li->li_state == SCSI_LOW_LUN_OK)
 2080         {
 2081                 scsi_low_calcf_target(ti);
 2082                 scsi_low_calcf_lun(li);
 2083                 if (li->li_flags_valid == SCSI_LOW_LUN_FLAGS_ALL_VALID &&
 2084                     (slp->sl_show_result & SHOW_CALCF_RES) != 0)
 2085                 {
 2086                         scsi_low_calcf_show(li);
 2087                 }       
 2088         }
 2089 
 2090         cb->ccb_rcnt --;
 2091         return SCSI_LOW_DONE_RETRY;
 2092 }
 2093 
 2094 static int
 2095 scsi_low_done(slp, cb)
 2096         struct scsi_low_softc *slp;
 2097         struct slccb *cb;
 2098 {
 2099         int rv;
 2100 
 2101         if (cb->ccb_error == 0)
 2102         {
 2103                 if ((cb->ccb_flags & (CCB_SENSE | CCB_CLEARQ)) != 0)
 2104                 {
 2105 #ifdef  SCSI_LOW_QCLEAR_AFTER_CA
 2106                         /* XXX:
 2107                          * SCSI-2 draft suggests 
 2108                          * page 0x0a QErr bit determins if
 2109                          * the target aborts or continues
 2110                          * the queueing io's after CA state resolved.
 2111                          * However many targets seem not to support
 2112                          * the page 0x0a. Thus we should manually clear the
 2113                          * queuing io's after CA state.
 2114                          */
 2115                         if ((cb->ccb_flags & CCB_CLEARQ) == 0)
 2116                         {
 2117                                 cb->ccb_rcnt --;
 2118                                 cb->ccb_flags |= CCB_CLEARQ;
 2119                                 goto retry;
 2120                         }
 2121 #endif  /* SCSI_LOW_QCLEAR_AFTER_CA */
 2122 
 2123                         if ((cb->ccb_flags & CCB_SENSE) != 0)
 2124                                 cb->ccb_error |= (SENSEIO | ABORTIO);
 2125                         cb->ccb_flags &= ~(CCB_SENSE | CCB_CLEARQ);
 2126                 }
 2127                 else switch (cb->ccb_sscp.scp_status)
 2128                 {
 2129                 case ST_GOOD:
 2130                 case ST_MET:
 2131                 case ST_INTERGOOD:
 2132                 case ST_INTERMET:
 2133                         if (cb->ccb_datalen == 0 ||
 2134                             cb->ccb_scp.scp_datalen == 0)
 2135                                 break;
 2136 
 2137                         if (cb->ccb_scp.scp_cmdlen > 0 &&
 2138                             (scsi_low_cmd_flags[cb->ccb_scp.scp_cmd[0]] &
 2139                              SCSI_LOW_CMD_RESIDUAL_CHK) == 0)
 2140                                 break;
 2141 
 2142                         cb->ccb_error |= PDMAERR;
 2143                         break;
 2144 
 2145                 case ST_BUSY:
 2146                 case ST_QUEFULL:
 2147                         cb->ccb_error |= (BUSYERR | STATERR);
 2148                         break;
 2149 
 2150                 case ST_CONFLICT:
 2151                         cb->ccb_error |= (STATERR | ABORTIO);
 2152                         break;
 2153 
 2154                 case ST_CHKCOND:
 2155                 case ST_CMDTERM:
 2156                         if (cb->ccb_flags & (CCB_AUTOSENSE | CCB_INTERNAL))
 2157                         {
 2158                                 cb->ccb_rcnt --;
 2159                                 cb->ccb_flags |= CCB_SENSE;
 2160                                 goto retry;
 2161                         }
 2162                         cb->ccb_error |= (UACAERR | STATERR | ABORTIO);
 2163                         break;
 2164 
 2165                 case ST_UNKNOWN:
 2166                 default:
 2167                         cb->ccb_error |= FATALIO;
 2168                         break;
 2169                 }
 2170         }
 2171         else
 2172         {
 2173                 if (cb->ccb_flags & CCB_SENSE)
 2174                 {
 2175                         cb->ccb_error |= (SENSEERR | ABORTIO);
 2176                 }
 2177                 cb->ccb_flags &= ~(CCB_CLEARQ | CCB_SENSE);
 2178         }
 2179 
 2180         /* internal ccb */
 2181         if ((cb->ccb_flags & CCB_INTERNAL) != 0)
 2182         {
 2183                 if (scsi_low_setup_done(slp, cb) == SCSI_LOW_DONE_RETRY)
 2184                         goto retry;
 2185         }
 2186 
 2187         /* check a ccb msgout flag */
 2188         if (cb->ccb_omsgoutflag != 0)
 2189         {
 2190 #define SCSI_LOW_MSG_ABORT_OK   (SCSI_LOW_MSG_ABORT | \
 2191                                  SCSI_LOW_MSG_ABORT_QTAG | \
 2192                                  SCSI_LOW_MSG_CLEAR_QTAG | \
 2193                                  SCSI_LOW_MSG_TERMIO)
 2194 
 2195                 if ((cb->ccb_omsgoutflag & SCSI_LOW_MSG_ABORT_OK) != 0)
 2196                 {
 2197                         cb->ccb_error |= ABORTIO;
 2198                 }
 2199         }
 2200 
 2201         /* call OS depend done */
 2202         if (cb->osdep != NULL)
 2203         {
 2204                 rv = (*slp->sl_osdep_fp->scsi_low_osdep_done) (slp, cb);
 2205                 if (rv == EJUSTRETURN)
 2206                         goto retry;
 2207         }
 2208         else if (cb->ccb_error != 0)
 2209         {
 2210                 if (cb->ccb_rcnt >= slp->sl_max_retry)
 2211                         cb->ccb_error |= ABORTIO;
 2212 
 2213                 if ((cb->ccb_flags & CCB_NORETRY) == 0 &&
 2214                     (cb->ccb_error & ABORTIO) == 0)
 2215                         goto retry;
 2216         }
 2217 
 2218         /* free our target */
 2219 #ifdef  SCSI_LOW_DEBUG
 2220         if (SCSI_LOW_DEBUG_GO(SCSI_LOW_DEBUG_DONE, cb->ti->ti_id) != 0)
 2221         {
 2222                 printf(">> SCSI_LOW_DONE_COMPLETE ===============\n");
 2223                 scsi_low_print(slp, NULL);
 2224         }
 2225 #endif  /* SCSI_LOW_DEBUG */
 2226 
 2227         scsi_low_deactivate_qtag(cb);
 2228         scsi_low_dealloc_qtag(cb);
 2229         scsi_low_free_ccb(cb);
 2230         slp->sl_nio --;
 2231         return SCSI_LOW_DONE_COMPLETE;
 2232 
 2233 retry:
 2234 #ifdef  SCSI_LOW_DEBUG
 2235         if (SCSI_LOW_DEBUG_GO(SCSI_LOW_DEBUG_DONE, cb->ti->ti_id) != 0)
 2236         {
 2237                 printf("** SCSI_LOW_DONE_RETRY ===============\n");
 2238                 scsi_low_print(slp, NULL);
 2239         }
 2240 #endif  /* SCSI_LOW_DEBUG */
 2241                 
 2242         cb->ccb_rcnt ++;
 2243         scsi_low_deactivate_qtag(cb);
 2244         scsi_low_ccb_message_retry(cb);
 2245         return SCSI_LOW_DONE_RETRY;
 2246 }
 2247 
 2248 /**************************************************************
 2249  * Reset
 2250  **************************************************************/
 2251 static void
 2252 scsi_low_reset_nexus_target(slp, ti, fdone)
 2253         struct scsi_low_softc *slp;
 2254         struct targ_info *ti;
 2255         int fdone;
 2256 {
 2257         struct lun_info *li;
 2258 
 2259         for (li = LIST_FIRST(&ti->ti_litab); li != NULL;
 2260              li = LIST_NEXT(li, lun_chain))
 2261         {
 2262                 scsi_low_reset_nexus_lun(slp, li, fdone);
 2263                 li->li_state = SCSI_LOW_LUN_SLEEP;
 2264                 li->li_maxnqio = 0;
 2265         }
 2266 
 2267         ti->ti_disc = 0;
 2268         ti->ti_setup_msg = 0;
 2269         ti->ti_setup_msg_done = 0;
 2270 
 2271         ti->ti_osynch.offset = ti->ti_osynch.period = 0;
 2272         ti->ti_owidth = SCSI_LOW_BUS_WIDTH_8;
 2273 
 2274         ti->ti_diskflags = SCSI_LOW_DISK_TFLAGS;
 2275         ti->ti_flags_valid &= ~SCSI_LOW_TARG_FLAGS_DISK_VALID;
 2276 
 2277         if (slp->sl_funcs->scsi_low_targ_init != NULL)
 2278         {
 2279                 ((*slp->sl_funcs->scsi_low_targ_init)
 2280                         (slp, ti, SCSI_LOW_INFO_REVOKE));
 2281         }
 2282         scsi_low_calcf_target(ti);
 2283 
 2284         for (li = LIST_FIRST(&ti->ti_litab); li != NULL;
 2285              li = LIST_NEXT(li, lun_chain))
 2286         {
 2287                 li->li_flags = 0;
 2288 
 2289                 li->li_diskflags = SCSI_LOW_DISK_LFLAGS;
 2290                 li->li_flags_valid &= ~SCSI_LOW_LUN_FLAGS_DISK_VALID;
 2291 
 2292                 if (slp->sl_funcs->scsi_low_lun_init != NULL)
 2293                 {
 2294                         ((*slp->sl_funcs->scsi_low_lun_init)
 2295                                 (slp, ti, li, SCSI_LOW_INFO_REVOKE));
 2296                 }
 2297                 scsi_low_calcf_lun(li);
 2298         }
 2299 }
 2300 
 2301 static void
 2302 scsi_low_reset_nexus(slp, fdone)
 2303         struct scsi_low_softc *slp;
 2304         int fdone;
 2305 {
 2306         struct targ_info *ti;
 2307         struct slccb *cb, *topcb;
 2308 
 2309         if ((cb = slp->sl_Qnexus) != NULL)
 2310         {
 2311                 topcb = scsi_low_revoke_ccb(slp, cb, fdone);
 2312         }
 2313         else
 2314         {
 2315                 topcb = NULL;
 2316         }
 2317 
 2318         for (ti = TAILQ_FIRST(&slp->sl_titab); ti != NULL;
 2319              ti = TAILQ_NEXT(ti, ti_chain))
 2320         {
 2321                 scsi_low_reset_nexus_target(slp, ti, fdone);
 2322                 scsi_low_bus_release(slp, ti);
 2323                 scsi_low_init_msgsys(slp, ti);
 2324         }
 2325 
 2326         if (topcb != NULL)
 2327         {
 2328                 topcb->ccb_flags |= CCB_STARTQ;
 2329                 TAILQ_INSERT_HEAD(&slp->sl_start, topcb, ccb_chain);
 2330         }
 2331 
 2332         slp->sl_disc = 0;
 2333         slp->sl_retry_sel = 0;
 2334         slp->sl_flags &= ~HW_PDMASTART;
 2335 }
 2336 
 2337 /* misc */
 2338 static int tw_pos;
 2339 static char tw_chars[] = "|/-\\";
 2340 #define TWIDDLEWAIT             10000
 2341 
 2342 static void
 2343 scsi_low_twiddle_wait(void)
 2344 {
 2345 
 2346         cnputc('\b');
 2347         cnputc(tw_chars[tw_pos++]);
 2348         tw_pos %= (sizeof(tw_chars) - 1);
 2349         DELAY(TWIDDLEWAIT);
 2350 }
 2351 
 2352 void
 2353 scsi_low_bus_reset(slp)
 2354         struct scsi_low_softc *slp;
 2355 {
 2356         int i;
 2357 
 2358         (*slp->sl_funcs->scsi_low_bus_reset) (slp);
 2359 
 2360         device_printf(slp->sl_dev, "try to reset scsi bus  ");
 2361         for (i = 0; i <= SCSI2_RESET_DELAY / TWIDDLEWAIT ; i++)
 2362                 scsi_low_twiddle_wait();
 2363         cnputc('\b');
 2364         printf("\n");
 2365 }
 2366 
 2367 int
 2368 scsi_low_restart(slp, flags, s)
 2369         struct scsi_low_softc *slp;
 2370         int flags;
 2371         u_char *s;
 2372 {
 2373         int error;
 2374 
 2375         if (s != NULL)
 2376                 device_printf(slp->sl_dev, "scsi bus restart. reason: %s\n", s);
 2377 
 2378         if ((error = scsi_low_init(slp, flags)) != 0)
 2379                 return error;
 2380 
 2381         scsi_low_start(slp);
 2382         return 0;
 2383 }
 2384 
 2385 /**************************************************************
 2386  * disconnect and reselect
 2387  **************************************************************/
 2388 #define MSGCMD_LUN(msg) (msg & 0x07)
 2389 
 2390 static struct slccb *
 2391 scsi_low_establish_ccb(ti, li, tag)
 2392         struct targ_info *ti;
 2393         struct lun_info *li;
 2394         scsi_low_tag_t tag;
 2395 {
 2396         struct scsi_low_softc *slp = ti->ti_sc;
 2397         struct slccb *cb;
 2398 
 2399         if (li == NULL)
 2400                 return NULL;
 2401 
 2402         cb = TAILQ_FIRST(&li->li_discq);
 2403         for ( ; cb != NULL; cb = TAILQ_NEXT(cb, ccb_chain))
 2404                 if (cb->ccb_tag == tag)
 2405                         goto found;
 2406         return cb;
 2407 
 2408         /* 
 2409          * establish our ccb nexus
 2410          */
 2411 found:
 2412 #ifdef  SCSI_LOW_DEBUG
 2413         if (SCSI_LOW_DEBUG_TEST_GO(SCSI_LOW_NEXUS_CHECK, ti->ti_id) != 0)
 2414         {
 2415                 device_printf(slp->sl_dev, "nexus(0x%lx) abort check start\n",
 2416                     (u_long) cb);
 2417                 cb->ccb_flags |= (CCB_NORETRY | CCB_SILENT);
 2418                 scsi_low_revoke_ccb(slp, cb, 1);
 2419                 return NULL;
 2420         }
 2421 
 2422         if (SCSI_LOW_DEBUG_TEST_GO(SCSI_LOW_ATTEN_CHECK, ti->ti_id) != 0)
 2423         {
 2424                 if (cb->ccb_omsgoutflag == 0)
 2425                         scsi_low_ccb_message_assert(cb, SCSI_LOW_MSG_NOOP);
 2426         }
 2427 #endif  /* SCSI_LOW_DEBUG */
 2428 
 2429         TAILQ_REMOVE(&li->li_discq, cb, ccb_chain);
 2430         cb->ccb_flags &= ~CCB_DISCQ;
 2431         slp->sl_Qnexus = cb;
 2432 
 2433         slp->sl_scp = cb->ccb_sscp;
 2434         slp->sl_error |= cb->ccb_error;
 2435 
 2436         slp->sl_disc --;
 2437         ti->ti_disc --;
 2438         li->li_disc --;
 2439 
 2440         /* inform "ccb nexus established" to the host driver */
 2441         (*slp->sl_funcs->scsi_low_establish_ccb_nexus) (slp);
 2442 
 2443         /* check msg */
 2444         if (cb->ccb_msgoutflag != 0)
 2445         {
 2446                 scsi_low_ccb_message_exec(slp, cb);
 2447         }
 2448 
 2449         return cb;
 2450 }
 2451 
 2452 struct targ_info *
 2453 scsi_low_reselected(slp, targ)
 2454         struct scsi_low_softc *slp;
 2455         u_int targ;
 2456 {
 2457         struct targ_info *ti;
 2458         struct slccb *cb;
 2459         u_char *s;
 2460 
 2461         /* 
 2462          * Check select vs reselected collision.
 2463          */
 2464 
 2465         if ((cb = slp->sl_selid) != NULL)
 2466         {
 2467                 scsi_low_arbit_fail(slp, cb);
 2468 #ifdef  SCSI_LOW_STATICS
 2469                 scsi_low_statics.nexus_conflict ++;
 2470 #endif  /* SCSI_LOW_STATICS */
 2471         }
 2472 
 2473         /* 
 2474          * Check if no current active nexus.
 2475          */
 2476         if (slp->sl_Tnexus != NULL)
 2477         {
 2478                 s = "host busy";
 2479                 goto world_restart;
 2480         }
 2481 
 2482         /* 
 2483          * Check a valid target id asserted ?
 2484          */
 2485         if (targ >= slp->sl_ntargs || targ == slp->sl_hostid)
 2486         {
 2487                 s = "scsi id illegal";
 2488                 goto world_restart;
 2489         }
 2490 
 2491         /* 
 2492          * Check the target scsi status.
 2493          */
 2494         ti = slp->sl_ti[targ];
 2495         if (ti->ti_phase != PH_DISC && ti->ti_phase != PH_NULL)
 2496         {
 2497                 s = "phase mismatch";
 2498                 goto world_restart;
 2499         }
 2500 
 2501         /* 
 2502          * Setup init msgsys
 2503          */
 2504         slp->sl_error = 0;
 2505         scsi_low_init_msgsys(slp, ti);
 2506 
 2507         /* 
 2508          * Establish our target nexus
 2509          */
 2510         SCSI_LOW_SETUP_PHASE(ti, PH_RESEL);
 2511         slp->sl_Tnexus = ti;
 2512 #ifdef  SCSI_LOW_STATICS
 2513         scsi_low_statics.nexus_reselected ++;
 2514 #endif  /* SCSI_LOW_STATICS */
 2515         return ti;
 2516 
 2517 world_restart:
 2518         device_printf(slp->sl_dev, "reselect(%x:unknown) %s\n", targ, s);
 2519         scsi_low_restart(slp, SCSI_LOW_RESTART_HARD, 
 2520                          "reselect: scsi world confused");
 2521         return NULL;
 2522 }
 2523 
 2524 /**************************************************************
 2525  * cmd out pointer setup
 2526  **************************************************************/
 2527 int
 2528 scsi_low_cmd(slp, ti)
 2529         struct scsi_low_softc *slp;
 2530         struct targ_info *ti;
 2531 {
 2532         struct slccb *cb = slp->sl_Qnexus;
 2533         
 2534         slp->sl_ph_count ++;
 2535         if (cb == NULL)
 2536         {
 2537                 /*
 2538                  * no ccb, abort!
 2539                  */
 2540                 slp->sl_scp.scp_cmd = (u_int8_t *) &unit_ready_cmd;
 2541                 slp->sl_scp.scp_cmdlen = sizeof(unit_ready_cmd);
 2542                 slp->sl_scp.scp_datalen = 0;
 2543                 slp->sl_scp.scp_direction = SCSI_LOW_READ;
 2544                 slp->sl_error |= FATALIO;
 2545                 scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_ABORT, 0);
 2546                 SCSI_LOW_INFO(slp, ti, "CMDOUT: ccb nexus not found");
 2547                 return EINVAL;
 2548         }
 2549         else 
 2550         {
 2551 #ifdef  SCSI_LOW_DEBUG
 2552                 if (SCSI_LOW_DEBUG_TEST_GO(SCSI_LOW_CMDLNK_CHECK, ti->ti_id))
 2553                 {
 2554                         scsi_low_test_cmdlnk(slp, cb);
 2555                 }
 2556 #endif  /* SCSI_LOW_DEBUG */
 2557         }
 2558         return 0;
 2559 }
 2560 
 2561 /**************************************************************
 2562  * data out pointer setup
 2563  **************************************************************/
 2564 int
 2565 scsi_low_data(slp, ti, bp, direction)
 2566         struct scsi_low_softc *slp;
 2567         struct targ_info *ti;
 2568         struct buf **bp;
 2569         int direction;
 2570 {
 2571         struct slccb *cb = slp->sl_Qnexus;
 2572 
 2573         if (cb != NULL && direction == cb->ccb_sscp.scp_direction)
 2574         {
 2575                 *bp = cb->bp;
 2576                 return 0;
 2577         }
 2578 
 2579         slp->sl_error |= (FATALIO | PDMAERR);
 2580         slp->sl_scp.scp_datalen = 0;
 2581         slp->sl_scp.scp_direction = direction;
 2582         scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_ABORT, 0);
 2583         if (ti->ti_ophase != ti->ti_phase)
 2584         {
 2585                 char *s;
 2586 
 2587                 if (cb == NULL)
 2588                         s = "DATA PHASE: ccb nexus not found";
 2589                 else
 2590                         s = "DATA PHASE: xfer direction mismatch";
 2591                 SCSI_LOW_INFO(slp, ti, s);
 2592         }
 2593 
 2594         *bp = NULL;
 2595         return EINVAL;
 2596 }
 2597 
 2598 /**************************************************************
 2599  * MSG_SYS 
 2600  **************************************************************/
 2601 #define MSGINPTR_CLR(ti) {(ti)->ti_msginptr = 0; (ti)->ti_msginlen = 0;}
 2602 #define MSGIN_PERIOD(ti) ((ti)->ti_msgin[3])
 2603 #define MSGIN_OFFSET(ti) ((ti)->ti_msgin[4])
 2604 #define MSGIN_WIDTHP(ti) ((ti)->ti_msgin[3])
 2605 #define MSGIN_DATA_LAST 0x30
 2606 
 2607 static int scsi_low_errfunc_synch(struct scsi_low_softc *, u_int);
 2608 static int scsi_low_errfunc_wide(struct scsi_low_softc *, u_int);
 2609 static int scsi_low_errfunc_identify(struct scsi_low_softc *, u_int);
 2610 static int scsi_low_errfunc_qtag(struct scsi_low_softc *, u_int);
 2611 
 2612 static int scsi_low_msgfunc_synch(struct scsi_low_softc *);
 2613 static int scsi_low_msgfunc_wide(struct scsi_low_softc *);
 2614 static int scsi_low_msgfunc_identify(struct scsi_low_softc *);
 2615 static int scsi_low_msgfunc_abort(struct scsi_low_softc *);
 2616 static int scsi_low_msgfunc_qabort(struct scsi_low_softc *);
 2617 static int scsi_low_msgfunc_qtag(struct scsi_low_softc *);
 2618 static int scsi_low_msgfunc_reset(struct scsi_low_softc *);
 2619 
 2620 struct scsi_low_msgout_data {
 2621         u_int   md_flags;
 2622         u_int8_t md_msg;
 2623         int (*md_msgfunc)(struct scsi_low_softc *);
 2624         int (*md_errfunc)(struct scsi_low_softc *, u_int);
 2625 #define MSG_RELEASE_ATN 0x0001
 2626         u_int md_condition;
 2627 };
 2628 
 2629 struct scsi_low_msgout_data scsi_low_msgout_data[] = {
 2630 /* 0 */ {SCSI_LOW_MSG_RESET, MSG_RESET, scsi_low_msgfunc_reset, NULL, MSG_RELEASE_ATN},
 2631 /* 1 */ {SCSI_LOW_MSG_REJECT, MSG_REJECT, NULL, NULL, MSG_RELEASE_ATN},
 2632 /* 2 */ {SCSI_LOW_MSG_PARITY, MSG_PARITY, NULL, NULL, MSG_RELEASE_ATN},
 2633 /* 3 */ {SCSI_LOW_MSG_ERROR, MSG_I_ERROR, NULL, NULL, MSG_RELEASE_ATN},
 2634 /* 4 */ {SCSI_LOW_MSG_IDENTIFY, MSG_IDENTIFY, scsi_low_msgfunc_identify, scsi_low_errfunc_identify, 0},
 2635 /* 5 */ {SCSI_LOW_MSG_ABORT, MSG_ABORT, scsi_low_msgfunc_abort, NULL, MSG_RELEASE_ATN},
 2636 /* 6 */ {SCSI_LOW_MSG_TERMIO, MSG_TERM_IO, NULL, NULL, MSG_RELEASE_ATN},
 2637 /* 7 */ {SCSI_LOW_MSG_SIMPLE_QTAG,  MSG_SIMPLE_QTAG, scsi_low_msgfunc_qtag, scsi_low_errfunc_qtag, 0},
 2638 /* 8 */ {SCSI_LOW_MSG_ORDERED_QTAG, MSG_ORDERED_QTAG, scsi_low_msgfunc_qtag, scsi_low_errfunc_qtag, 0},
 2639 /* 9 */{SCSI_LOW_MSG_HEAD_QTAG,  MSG_HEAD_QTAG, scsi_low_msgfunc_qtag, scsi_low_errfunc_qtag, 0},
 2640 /* 10 */ {SCSI_LOW_MSG_ABORT_QTAG, MSG_ABORT_QTAG, scsi_low_msgfunc_qabort, NULL,  MSG_RELEASE_ATN},
 2641 /* 11 */ {SCSI_LOW_MSG_CLEAR_QTAG, MSG_CLEAR_QTAG, scsi_low_msgfunc_abort, NULL, MSG_RELEASE_ATN},
 2642 /* 12 */{SCSI_LOW_MSG_WIDE, MSG_EXTEND, scsi_low_msgfunc_wide, scsi_low_errfunc_wide, MSG_RELEASE_ATN},
 2643 /* 13 */{SCSI_LOW_MSG_SYNCH, MSG_EXTEND, scsi_low_msgfunc_synch, scsi_low_errfunc_synch, MSG_RELEASE_ATN},
 2644 /* 14 */{SCSI_LOW_MSG_NOOP, MSG_NOOP, NULL, NULL, MSG_RELEASE_ATN},
 2645 /* 15 */{SCSI_LOW_MSG_ALL, 0},
 2646 };
 2647 
 2648 static int scsi_low_msginfunc_ext(struct scsi_low_softc *);
 2649 static int scsi_low_synch(struct scsi_low_softc *);
 2650 static int scsi_low_wide(struct scsi_low_softc *);
 2651 static int scsi_low_msginfunc_msg_reject(struct scsi_low_softc *);
 2652 static int scsi_low_msginfunc_rejop(struct scsi_low_softc *);
 2653 static int scsi_low_msginfunc_rp(struct scsi_low_softc *);
 2654 static int scsi_low_msginfunc_sdp(struct scsi_low_softc *);
 2655 static int scsi_low_msginfunc_disc(struct scsi_low_softc *);
 2656 static int scsi_low_msginfunc_cc(struct scsi_low_softc *);
 2657 static int scsi_low_msginfunc_lcc(struct scsi_low_softc *);
 2658 static int scsi_low_msginfunc_parity(struct scsi_low_softc *);
 2659 static int scsi_low_msginfunc_noop(struct scsi_low_softc *);
 2660 static int scsi_low_msginfunc_simple_qtag(struct scsi_low_softc *);
 2661 static int scsi_low_msginfunc_i_wide_residue(struct scsi_low_softc *);
 2662 
 2663 struct scsi_low_msgin_data {
 2664         u_int md_len;
 2665         int (*md_msgfunc)(struct scsi_low_softc *);
 2666 };
 2667 
 2668 struct scsi_low_msgin_data scsi_low_msgin_data[] = {
 2669 /* 0 */ {1,     scsi_low_msginfunc_cc},
 2670 /* 1 */ {2,     scsi_low_msginfunc_ext},
 2671 /* 2 */ {1,     scsi_low_msginfunc_sdp},
 2672 /* 3 */ {1,     scsi_low_msginfunc_rp},
 2673 /* 4 */ {1,     scsi_low_msginfunc_disc},
 2674 /* 5 */ {1,     scsi_low_msginfunc_rejop},
 2675 /* 6 */ {1,     scsi_low_msginfunc_rejop},
 2676 /* 7 */ {1,     scsi_low_msginfunc_msg_reject},
 2677 /* 8 */ {1,     scsi_low_msginfunc_noop},
 2678 /* 9 */ {1,     scsi_low_msginfunc_parity},
 2679 /* a */ {1,     scsi_low_msginfunc_lcc},
 2680 /* b */ {1,     scsi_low_msginfunc_lcc},
 2681 /* c */ {1,     scsi_low_msginfunc_rejop},
 2682 /* d */ {2,     scsi_low_msginfunc_rejop},
 2683 /* e */ {1,     scsi_low_msginfunc_rejop},
 2684 /* f */ {1,     scsi_low_msginfunc_rejop},
 2685 /* 0x10 */ {1,  scsi_low_msginfunc_rejop},
 2686 /* 0x11 */ {1,  scsi_low_msginfunc_rejop},
 2687 /* 0x12 */ {1,  scsi_low_msginfunc_rejop},
 2688 /* 0x13 */ {1,  scsi_low_msginfunc_rejop},
 2689 /* 0x14 */ {1,  scsi_low_msginfunc_rejop},
 2690 /* 0x15 */ {1,  scsi_low_msginfunc_rejop},
 2691 /* 0x16 */ {1,  scsi_low_msginfunc_rejop},
 2692 /* 0x17 */ {1,  scsi_low_msginfunc_rejop},
 2693 /* 0x18 */ {1,  scsi_low_msginfunc_rejop},
 2694 /* 0x19 */ {1,  scsi_low_msginfunc_rejop},
 2695 /* 0x1a */ {1,  scsi_low_msginfunc_rejop},
 2696 /* 0x1b */ {1,  scsi_low_msginfunc_rejop},
 2697 /* 0x1c */ {1,  scsi_low_msginfunc_rejop},
 2698 /* 0x1d */ {1,  scsi_low_msginfunc_rejop},
 2699 /* 0x1e */ {1,  scsi_low_msginfunc_rejop},
 2700 /* 0x1f */ {1,  scsi_low_msginfunc_rejop},
 2701 /* 0x20 */ {2,  scsi_low_msginfunc_simple_qtag},
 2702 /* 0x21 */ {2,  scsi_low_msginfunc_rejop},
 2703 /* 0x22 */ {2,  scsi_low_msginfunc_rejop},
 2704 /* 0x23 */ {2,  scsi_low_msginfunc_i_wide_residue},
 2705 /* 0x24 */ {2,  scsi_low_msginfunc_rejop},
 2706 /* 0x25 */ {2,  scsi_low_msginfunc_rejop},
 2707 /* 0x26 */ {2,  scsi_low_msginfunc_rejop},
 2708 /* 0x27 */ {2,  scsi_low_msginfunc_rejop},
 2709 /* 0x28 */ {2,  scsi_low_msginfunc_rejop},
 2710 /* 0x29 */ {2,  scsi_low_msginfunc_rejop},
 2711 /* 0x2a */ {2,  scsi_low_msginfunc_rejop},
 2712 /* 0x2b */ {2,  scsi_low_msginfunc_rejop},
 2713 /* 0x2c */ {2,  scsi_low_msginfunc_rejop},
 2714 /* 0x2d */ {2,  scsi_low_msginfunc_rejop},
 2715 /* 0x2e */ {2,  scsi_low_msginfunc_rejop},
 2716 /* 0x2f */ {2,  scsi_low_msginfunc_rejop},
 2717 /* 0x30 */ {1,  scsi_low_msginfunc_rejop}       /* default rej op */
 2718 };
 2719 
 2720 /**************************************************************
 2721  * msgout
 2722  **************************************************************/
 2723 static int
 2724 scsi_low_msgfunc_synch(slp)
 2725         struct scsi_low_softc *slp;
 2726 {
 2727         struct targ_info *ti = slp->sl_Tnexus;
 2728         int ptr = ti->ti_msgoutlen;
 2729 
 2730         ti->ti_msgoutstr[ptr + 1] = MSG_EXTEND_SYNCHLEN;
 2731         ti->ti_msgoutstr[ptr + 2] = MSG_EXTEND_SYNCHCODE;
 2732         ti->ti_msgoutstr[ptr + 3] = ti->ti_maxsynch.period;
 2733         ti->ti_msgoutstr[ptr + 4] = ti->ti_maxsynch.offset;
 2734         return MSG_EXTEND_SYNCHLEN + 2;
 2735 }
 2736 
 2737 static int
 2738 scsi_low_msgfunc_wide(slp)
 2739         struct scsi_low_softc *slp;
 2740 {
 2741         struct targ_info *ti = slp->sl_Tnexus;
 2742         int ptr = ti->ti_msgoutlen;
 2743 
 2744         ti->ti_msgoutstr[ptr + 1] = MSG_EXTEND_WIDELEN;
 2745         ti->ti_msgoutstr[ptr + 2] = MSG_EXTEND_WIDECODE;
 2746         ti->ti_msgoutstr[ptr + 3] = ti->ti_width;
 2747         return MSG_EXTEND_WIDELEN + 2;
 2748 }
 2749 
 2750 static int
 2751 scsi_low_msgfunc_identify(slp)
 2752         struct scsi_low_softc *slp;
 2753 {
 2754         struct targ_info *ti = slp->sl_Tnexus;
 2755         struct lun_info *li = slp->sl_Lnexus;
 2756         struct slccb *cb = slp->sl_Qnexus;
 2757         int ptr = ti->ti_msgoutlen;
 2758         u_int8_t msg;
 2759 
 2760         msg = MSG_IDENTIFY;
 2761         if (cb == NULL)
 2762         {
 2763                 slp->sl_error |= FATALIO;
 2764                 scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_ABORT, 0);
 2765                 SCSI_LOW_INFO(slp, ti, "MSGOUT: nexus unknown");
 2766         }
 2767         else
 2768         {
 2769                 if (scsi_low_is_disconnect_ok(cb) != 0)
 2770                         msg |= (MSG_IDENTIFY_DISCPRIV | li->li_lun);
 2771                 else
 2772                         msg |= li->li_lun;
 2773 
 2774                 if (ti->ti_phase == PH_MSGOUT)
 2775                 {
 2776                         (*slp->sl_funcs->scsi_low_establish_lun_nexus) (slp);
 2777                         if (cb->ccb_tag == SCSI_LOW_UNKTAG)
 2778                         {
 2779                                 (*slp->sl_funcs->scsi_low_establish_ccb_nexus) (slp);
 2780                         }
 2781                 }
 2782         }
 2783         ti->ti_msgoutstr[ptr + 0] = msg;
 2784         return 1;
 2785 }
 2786 
 2787 static int
 2788 scsi_low_msgfunc_abort(slp)
 2789         struct scsi_low_softc *slp;
 2790 {
 2791 
 2792         SCSI_LOW_SETUP_MSGPHASE(slp, MSGPH_ABORT);
 2793         return 1;
 2794 }
 2795 
 2796 static int
 2797 scsi_low_msgfunc_qabort(slp)
 2798         struct scsi_low_softc *slp;
 2799 {
 2800 
 2801         SCSI_LOW_SETUP_MSGPHASE(slp, MSGPH_TERM);
 2802         return 1;
 2803 }
 2804 
 2805 static int
 2806 scsi_low_msgfunc_reset(slp)
 2807         struct scsi_low_softc *slp;
 2808 {
 2809 
 2810         SCSI_LOW_SETUP_MSGPHASE(slp, MSGPH_RESET);
 2811         return 1;
 2812 }
 2813 
 2814 static int
 2815 scsi_low_msgfunc_qtag(slp)
 2816         struct scsi_low_softc *slp;
 2817 {
 2818         struct targ_info *ti = slp->sl_Tnexus;
 2819         struct slccb *cb = slp->sl_Qnexus;
 2820         int ptr = ti->ti_msgoutlen;
 2821 
 2822         if (cb == NULL || cb->ccb_tag == SCSI_LOW_UNKTAG)
 2823         {
 2824                 ti->ti_msgoutstr[ptr + 0] = MSG_NOOP;
 2825                 return 1;
 2826         }
 2827         else
 2828         {
 2829                 ti->ti_msgoutstr[ptr + 1] = (u_int8_t) cb->ccb_tag;
 2830                 if (ti->ti_phase == PH_MSGOUT)
 2831                 {
 2832                         (*slp->sl_funcs->scsi_low_establish_ccb_nexus) (slp);
 2833                 }
 2834         }
 2835         return 2;
 2836 }
 2837 
 2838 /*
 2839  * The following functions are called when targets give unexpected
 2840  * responces in msgin (after msgout).
 2841  */
 2842 static int
 2843 scsi_low_errfunc_identify(slp, msgflags)
 2844         struct scsi_low_softc *slp;
 2845         u_int msgflags;
 2846 {
 2847 
 2848         if (slp->sl_Lnexus != NULL)
 2849         {
 2850                 slp->sl_Lnexus->li_cfgflags &= ~SCSI_LOW_DISC;
 2851                 scsi_low_calcf_lun(slp->sl_Lnexus);
 2852         }
 2853         return 0;
 2854 }
 2855 
 2856 static int
 2857 scsi_low_errfunc_synch(slp, msgflags)
 2858         struct scsi_low_softc *slp;
 2859         u_int msgflags;
 2860 {
 2861         struct targ_info *ti = slp->sl_Tnexus;
 2862 
 2863         MSGIN_PERIOD(ti) = 0;
 2864         MSGIN_OFFSET(ti) = 0;
 2865         scsi_low_synch(slp);
 2866         return 0;
 2867 }
 2868 
 2869 static int
 2870 scsi_low_errfunc_wide(slp, msgflags)
 2871         struct scsi_low_softc *slp;
 2872         u_int msgflags;
 2873 {
 2874         struct targ_info *ti = slp->sl_Tnexus;
 2875 
 2876         MSGIN_WIDTHP(ti) = 0;
 2877         scsi_low_wide(slp);
 2878         return 0;
 2879 }
 2880 
 2881 static int
 2882 scsi_low_errfunc_qtag(slp, msgflags)
 2883         struct scsi_low_softc *slp;
 2884         u_int msgflags;
 2885 {
 2886 
 2887         if ((msgflags & SCSI_LOW_MSG_REJECT) != 0)
 2888         {
 2889                 if (slp->sl_Qnexus != NULL)
 2890                 {
 2891                         scsi_low_deactivate_qtag(slp->sl_Qnexus);
 2892                 }
 2893                 if (slp->sl_Lnexus != NULL)
 2894                 {
 2895                         slp->sl_Lnexus->li_cfgflags &= ~SCSI_LOW_QTAG;
 2896                         scsi_low_calcf_lun(slp->sl_Lnexus);
 2897                 }
 2898                 device_printf(slp->sl_dev, "scsi_low: qtag msg rejected\n");
 2899         }
 2900         return 0;
 2901 }
 2902 
 2903 
 2904 int
 2905 scsi_low_msgout(slp, ti, fl)
 2906         struct scsi_low_softc *slp;
 2907         struct targ_info *ti;
 2908         u_int fl;
 2909 {
 2910         struct scsi_low_msgout_data *mdp;
 2911         int len = 0;
 2912 
 2913 #ifdef  SCSI_LOW_DIAGNOSTIC
 2914         if (ti != slp->sl_Tnexus)
 2915         {
 2916                 scsi_low_print(slp, NULL);
 2917                 panic("scsi_low_msgout: Target nexus inconsistent");
 2918         }
 2919 #endif  /* SCSI_LOW_DIAGNOSTIC */
 2920 
 2921         slp->sl_ph_count ++;
 2922         if (slp->sl_ph_count > SCSI_LOW_MAX_PHCHANGES)
 2923         {
 2924                 device_printf(slp->sl_dev, "too many phase changes\n");
 2925                 slp->sl_error |= FATALIO;
 2926                 scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_ABORT, 0);
 2927         }
 2928                 
 2929         /* STEP I.
 2930          * Scsi phase changes.
 2931          * Previously msgs asserted are accepted by our target or
 2932          * processed by scsi_low_msgin.
 2933          * Thus clear all saved informations.
 2934          */
 2935         if ((fl & SCSI_LOW_MSGOUT_INIT) != 0)
 2936         {
 2937                 ti->ti_omsgflags = 0;
 2938                 ti->ti_emsgflags = 0;
 2939         }
 2940         else if (slp->sl_atten == 0)
 2941         {
 2942         /* STEP II.
 2943          * We did not assert attention, however still our target required
 2944          * msgs. Resend previous msgs. 
 2945          */
 2946                 ti->ti_msgflags |= ti->ti_omsgflags;
 2947                 ti->ti_omsgflags = 0;
 2948 #ifdef  SCSI_LOW_DIAGNOSTIC
 2949                 device_printf(slp->sl_dev, "scsi_low_msgout: retry msgout\n");
 2950 #endif  /* SCSI_LOW_DIAGNOSTIC */
 2951         }
 2952 
 2953         /* STEP III.
 2954          * We have no msgs. send MSG_NOOP (OK?)
 2955          */
 2956         if (scsi_low_is_msgout_continue(ti, 0) == 0)
 2957                 scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_NOOP, 0);
 2958 
 2959         /* STEP IV.
 2960          * Process all msgs
 2961          */
 2962         ti->ti_msgoutlen = 0;
 2963         slp->sl_clear_atten = 0;
 2964         mdp = &scsi_low_msgout_data[0];
 2965         for ( ; mdp->md_flags != SCSI_LOW_MSG_ALL; mdp ++)
 2966         {
 2967                 if ((ti->ti_msgflags & mdp->md_flags) != 0)
 2968                 {
 2969                         ti->ti_omsgflags |= mdp->md_flags;
 2970                         ti->ti_msgflags &= ~mdp->md_flags;
 2971                         ti->ti_emsgflags = mdp->md_flags;
 2972 
 2973                         ti->ti_msgoutstr[ti->ti_msgoutlen] = mdp->md_msg;
 2974                         if (mdp->md_msgfunc != NULL)
 2975                                 len = (*mdp->md_msgfunc) (slp);
 2976                         else
 2977                                 len = 1;
 2978 
 2979 #ifdef  SCSI_LOW_DIAGNOSTIC
 2980                         scsi_low_msg_log_write(&ti->ti_log_msgout,
 2981                                &ti->ti_msgoutstr[ti->ti_msgoutlen], len);
 2982 #endif  /* SCSI_LOW_DIAGNOSTIC */
 2983 
 2984                         ti->ti_msgoutlen += len;
 2985                         if ((mdp->md_condition & MSG_RELEASE_ATN) != 0)
 2986                         {
 2987                                 slp->sl_clear_atten = 1;
 2988                                 break;
 2989                         }
 2990 
 2991                         if ((fl & SCSI_LOW_MSGOUT_UNIFY) == 0 ||
 2992                             ti->ti_msgflags == 0)
 2993                                 break;
 2994 
 2995                         if (ti->ti_msgoutlen >= SCSI_LOW_MAX_MSGLEN - 5)
 2996                                 break;
 2997                 }
 2998         }
 2999 
 3000         if (scsi_low_is_msgout_continue(ti, 0) == 0)
 3001                 slp->sl_clear_atten = 1;
 3002 
 3003         return ti->ti_msgoutlen;
 3004 }
 3005 
 3006 /**************************************************************
 3007  * msgin
 3008  **************************************************************/
 3009 static int
 3010 scsi_low_msginfunc_noop(slp)
 3011         struct scsi_low_softc *slp;
 3012 {
 3013 
 3014         return 0;
 3015 }
 3016 
 3017 static int
 3018 scsi_low_msginfunc_rejop(slp)
 3019         struct scsi_low_softc *slp;
 3020 {
 3021         struct targ_info *ti = slp->sl_Tnexus;
 3022         u_int8_t msg = ti->ti_msgin[0];
 3023 
 3024         device_printf(slp->sl_dev, "MSGIN: msg 0x%x rejected\n", (u_int) msg);
 3025         scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_REJECT, 0);
 3026         return 0;
 3027 }
 3028 
 3029 static int
 3030 scsi_low_msginfunc_cc(slp)
 3031         struct scsi_low_softc *slp;
 3032 {
 3033         struct lun_info *li;
 3034 
 3035         SCSI_LOW_SETUP_MSGPHASE(slp, MSGPH_CMDC);
 3036 
 3037         /* validate status */
 3038         if (slp->sl_Qnexus == NULL)
 3039                 return ENOENT;
 3040 
 3041         slp->sl_Qnexus->ccb_sscp.scp_status = slp->sl_scp.scp_status;
 3042         li = slp->sl_Lnexus;
 3043         switch (slp->sl_scp.scp_status)
 3044         {
 3045         case ST_GOOD:
 3046                 li->li_maxnqio = li->li_maxnexus;
 3047                 break;
 3048 
 3049         case ST_CHKCOND:
 3050                 li->li_maxnqio = 0;
 3051                 if (li->li_qflags & SCSI_LOW_QFLAG_CA_QCLEAR)
 3052                         scsi_low_reset_nexus_lun(slp, li, 0);
 3053                 break;
 3054 
 3055         case ST_BUSY:
 3056                 li->li_maxnqio = 0;
 3057                 break;
 3058 
 3059         case ST_QUEFULL:
 3060                 if (li->li_maxnexus >= li->li_nqio)
 3061                         li->li_maxnexus = li->li_nqio - 1;
 3062                 li->li_maxnqio = li->li_maxnexus;
 3063                 break;
 3064 
 3065         case ST_INTERGOOD:
 3066         case ST_INTERMET:
 3067                 slp->sl_error |= MSGERR;
 3068                 break;
 3069 
 3070         default:
 3071                 break;
 3072         }
 3073         return 0;
 3074 }
 3075 
 3076 static int
 3077 scsi_low_msginfunc_lcc(slp)
 3078         struct scsi_low_softc *slp;
 3079 {
 3080         struct targ_info *ti;
 3081         struct lun_info *li;
 3082         struct slccb *ncb, *cb;
 3083 
 3084         ti = slp->sl_Tnexus;
 3085         li = slp->sl_Lnexus;
 3086         if ((cb = slp->sl_Qnexus) == NULL)
 3087                 goto bad;
 3088                 
 3089         cb->ccb_sscp.scp_status = slp->sl_scp.scp_status;
 3090         switch (slp->sl_scp.scp_status)
 3091         {
 3092         case ST_INTERGOOD:
 3093         case ST_INTERMET:
 3094                 li->li_maxnqio = li->li_maxnexus;
 3095                 break;
 3096 
 3097         default:
 3098                 slp->sl_error |= MSGERR;
 3099                 break;
 3100         }
 3101 
 3102         if ((li->li_flags & SCSI_LOW_LINK) == 0)
 3103                 goto bad;
 3104 
 3105         cb->ccb_error |= slp->sl_error;
 3106         if (cb->ccb_error != 0)
 3107                 goto bad;
 3108 
 3109         for (ncb = TAILQ_FIRST(&slp->sl_start); ncb != NULL;
 3110              ncb = TAILQ_NEXT(ncb, ccb_chain))
 3111         {
 3112                 if (ncb->li == li)
 3113                         goto cmd_link_start;
 3114         }
 3115 
 3116 
 3117 bad:
 3118         SCSI_LOW_SETUP_MSGPHASE(slp, MSGPH_LCTERM);
 3119         scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_REJECT, 0);
 3120         return EIO;
 3121 
 3122 cmd_link_start:
 3123         ncb->ccb_flags &= ~CCB_STARTQ;
 3124         TAILQ_REMOVE(&slp->sl_start, ncb, ccb_chain);
 3125 
 3126         scsi_low_dealloc_qtag(ncb);
 3127         ncb->ccb_tag = cb->ccb_tag;
 3128         ncb->ccb_otag = cb->ccb_otag;
 3129         cb->ccb_tag = SCSI_LOW_UNKTAG;
 3130         cb->ccb_otag = SCSI_LOW_UNKTAG;
 3131         if (scsi_low_done(slp, cb) == SCSI_LOW_DONE_RETRY)
 3132                 panic("%s: linked ccb retried",
 3133                     device_get_nameunit(slp->sl_dev));
 3134 
 3135         slp->sl_Qnexus = ncb;
 3136         slp->sl_ph_count = 0;
 3137 
 3138         ncb->ccb_error = 0;
 3139         ncb->ccb_datalen = -1;
 3140         ncb->ccb_scp.scp_status = ST_UNKNOWN;
 3141         ncb->ccb_flags &= ~CCB_INTERNAL;
 3142 
 3143         scsi_low_init_msgsys(slp, ti);
 3144 
 3145         (*slp->sl_osdep_fp->scsi_low_osdep_ccb_setup) (slp, ncb);
 3146 
 3147         if (ncb->ccb_tcmax < SCSI_LOW_MIN_TOUT)
 3148                 ncb->ccb_tcmax = SCSI_LOW_MIN_TOUT;
 3149         ncb->ccb_tc = ncb->ccb_tcmax;
 3150 
 3151         /* setup saved scsi data pointer */
 3152         ncb->ccb_sscp = ncb->ccb_scp;
 3153         slp->sl_scp = ncb->ccb_sscp;
 3154         slp->sl_error = ncb->ccb_error;
 3155 
 3156 #ifdef  SCSI_LOW_DIAGNOSTIC
 3157         scsi_low_msg_log_init(&ti->ti_log_msgin);
 3158         scsi_low_msg_log_init(&ti->ti_log_msgout);
 3159 #endif  /* SCSI_LOW_DIAGNOSTIC */
 3160         return EJUSTRETURN;
 3161 }
 3162 
 3163 static int
 3164 scsi_low_msginfunc_disc(slp)
 3165         struct scsi_low_softc *slp;
 3166 {
 3167 
 3168         SCSI_LOW_SETUP_MSGPHASE(slp, MSGPH_DISC);
 3169         return 0;
 3170 }
 3171 
 3172 static int
 3173 scsi_low_msginfunc_sdp(slp)
 3174         struct scsi_low_softc *slp;
 3175 {
 3176         struct slccb *cb = slp->sl_Qnexus;
 3177 
 3178         if (cb != NULL)
 3179         {
 3180                 cb->ccb_sscp.scp_datalen = slp->sl_scp.scp_datalen;
 3181                 cb->ccb_sscp.scp_data = slp->sl_scp.scp_data;
 3182         }
 3183         else
 3184                 scsi_low_assert_msg(slp, slp->sl_Tnexus, SCSI_LOW_MSG_REJECT, 0);
 3185         return 0;
 3186 }
 3187 
 3188 static int
 3189 scsi_low_msginfunc_rp(slp)
 3190         struct scsi_low_softc *slp;
 3191 {
 3192 
 3193         if (slp->sl_Qnexus != NULL)
 3194                 slp->sl_scp = slp->sl_Qnexus->ccb_sscp;
 3195         else
 3196                 scsi_low_assert_msg(slp, slp->sl_Tnexus, SCSI_LOW_MSG_REJECT, 0);
 3197         return 0;
 3198 }
 3199 
 3200 static int
 3201 scsi_low_synch(slp)
 3202         struct scsi_low_softc *slp;
 3203 {
 3204         struct targ_info *ti = slp->sl_Tnexus;
 3205         u_int period = 0, offset = 0, speed;
 3206         u_char *s;
 3207         int error;
 3208 
 3209         if ((MSGIN_PERIOD(ti) >= ti->ti_maxsynch.period &&
 3210              MSGIN_OFFSET(ti) <= ti->ti_maxsynch.offset) ||
 3211              MSGIN_OFFSET(ti) == 0)
 3212         {
 3213                 if ((offset = MSGIN_OFFSET(ti)) != 0)
 3214                         period = MSGIN_PERIOD(ti);
 3215                 s = offset ? "synchronous" : "async";
 3216         }
 3217         else
 3218         {
 3219                 /* XXX:
 3220                  * Target seems to be brain damaged.
 3221                  * Force async transfer.
 3222                  */
 3223                 ti->ti_maxsynch.period = 0;
 3224                 ti->ti_maxsynch.offset = 0;
 3225                 device_printf(slp->sl_dev,
 3226                     "target brain damaged. async transfer\n");
 3227                 return EINVAL;
 3228         }
 3229 
 3230         ti->ti_maxsynch.period = period;
 3231         ti->ti_maxsynch.offset = offset;
 3232 
 3233         error = (*slp->sl_funcs->scsi_low_msg) (slp, ti, SCSI_LOW_MSG_SYNCH);
 3234         if (error != 0)
 3235         {
 3236                 /* XXX:
 3237                  * Current period and offset are not acceptable 
 3238                  * for our adapter.
 3239                  * The adapter changes max synch and max offset.
 3240                  */
 3241                 device_printf(slp->sl_dev,
 3242                     "synch neg failed. retry synch msg neg ...\n");
 3243                 return error;
 3244         }
 3245 
 3246         ti->ti_osynch = ti->ti_maxsynch;
 3247         if (offset > 0)
 3248         {
 3249                 ti->ti_setup_msg_done |= SCSI_LOW_MSG_SYNCH;
 3250         }
 3251 
 3252         /* inform data */
 3253         if ((slp->sl_show_result & SHOW_SYNCH_NEG) != 0)
 3254         {
 3255 #ifdef  SCSI_LOW_NEGOTIATE_BEFORE_SENSE
 3256                 struct slccb *cb = slp->sl_Qnexus;
 3257 
 3258                 if (cb != NULL && (cb->ccb_flags & CCB_SENSE) != 0)
 3259                         return 0;
 3260 #endif  /* SCSI_LOW_NEGOTIATE_BEFORE_SENSE */
 3261 
 3262                 device_printf(slp->sl_dev,
 3263                     "(%d:*): <%s> offset %d period %dns ",
 3264                     ti->ti_id, s, offset, period * 4);
 3265 
 3266                 if (period != 0)
 3267                 {
 3268                         speed = 1000 * 10 / (period * 4);
 3269                         printf("%d.%d M/s", speed / 10, speed % 10);
 3270                 }
 3271                 printf("\n");
 3272         }
 3273         return 0;
 3274 }
 3275 
 3276 static int
 3277 scsi_low_wide(slp)
 3278         struct scsi_low_softc *slp;
 3279 {
 3280         struct targ_info *ti = slp->sl_Tnexus;
 3281         int error;
 3282 
 3283         ti->ti_width = MSGIN_WIDTHP(ti);
 3284         error = (*slp->sl_funcs->scsi_low_msg) (slp, ti, SCSI_LOW_MSG_WIDE);
 3285         if (error != 0)
 3286         {
 3287                 /* XXX:
 3288                  * Current width is not acceptable for our adapter.
 3289                  * The adapter changes max width.
 3290                  */
 3291                 device_printf(slp->sl_dev,
 3292                     "wide neg failed. retry wide msg neg ...\n");
 3293                 return error;
 3294         }
 3295 
 3296         ti->ti_owidth = ti->ti_width;
 3297         if (ti->ti_width > SCSI_LOW_BUS_WIDTH_8)
 3298         {
 3299                 ti->ti_setup_msg_done |= 
 3300                         (SCSI_LOW_MSG_SYNCH | SCSI_LOW_MSG_WIDE);
 3301         }
 3302                 
 3303         /* inform data */
 3304         if ((slp->sl_show_result & SHOW_WIDE_NEG) != 0)
 3305         {
 3306 #ifdef  SCSI_LOW_NEGOTIATE_BEFORE_SENSE
 3307                 struct slccb *cb = slp->sl_Qnexus;
 3308 
 3309                 if (cb != NULL && (cb->ccb_flags & CCB_SENSE) != 0)
 3310                         return 0;
 3311 #endif  /* SCSI_LOW_NEGOTIATE_BEFORE_SENSE */
 3312 
 3313                 device_printf(slp->sl_dev, "(%d:*): transfer width %d bits\n",
 3314                     ti->ti_id, 1 << (3 + ti->ti_width));
 3315         }
 3316         return 0;
 3317 }
 3318 
 3319 static int
 3320 scsi_low_msginfunc_simple_qtag(slp)
 3321         struct scsi_low_softc *slp;
 3322 {
 3323         struct targ_info *ti = slp->sl_Tnexus;
 3324         scsi_low_tag_t etag = (scsi_low_tag_t) ti->ti_msgin[1];
 3325 
 3326         if (slp->sl_Qnexus != NULL)
 3327         {
 3328                 if (slp->sl_Qnexus->ccb_tag != etag)
 3329                 {
 3330                         slp->sl_error |= FATALIO;
 3331                         scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_ABORT, 0);
 3332                         SCSI_LOW_INFO(slp, ti, "MSGIN: qtag mismatch");
 3333                 }
 3334         }
 3335         else if (scsi_low_establish_ccb(ti, slp->sl_Lnexus, etag) == NULL)
 3336         {
 3337 #ifdef  SCSI_LOW_DEBUG
 3338                 if (SCSI_LOW_DEBUG_TEST_GO(SCSI_LOW_NEXUS_CHECK, ti->ti_id))
 3339                         return 0;
 3340 #endif  /* SCSI_LOW_DEBUG */
 3341 
 3342                 slp->sl_error |= FATALIO;
 3343                 scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_ABORT_QTAG, 0);
 3344                 SCSI_LOW_INFO(slp, ti, "MSGIN: taged ccb not found");
 3345         }
 3346         return 0;
 3347 }
 3348 
 3349 static int
 3350 scsi_low_msginfunc_i_wide_residue(slp)
 3351         struct scsi_low_softc *slp;
 3352 {
 3353         struct targ_info *ti = slp->sl_Tnexus;
 3354         struct slccb *cb = slp->sl_Qnexus;
 3355         int res = (int) ti->ti_msgin[1];
 3356 
 3357         if (cb == NULL || res <= 0 ||
 3358             (ti->ti_width == SCSI_LOW_BUS_WIDTH_16 && res > 1) ||
 3359             (ti->ti_width == SCSI_LOW_BUS_WIDTH_32 && res > 3))
 3360                 return EINVAL;
 3361                 
 3362         if (slp->sl_scp.scp_datalen + res > cb->ccb_scp.scp_datalen)
 3363                 return EINVAL;
 3364 
 3365         slp->sl_scp.scp_datalen += res;
 3366         slp->sl_scp.scp_data -= res;
 3367         scsi_low_data_finish(slp);
 3368         return 0;
 3369 }
 3370 
 3371 static int
 3372 scsi_low_msginfunc_ext(slp)
 3373         struct scsi_low_softc *slp;
 3374 {
 3375         struct slccb *cb = slp->sl_Qnexus;
 3376         struct lun_info *li = slp->sl_Lnexus;
 3377         struct targ_info *ti = slp->sl_Tnexus;
 3378         int count, retry;
 3379         u_int32_t *ptr;
 3380 
 3381         if (ti->ti_msginptr == 2)
 3382         {
 3383                 ti->ti_msginlen = ti->ti_msgin[1] + 2;
 3384                 return 0;
 3385         }
 3386 
 3387         switch (MKMSG_EXTEND(ti->ti_msgin[1], ti->ti_msgin[2]))
 3388         {
 3389         case MKMSG_EXTEND(MSG_EXTEND_MDPLEN, MSG_EXTEND_MDPCODE):
 3390                 if (cb == NULL)
 3391                         break;
 3392 
 3393                 ptr = (u_int32_t *)(&ti->ti_msgin[3]);
 3394                 count = (int) htonl((long) (*ptr));
 3395                 if(slp->sl_scp.scp_datalen - count < 0 || 
 3396                    slp->sl_scp.scp_datalen - count > cb->ccb_scp.scp_datalen)
 3397                         break;
 3398 
 3399                 slp->sl_scp.scp_datalen -= count;
 3400                 slp->sl_scp.scp_data += count;
 3401                 return 0;
 3402 
 3403         case MKMSG_EXTEND(MSG_EXTEND_SYNCHLEN, MSG_EXTEND_SYNCHCODE):
 3404                 if (li == NULL)
 3405                         break;
 3406 
 3407                 retry = scsi_low_synch(slp);
 3408                 if (retry != 0 || (ti->ti_emsgflags & SCSI_LOW_MSG_SYNCH) == 0)
 3409                         scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_SYNCH, 0);
 3410 
 3411 #ifdef  SCSI_LOW_DEBUG
 3412                 if (SCSI_LOW_DEBUG_TEST_GO(SCSI_LOW_ATTEN_CHECK, ti->ti_id))
 3413                 {
 3414                         scsi_low_test_atten(slp, ti, SCSI_LOW_MSG_SYNCH);
 3415                 }
 3416 #endif  /* SCSI_LOW_DEBUG */
 3417                 return 0;
 3418 
 3419         case MKMSG_EXTEND(MSG_EXTEND_WIDELEN, MSG_EXTEND_WIDECODE):
 3420                 if (li == NULL)
 3421                         break;
 3422 
 3423                 retry = scsi_low_wide(slp);
 3424                 if (retry != 0 || (ti->ti_emsgflags & SCSI_LOW_MSG_WIDE) == 0)
 3425                         scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_WIDE, 0);
 3426 
 3427                 return 0;
 3428 
 3429         default:
 3430                 break;
 3431         }
 3432 
 3433         scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_REJECT, 0);
 3434         return EINVAL;
 3435 }
 3436 
 3437 static int
 3438 scsi_low_msginfunc_parity(slp)
 3439         struct scsi_low_softc *slp;
 3440 {
 3441         struct targ_info *ti = slp->sl_Tnexus;
 3442 
 3443         /* only I -> T, invalid! */
 3444         scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_REJECT, 0);
 3445         return 0;
 3446 }
 3447 
 3448 static int
 3449 scsi_low_msginfunc_msg_reject(slp)
 3450         struct scsi_low_softc *slp;
 3451 {
 3452         struct targ_info *ti = slp->sl_Tnexus;
 3453         struct scsi_low_msgout_data *mdp;
 3454         u_int msgflags;
 3455 
 3456         if (ti->ti_emsgflags != 0)
 3457         {
 3458                 device_printf(slp->sl_dev, "msg flags [0x%x] rejected\n",
 3459                     ti->ti_emsgflags);
 3460                 msgflags = SCSI_LOW_MSG_REJECT;
 3461                 mdp = &scsi_low_msgout_data[0];
 3462                 for ( ; mdp->md_flags != SCSI_LOW_MSG_ALL; mdp ++)
 3463                 {
 3464                         if ((ti->ti_emsgflags & mdp->md_flags) != 0)
 3465                         {
 3466                                 ti->ti_emsgflags &= ~mdp->md_flags;
 3467                                 if (mdp->md_errfunc != NULL)
 3468                                         (*mdp->md_errfunc) (slp, msgflags);
 3469                                 break;
 3470                         }
 3471                 }
 3472                 return 0;
 3473         }
 3474         else
 3475         {
 3476                 SCSI_LOW_INFO(slp, ti, "MSGIN: rejected msg not found");
 3477                 slp->sl_error |= MSGERR;
 3478         }
 3479         return EINVAL;
 3480 }
 3481 
 3482 int
 3483 scsi_low_msgin(slp, ti, c)
 3484         struct scsi_low_softc *slp;
 3485         struct targ_info *ti;
 3486         u_int c;
 3487 {
 3488         struct scsi_low_msgin_data *sdp;
 3489         struct lun_info *li;
 3490         u_int8_t msg;
 3491 
 3492 #ifdef  SCSI_LOW_DIAGNOSTIC
 3493         if (ti != slp->sl_Tnexus)
 3494         {
 3495                 scsi_low_print(slp, NULL);
 3496                 panic("scsi_low_msgin: Target nexus inconsistent");
 3497         }
 3498 #endif  /* SCSI_LOW_DIAGNOSTIC */
 3499 
 3500         /*
 3501          * Phase changes, clear the pointer.
 3502          */
 3503         if (ti->ti_ophase != ti->ti_phase)
 3504         {
 3505                 MSGINPTR_CLR(ti);
 3506                 ti->ti_msgin_parity_error = 0;
 3507 
 3508                 slp->sl_ph_count ++;
 3509                 if (slp->sl_ph_count > SCSI_LOW_MAX_PHCHANGES)
 3510                 {
 3511                         device_printf(slp->sl_dev, "too many phase changes\n");
 3512                         slp->sl_error |= FATALIO;
 3513                         scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_ABORT, 0);
 3514                 }
 3515         }
 3516 
 3517         /*
 3518          * Store a current messages byte into buffer and 
 3519          * wait for the completion of the current msg.
 3520          */
 3521         ti->ti_msgin[ti->ti_msginptr ++] = (u_int8_t) c;
 3522         if (ti->ti_msginptr >= SCSI_LOW_MAX_MSGLEN)
 3523         {
 3524                 ti->ti_msginptr = SCSI_LOW_MAX_MSGLEN - 1;
 3525                 scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_REJECT, 0);
 3526         }       
 3527 
 3528         /*
 3529          * Check parity errors.
 3530          */
 3531         if ((c & SCSI_LOW_DATA_PE) != 0)
 3532         {
 3533                 ti->ti_msgin_parity_error ++;
 3534                 scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_PARITY, 0);
 3535                 goto out;
 3536         }
 3537 
 3538         if (ti->ti_msgin_parity_error != 0)
 3539                 goto out;
 3540 
 3541         /*
 3542          * Calculate messages length.
 3543          */
 3544         msg = ti->ti_msgin[0];
 3545         if (msg < MSGIN_DATA_LAST)
 3546                 sdp = &scsi_low_msgin_data[msg];
 3547         else
 3548                 sdp = &scsi_low_msgin_data[MSGIN_DATA_LAST];
 3549 
 3550         if (ti->ti_msginlen == 0)
 3551         {
 3552                 ti->ti_msginlen = sdp->md_len;
 3553         }
 3554 
 3555         /*
 3556          * Check comletion.
 3557          */
 3558         if (ti->ti_msginptr < ti->ti_msginlen)
 3559                 return EJUSTRETURN;
 3560 
 3561         /*
 3562          * Do process.
 3563          */
 3564         if ((msg & MSG_IDENTIFY) == 0)
 3565         {
 3566                 if (((*sdp->md_msgfunc) (slp)) == EJUSTRETURN)
 3567                         return EJUSTRETURN;
 3568         }
 3569         else
 3570         {
 3571                 li = slp->sl_Lnexus;
 3572                 if (li == NULL)
 3573                 {
 3574                         li = scsi_low_alloc_li(ti, MSGCMD_LUN(msg), 0);
 3575                         if (li == NULL)
 3576                                 goto badlun;
 3577                         slp->sl_Lnexus = li;
 3578                         (*slp->sl_funcs->scsi_low_establish_lun_nexus) (slp);
 3579                 }       
 3580                 else
 3581                 {
 3582                         if (MSGCMD_LUN(msg) != li->li_lun)
 3583                                 goto badlun;
 3584                 }
 3585 
 3586                 if (slp->sl_Qnexus == NULL && li->li_nqio == 0)
 3587                 {
 3588                         if (!scsi_low_establish_ccb(ti, li, SCSI_LOW_UNKTAG))
 3589                         {
 3590 #ifdef  SCSI_LOW_DEBUG
 3591                                 if (SCSI_LOW_DEBUG_TEST_GO(SCSI_LOW_NEXUS_CHECK, ti->ti_id) != 0)
 3592                                 {
 3593                                         goto out;
 3594                                 }
 3595 #endif  /* SCSI_LOW_DEBUG */
 3596                                 goto badlun;
 3597                         }
 3598                 }
 3599         }
 3600         goto out;
 3601 
 3602         /*
 3603          * Msg process completed, reset msgin pointer and assert ATN if desired.
 3604          */
 3605 badlun:
 3606         slp->sl_error |= FATALIO;
 3607         scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_ABORT, 0);
 3608         SCSI_LOW_INFO(slp, ti, "MSGIN: identify wrong");
 3609 
 3610 out:
 3611         if (ti->ti_msginptr < ti->ti_msginlen)
 3612                 return EJUSTRETURN;
 3613 
 3614 #ifdef  SCSI_LOW_DIAGNOSTIC
 3615         scsi_low_msg_log_write(&ti->ti_log_msgin,
 3616                                &ti->ti_msgin[0], ti->ti_msginlen);
 3617 #endif  /* SCSI_LOW_DIAGNOSTIC */
 3618 
 3619         MSGINPTR_CLR(ti);
 3620         return 0;
 3621 }
 3622 
 3623 /**********************************************************
 3624  * disconnect
 3625  **********************************************************/
 3626 int
 3627 scsi_low_disconnected(slp, ti)
 3628         struct scsi_low_softc *slp;
 3629         struct targ_info *ti;
 3630 {
 3631         struct slccb *cb = slp->sl_Qnexus;
 3632 
 3633         /* check phase completion */
 3634         switch (slp->sl_msgphase)
 3635         {
 3636         case MSGPH_RESET:
 3637                 scsi_low_statusin(slp, slp->sl_Tnexus, ST_GOOD);
 3638                 scsi_low_msginfunc_cc(slp);
 3639                 scsi_low_reset_nexus_target(slp, slp->sl_Tnexus, 0);
 3640                 goto io_resume;
 3641 
 3642         case MSGPH_ABORT:
 3643                 scsi_low_statusin(slp, slp->sl_Tnexus, ST_GOOD);
 3644                 scsi_low_msginfunc_cc(slp);
 3645                 scsi_low_reset_nexus_lun(slp, slp->sl_Lnexus, 0);
 3646                 goto io_resume;
 3647 
 3648         case MSGPH_TERM:
 3649                 scsi_low_statusin(slp, slp->sl_Tnexus, ST_GOOD);
 3650                 scsi_low_msginfunc_cc(slp);
 3651                 goto io_resume;
 3652 
 3653         case MSGPH_DISC:
 3654                 if (cb != NULL)
 3655                 {
 3656                         struct lun_info *li;
 3657 
 3658                         li = cb->li;
 3659                         TAILQ_INSERT_TAIL(&li->li_discq, cb, ccb_chain);
 3660                         cb->ccb_flags |= CCB_DISCQ;
 3661                         cb->ccb_error |= slp->sl_error;
 3662                         li->li_disc ++;
 3663                         ti->ti_disc ++;
 3664                         slp->sl_disc ++;
 3665                 }
 3666 
 3667 #ifdef  SCSI_LOW_STATICS
 3668                 scsi_low_statics.nexus_disconnected ++;
 3669 #endif  /* SCSI_LOW_STATICS */
 3670 
 3671 #ifdef  SCSI_LOW_DEBUG
 3672                 if (SCSI_LOW_DEBUG_GO(SCSI_LOW_DEBUG_DISC, ti->ti_id) != 0)
 3673                 {
 3674                         printf("## SCSI_LOW_DISCONNECTED ===============\n");
 3675                         scsi_low_print(slp, NULL);
 3676                 }
 3677 #endif  /* SCSI_LOW_DEBUG */
 3678                 break;
 3679 
 3680         case MSGPH_NULL:
 3681                 slp->sl_error |= FATALIO;
 3682                 if (ti->ti_phase == PH_SELSTART)
 3683                         slp->sl_error |= SELTIMEOUTIO;
 3684                 else
 3685                         slp->sl_error |= UBFERR;
 3686                 /* fall through */
 3687 
 3688         case MSGPH_LCTERM:
 3689         case MSGPH_CMDC:
 3690 io_resume:
 3691                 if (cb == NULL)
 3692                         break;
 3693 
 3694 #ifdef  SCSI_LOW_DEBUG
 3695                 if (SCSI_LOW_DEBUG_TEST_GO(SCSI_LOW_ATTEN_CHECK, ti->ti_id))
 3696                 {
 3697                         if (cb->ccb_omsgoutflag == SCSI_LOW_MSG_NOOP &&
 3698                             (cb->ccb_msgoutflag != 0 ||
 3699                              (ti->ti_msgflags & SCSI_LOW_MSG_NOOP)))
 3700                         {
 3701                                 scsi_low_info(slp, ti, "ATTEN CHECK FAILED");
 3702                         }
 3703                 }
 3704 #endif  /* SCSI_LOW_DEBUG */
 3705 
 3706                 cb->ccb_error |= slp->sl_error;
 3707                 if (scsi_low_done(slp, cb) == SCSI_LOW_DONE_RETRY)
 3708                 {
 3709                         cb->ccb_flags |= CCB_STARTQ;
 3710                         TAILQ_INSERT_HEAD(&slp->sl_start, cb, ccb_chain);
 3711                 }
 3712                 break;
 3713         }
 3714 
 3715         scsi_low_bus_release(slp, ti);  
 3716         scsi_low_start(slp);
 3717         return 1;
 3718 }
 3719 
 3720 /**********************************************************
 3721  * TAG operations
 3722  **********************************************************/
 3723 static int
 3724 scsi_low_alloc_qtag(cb)
 3725         struct slccb *cb;
 3726 {
 3727         struct lun_info *li = cb->li;
 3728         scsi_low_tag_t etag;
 3729 
 3730         if (cb->ccb_otag != SCSI_LOW_UNKTAG)
 3731                 return 0;
 3732 
 3733 #ifndef SCSI_LOW_ALT_QTAG_ALLOCATE
 3734         etag = ffs(li->li_qtagbits);
 3735         if (etag == 0)
 3736                 return ENOSPC;
 3737 
 3738         li->li_qtagbits &= ~(1 << (etag - 1));
 3739         cb->ccb_otag = etag;
 3740         return 0;
 3741 
 3742 #else   /* SCSI_LOW_ALT_QTAG_ALLOCATE */
 3743         for (etag = li->li_qd ; li->li_qd < SCSI_LOW_MAXNEXUS; li->li_qd ++)
 3744                 if (li->li_qtagarray[li->li_qd] == 0)
 3745                         goto found;
 3746 
 3747         for (li->li_qd = 0; li->li_qd < etag; li->li_qd ++)
 3748                 if (li->li_qtagarray[li->li_qd] == 0)
 3749                         goto found;
 3750 
 3751         return ENOSPC;
 3752 
 3753 found:
 3754         li->li_qtagarray[li->li_qd] ++;
 3755         cb->ccb_otag = (li->li_qd ++);
 3756         return 0;
 3757 #endif  /* SCSI_LOW_ALT_QTAG_ALLOCATE */
 3758 }
 3759         
 3760 static int
 3761 scsi_low_dealloc_qtag(cb)
 3762         struct slccb *cb;
 3763 {
 3764         struct lun_info *li = cb->li;
 3765         scsi_low_tag_t etag;
 3766 
 3767         if (cb->ccb_otag == SCSI_LOW_UNKTAG)
 3768                 return 0;
 3769 
 3770 #ifndef SCSI_LOW_ALT_QTAG_ALLOCATE
 3771         etag = cb->ccb_otag - 1;
 3772 #ifdef  SCSI_LOW_DIAGNOSTIC
 3773         if (etag >= sizeof(li->li_qtagbits) * NBBY)
 3774                 panic("scsi_low_dealloc_tag: illegal tag");
 3775 #endif  /* SCSI_LOW_DIAGNOSTIC */
 3776         li->li_qtagbits |= (1 << etag);
 3777 
 3778 #else   /* SCSI_LOW_ALT_QTAG_ALLOCATE */
 3779         etag = cb->ccb_otag;
 3780 #ifdef  SCSI_LOW_DIAGNOSTIC
 3781         if (etag >= SCSI_LOW_MAXNEXUS)
 3782                 panic("scsi_low_dealloc_tag: illegal tag");
 3783 #endif  /* SCSI_LOW_DIAGNOSTIC */
 3784         li->li_qtagarray[etag] --;
 3785 #endif  /* SCSI_LOW_ALT_QTAG_ALLOCATE */
 3786 
 3787         cb->ccb_otag = SCSI_LOW_UNKTAG;
 3788         return 0;
 3789 }
 3790 
 3791 static struct slccb *
 3792 scsi_low_revoke_ccb(slp, cb, fdone)
 3793         struct scsi_low_softc *slp;
 3794         struct slccb *cb;
 3795         int fdone;
 3796 {
 3797         struct targ_info *ti = cb->ti;
 3798         struct lun_info *li = cb->li;
 3799 
 3800 #ifdef  SCSI_LOW_DIAGNOSTIC
 3801         if ((cb->ccb_flags & (CCB_STARTQ | CCB_DISCQ)) == 
 3802             (CCB_STARTQ | CCB_DISCQ))
 3803         {
 3804                 panic("%s: ccb in both queue",
 3805                     device_get_nameunit(slp->sl_dev));
 3806         }
 3807 #endif  /* SCSI_LOW_DIAGNOSTIC */
 3808 
 3809         if ((cb->ccb_flags & CCB_STARTQ) != 0)
 3810         {
 3811                 TAILQ_REMOVE(&slp->sl_start, cb, ccb_chain);
 3812         }
 3813 
 3814         if ((cb->ccb_flags & CCB_DISCQ) != 0)
 3815         {
 3816                 TAILQ_REMOVE(&li->li_discq, cb, ccb_chain);
 3817                 li->li_disc --;
 3818                 ti->ti_disc --;
 3819                 slp->sl_disc --;
 3820         }
 3821 
 3822         cb->ccb_flags &= ~(CCB_STARTQ | CCB_DISCQ | 
 3823                            CCB_SENSE | CCB_CLEARQ | CCB_INTERNAL);
 3824 
 3825         if (fdone != 0 &&
 3826             (cb->ccb_rcnt ++ >= slp->sl_max_retry || 
 3827              (cb->ccb_flags & CCB_NORETRY) != 0))
 3828         {
 3829                 cb->ccb_error |= FATALIO;
 3830                 cb->ccb_flags &= ~CCB_AUTOSENSE;
 3831                 if (scsi_low_done(slp, cb) != SCSI_LOW_DONE_COMPLETE)
 3832                         panic("%s: done ccb retried",
 3833                             device_get_nameunit(slp->sl_dev));
 3834                 return NULL;
 3835         }
 3836         else
 3837         {
 3838                 cb->ccb_error |= PENDINGIO;
 3839                 scsi_low_deactivate_qtag(cb);
 3840                 scsi_low_ccb_message_retry(cb);
 3841                 cb->ccb_tc = cb->ccb_tcmax = SCSI_LOW_MIN_TOUT;
 3842                 return cb;
 3843         }
 3844 }
 3845 
 3846 static void
 3847 scsi_low_reset_nexus_lun(slp, li, fdone)
 3848         struct scsi_low_softc *slp;
 3849         struct lun_info *li;
 3850         int fdone;
 3851 {
 3852         struct slccb *cb, *ncb, *ecb;
 3853 
 3854         if (li == NULL)
 3855                 return;
 3856 
 3857         ecb = NULL;
 3858         for (cb = TAILQ_FIRST(&li->li_discq); cb != NULL; cb = ncb)
 3859         {
 3860                 ncb = TAILQ_NEXT(cb, ccb_chain);
 3861                 cb = scsi_low_revoke_ccb(slp, cb, fdone);
 3862                 if (cb != NULL)
 3863                 {
 3864                         /*
 3865                          * presumely keep ordering of io
 3866                          */
 3867                         cb->ccb_flags |= CCB_STARTQ;
 3868                         if (ecb == NULL)
 3869                         {
 3870                                 TAILQ_INSERT_HEAD(&slp->sl_start,\
 3871                                                   cb, ccb_chain);
 3872                         }
 3873                         else
 3874                         {
 3875                                 TAILQ_INSERT_AFTER(&slp->sl_start,\
 3876                                                    ecb, cb, ccb_chain);
 3877                         }
 3878                         ecb = cb;
 3879                 }
 3880         }
 3881 }
 3882         
 3883 /**************************************************************
 3884  * Qurik setup
 3885  **************************************************************/
 3886 static void
 3887 scsi_low_calcf_lun(li)
 3888         struct lun_info *li;
 3889 {
 3890         struct targ_info *ti = li->li_ti;
 3891         struct scsi_low_softc *slp = ti->ti_sc;
 3892         u_int cfgflags, diskflags;
 3893 
 3894         if (li->li_flags_valid == SCSI_LOW_LUN_FLAGS_ALL_VALID)
 3895                 cfgflags = li->li_cfgflags;
 3896         else
 3897                 cfgflags = 0;
 3898 
 3899         diskflags = li->li_diskflags & li->li_quirks;
 3900 
 3901         /* disconnect */
 3902         li->li_flags &= ~SCSI_LOW_DISC;
 3903         if ((slp->sl_cfgflags & CFG_NODISC) == 0 &&
 3904             (diskflags & SCSI_LOW_DISK_DISC) != 0 &&
 3905             (cfgflags & SCSI_LOW_DISC) != 0)
 3906                 li->li_flags |= SCSI_LOW_DISC;
 3907 
 3908         /* parity */
 3909         li->li_flags |= SCSI_LOW_NOPARITY;
 3910         if ((slp->sl_cfgflags & CFG_NOPARITY) == 0 &&
 3911             (diskflags & SCSI_LOW_DISK_PARITY) != 0 &&
 3912             (cfgflags & SCSI_LOW_NOPARITY) == 0)
 3913                 li->li_flags &= ~SCSI_LOW_NOPARITY;
 3914 
 3915         /* qtag */
 3916         if ((slp->sl_cfgflags & CFG_NOQTAG) == 0 &&
 3917             (cfgflags & SCSI_LOW_QTAG) != 0 &&
 3918             (diskflags & SCSI_LOW_DISK_QTAG) != 0)
 3919         {
 3920                 li->li_flags |= SCSI_LOW_QTAG;
 3921                 li->li_maxnexus = SCSI_LOW_MAXNEXUS;
 3922                 li->li_maxnqio = li->li_maxnexus;
 3923         }
 3924         else
 3925         {
 3926                 li->li_flags &= ~SCSI_LOW_QTAG;
 3927                 li->li_maxnexus = 0;
 3928                 li->li_maxnqio = li->li_maxnexus;
 3929         }
 3930 
 3931         /* cmd link */
 3932         li->li_flags &= ~SCSI_LOW_LINK;
 3933         if ((cfgflags & SCSI_LOW_LINK) != 0 &&
 3934             (diskflags & SCSI_LOW_DISK_LINK) != 0)
 3935                 li->li_flags |= SCSI_LOW_LINK;
 3936 
 3937         /* compatible flags */
 3938         li->li_flags &= ~SCSI_LOW_SYNC;
 3939         if (ti->ti_maxsynch.offset > 0)
 3940                 li->li_flags |= SCSI_LOW_SYNC;
 3941 
 3942 #ifdef  SCSI_LOW_DEBUG
 3943         if (SCSI_LOW_DEBUG_GO(SCSI_LOW_DEBUG_CALCF, ti->ti_id) != 0)
 3944         {
 3945                 scsi_low_calcf_show(li);
 3946         }
 3947 #endif  /* SCSI_LOW_DEBUG */
 3948 }
 3949 
 3950 static void
 3951 scsi_low_calcf_target(ti)
 3952         struct targ_info *ti;
 3953 {
 3954         struct scsi_low_softc *slp = ti->ti_sc;
 3955         u_int offset, period, diskflags;
 3956 
 3957         diskflags = ti->ti_diskflags & ti->ti_quirks;
 3958 
 3959         /* synch */
 3960         if ((slp->sl_cfgflags & CFG_ASYNC) == 0 &&
 3961             (diskflags & SCSI_LOW_DISK_SYNC) != 0)
 3962         {
 3963                 offset = ti->ti_maxsynch.offset;
 3964                 period = ti->ti_maxsynch.period;
 3965                 if (offset == 0 || period == 0)
 3966                         offset = period = 0;
 3967         }
 3968         else
 3969         {
 3970                 offset = period = 0;
 3971         }
 3972         
 3973         ti->ti_maxsynch.offset = offset;
 3974         ti->ti_maxsynch.period = period;
 3975 
 3976         /* wide */
 3977         if ((diskflags & SCSI_LOW_DISK_WIDE_32) == 0 &&
 3978              ti->ti_width > SCSI_LOW_BUS_WIDTH_16)
 3979                 ti->ti_width = SCSI_LOW_BUS_WIDTH_16;
 3980 
 3981         if ((diskflags & SCSI_LOW_DISK_WIDE_16) == 0 &&
 3982             ti->ti_width > SCSI_LOW_BUS_WIDTH_8)
 3983                 ti->ti_width = SCSI_LOW_BUS_WIDTH_8;
 3984 
 3985         if (ti->ti_flags_valid == SCSI_LOW_TARG_FLAGS_ALL_VALID)
 3986         {
 3987                 if (ti->ti_maxsynch.offset != ti->ti_osynch.offset ||
 3988                     ti->ti_maxsynch.period != ti->ti_osynch.period)
 3989                         ti->ti_setup_msg |= SCSI_LOW_MSG_SYNCH;
 3990                 if (ti->ti_width != ti->ti_owidth)
 3991                         ti->ti_setup_msg |= (SCSI_LOW_MSG_WIDE | SCSI_LOW_MSG_SYNCH);
 3992 
 3993                 ti->ti_osynch = ti->ti_maxsynch;
 3994                 ti->ti_owidth = ti->ti_width;
 3995         }
 3996 
 3997 #ifdef  SCSI_LOW_DEBUG
 3998         if (SCSI_LOW_DEBUG_GO(SCSI_LOW_DEBUG_CALCF, ti->ti_id) != 0)
 3999         {
 4000                 device_printf(slp->sl_dev,
 4001                         "(%d:*): max period(%dns) offset(%d) width(%d)\n",
 4002                         ti->ti_id,
 4003                         ti->ti_maxsynch.period * 4,
 4004                         ti->ti_maxsynch.offset,
 4005                         ti->ti_width);
 4006         }
 4007 #endif  /* SCSI_LOW_DEBUG */
 4008 }
 4009 
 4010 static void
 4011 scsi_low_calcf_show(li)
 4012         struct lun_info *li;
 4013 {
 4014         struct targ_info *ti = li->li_ti;
 4015         struct scsi_low_softc *slp = ti->ti_sc;
 4016 
 4017         device_printf(slp->sl_dev,
 4018                 "(%d:%d): period(%d ns) offset(%d) width(%d) flags 0x%b\n",
 4019                 ti->ti_id, li->li_lun,
 4020                 ti->ti_maxsynch.period * 4,
 4021                 ti->ti_maxsynch.offset,
 4022                 ti->ti_width,
 4023                 li->li_flags, SCSI_LOW_BITS);
 4024 }
 4025 
 4026 #ifdef  SCSI_LOW_START_UP_CHECK
 4027 /**************************************************************
 4028  * scsi world start up
 4029  **************************************************************/
 4030 static int scsi_low_poll(struct scsi_low_softc *, struct slccb *);
 4031 
 4032 static int
 4033 scsi_low_start_up(slp)
 4034         struct scsi_low_softc *slp;
 4035 {
 4036         struct targ_info *ti;
 4037         struct lun_info *li;
 4038         struct slccb *cb;
 4039         int target, lun;
 4040 
 4041         device_printf(slp->sl_dev, "scsi_low: probing all devices ....\n");
 4042 
 4043         for (target = 0; target < slp->sl_ntargs; target ++)
 4044         {
 4045                 if (target == slp->sl_hostid)
 4046                 {
 4047                         if ((slp->sl_show_result & SHOW_PROBE_RES) != 0)
 4048                         {
 4049                                 device_printf(slp->sl_dev,
 4050                                     "scsi_low: target %d (host card)\n",
 4051                                     target);
 4052                         }
 4053                         continue;
 4054                 }
 4055 
 4056                 if ((slp->sl_show_result & SHOW_PROBE_RES) != 0)
 4057                 {
 4058                         device_printf(slp->sl_dev, "scsi_low: target %d lun ",
 4059                             target);
 4060                 }
 4061 
 4062                 ti = slp->sl_ti[target];
 4063                 for (lun = 0; lun < slp->sl_nluns; lun ++)
 4064                 {
 4065                         if ((cb = SCSI_LOW_ALLOC_CCB(1)) == NULL)
 4066                                 break;
 4067 
 4068                         cb->osdep = NULL;
 4069                         cb->bp = NULL;
 4070 
 4071                         li = scsi_low_alloc_li(ti, lun, 1);
 4072 
 4073                         scsi_low_enqueue(slp, ti, li, cb,
 4074                                          CCB_AUTOSENSE | CCB_POLLED, 0);
 4075 
 4076                         scsi_low_poll(slp, cb);
 4077 
 4078                         if (li->li_state != SCSI_LOW_LUN_OK)
 4079                                 break;
 4080 
 4081                         if ((slp->sl_show_result & SHOW_PROBE_RES) != 0)
 4082                         {
 4083                                 printf("%d ", lun);             
 4084                         }
 4085                 }
 4086 
 4087                 if ((slp->sl_show_result & SHOW_PROBE_RES) != 0)
 4088                 {
 4089                         printf("\n");
 4090                 }
 4091         }
 4092         return 0;
 4093 }
 4094 
 4095 static int
 4096 scsi_low_poll(slp, cb)
 4097         struct scsi_low_softc *slp;
 4098         struct slccb *cb;
 4099 {
 4100         int tcount;
 4101 
 4102         tcount = 0;
 4103         while (slp->sl_nio > 0)
 4104         {
 4105                 DELAY((1000 * 1000) / SCSI_LOW_POLL_HZ);
 4106 
 4107                 (*slp->sl_funcs->scsi_low_poll) (slp);
 4108                 if (tcount ++ < SCSI_LOW_POLL_HZ / SCSI_LOW_TIMEOUT_HZ)
 4109                         continue;
 4110 
 4111                 tcount = 0;
 4112                 scsi_low_timeout_check(slp);
 4113         }
 4114 
 4115         return 0;
 4116 }
 4117 #endif  /* SCSI_LOW_START_UP_CHECK */
 4118 
 4119 /**********************************************************
 4120  * DEBUG SECTION
 4121  **********************************************************/
 4122 #ifdef  SCSI_LOW_DEBUG
 4123 static void
 4124 scsi_low_test_abort(slp, ti, li)
 4125         struct scsi_low_softc *slp;
 4126         struct targ_info *ti;
 4127         struct lun_info *li;
 4128 {
 4129         struct slccb *acb;
 4130 
 4131         if (li->li_disc > 1)
 4132         {
 4133                 acb = TAILQ_FIRST(&li->li_discq); 
 4134                 if (scsi_low_abort_ccb(slp, acb) == 0)
 4135                 {
 4136                         device_printf(slp->sl_dev,
 4137                             "aborting ccb(0x%lx) start\n", (u_long) acb);
 4138                 }
 4139         }
 4140 }
 4141 
 4142 static void
 4143 scsi_low_test_atten(slp, ti, msg)
 4144         struct scsi_low_softc *slp;
 4145         struct targ_info *ti;
 4146         u_int msg;
 4147 {
 4148 
 4149         if (slp->sl_ph_count < SCSI_LOW_MAX_ATTEN_CHECK)
 4150                 scsi_low_assert_msg(slp, ti, msg, 0);
 4151         else
 4152                 device_printf(slp->sl_dev, "atten check OK\n");
 4153 }
 4154 
 4155 static void
 4156 scsi_low_test_cmdlnk(slp, cb)
 4157         struct scsi_low_softc *slp;
 4158         struct slccb *cb;
 4159 {
 4160 #define SCSI_LOW_CMDLNK_NOK     (CCB_INTERNAL | CCB_SENSE | CCB_CLEARQ)
 4161 
 4162         if ((cb->ccb_flags & SCSI_LOW_CMDLNK_NOK) != 0)
 4163                 return;
 4164 
 4165         memcpy(cb->ccb_scsi_cmd, slp->sl_scp.scp_cmd,
 4166                slp->sl_scp.scp_cmdlen);
 4167         cb->ccb_scsi_cmd[slp->sl_scp.scp_cmdlen - 1] |= 1;
 4168         slp->sl_scp.scp_cmd = cb->ccb_scsi_cmd;
 4169 }
 4170 #endif  /* SCSI_LOW_DEBUG */
 4171 
 4172 /* static */ void
 4173 scsi_low_info(slp, ti, s)
 4174         struct scsi_low_softc *slp;
 4175         struct targ_info *ti;
 4176         u_char *s;
 4177 {
 4178 
 4179         if (slp == NULL)
 4180                 slp = LIST_FIRST(&sl_tab);
 4181         if (s == NULL)
 4182                 s = "no message";
 4183 
 4184         printf(">>>>> SCSI_LOW_INFO(0x%lx): %s\n", (u_long) slp->sl_Tnexus, s);
 4185         if (ti == NULL)
 4186         {
 4187                 for (ti = TAILQ_FIRST(&slp->sl_titab); ti != NULL;
 4188                      ti = TAILQ_NEXT(ti, ti_chain))
 4189                 {
 4190                         scsi_low_print(slp, ti);
 4191                 }
 4192         }
 4193         else
 4194         {
 4195                 scsi_low_print(slp, ti);
 4196         }
 4197 }
 4198 
 4199 static u_char *phase[] =
 4200 {
 4201         "FREE", "ARBSTART", "SELSTART", "SELECTED",
 4202         "CMDOUT", "DATA", "MSGIN", "MSGOUT", "STATIN", "DISC", "RESEL"
 4203 };
 4204 
 4205 void
 4206 scsi_low_print(slp, ti)
 4207         struct scsi_low_softc *slp;
 4208         struct targ_info *ti;
 4209 {
 4210         struct lun_info *li;
 4211         struct slccb *cb;
 4212         struct sc_p *sp;
 4213 
 4214         if (ti == NULL || ti == slp->sl_Tnexus)
 4215         {
 4216                 ti = slp->sl_Tnexus;
 4217                 li = slp->sl_Lnexus;
 4218                 cb = slp->sl_Qnexus;
 4219         }
 4220         else
 4221         {
 4222                 li = LIST_FIRST(&ti->ti_litab);
 4223                 cb = TAILQ_FIRST(&li->li_discq);
 4224         }
 4225         sp = &slp->sl_scp;
 4226 
 4227         device_printf(slp->sl_dev,
 4228             "=== NEXUS T(0x%lx) L(0x%lx) Q(0x%lx) NIO(%d) ===\n",
 4229             (u_long) ti, (u_long) li, (u_long) cb, slp->sl_nio);
 4230 
 4231         /* target stat */
 4232         if (ti != NULL)
 4233         {
 4234                 u_int flags = 0, maxnqio = 0, nqio = 0;
 4235                 int lun = -1;
 4236 
 4237                 if (li != NULL)
 4238                 {
 4239                         lun = li->li_lun;
 4240                         flags = li->li_flags;
 4241                         maxnqio = li->li_maxnqio;
 4242                         nqio = li->li_nqio;
 4243                 }
 4244 
 4245                 device_printf(slp->sl_dev,
 4246                        "(%d:%d) ph<%s> => ph<%s> DISC(%d) QIO(%d:%d)\n",
 4247                        ti->ti_id, lun, phase[(int) ti->ti_ophase], 
 4248                        phase[(int) ti->ti_phase], ti->ti_disc,
 4249                        nqio, maxnqio);
 4250 
 4251                 if (cb != NULL)
 4252                 {
 4253 printf("CCB: cmd[0] 0x%x clen 0x%x dlen 0x%x<0x%x stat 0x%x err %b\n",
 4254                        (u_int) cb->ccb_scp.scp_cmd[0],
 4255                        cb->ccb_scp.scp_cmdlen, 
 4256                        cb->ccb_datalen,
 4257                        cb->ccb_scp.scp_datalen,
 4258                        (u_int) cb->ccb_sscp.scp_status,
 4259                        cb->ccb_error, SCSI_LOW_ERRORBITS);
 4260                 }
 4261 
 4262 printf("MSGIN: ptr(%x) [%x][%x][%x][%x][%x] attention: %d\n",
 4263                (u_int) (ti->ti_msginptr), 
 4264                (u_int) (ti->ti_msgin[0]),
 4265                (u_int) (ti->ti_msgin[1]),
 4266                (u_int) (ti->ti_msgin[2]),
 4267                (u_int) (ti->ti_msgin[3]),
 4268                (u_int) (ti->ti_msgin[4]),
 4269                slp->sl_atten);
 4270 
 4271 printf("MSGOUT: msgflags 0x%x [%x][%x][%x][%x][%x] msgoutlen %d C_FLAGS: %b\n",
 4272                 (u_int) ti->ti_msgflags,
 4273                 (u_int) (ti->ti_msgoutstr[0]), 
 4274                 (u_int) (ti->ti_msgoutstr[1]), 
 4275                 (u_int) (ti->ti_msgoutstr[2]), 
 4276                 (u_int) (ti->ti_msgoutstr[3]), 
 4277                 (u_int) (ti->ti_msgoutstr[4]), 
 4278                 ti->ti_msgoutlen,
 4279                 flags, SCSI_LOW_BITS);
 4280 
 4281 #ifdef  SCSI_LOW_DIAGNOSTIC
 4282                 scsi_low_msg_log_show(&ti->ti_log_msgin, "MIN LOG ", 2);
 4283                 scsi_low_msg_log_show(&ti->ti_log_msgout, "MOUT LOG", 2);
 4284 #endif  /* SCSI_LOW_DIAGNOSTIC */
 4285 
 4286         }
 4287 
 4288         printf("SCB: daddr 0x%lx dlen 0x%x stat 0x%x err %b\n",
 4289                (u_long) sp->scp_data,
 4290                sp->scp_datalen,
 4291                (u_int) sp->scp_status,
 4292                slp->sl_error, SCSI_LOW_ERRORBITS);
 4293 }

Cache object: 731eb45bcd85b8c113b336926182fad6


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.