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.h

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 /*      $FreeBSD: releng/5.2/sys/cam/scsi/scsi_low.h 103870 2002-09-23 18:54:32Z alfred $       */
    2 /*      $NecBSD: scsi_low.h,v 1.24.10.5 2001/06/26 07:31:46 honda Exp $ */
    3 /*      $NetBSD$        */
    4 
    5 #define SCSI_LOW_DIAGNOSTIC
    6 #define SCSI_LOW_ALT_QTAG_ALLOCATE
    7 
    8 /*
    9  * [NetBSD for NEC PC-98 series]
   10  *  Copyright (c) 1995, 1996, 1997, 1998, 1999, 2000, 2001
   11  *      NetBSD/pc98 porting staff. All rights reserved.
   12  *  Copyright (c) 1995, 1996, 1997, 1998, 1999, 2000, 2001
   13  *      Naofumi HONDA. All rights reserved.
   14  *
   15  * [Ported for FreeBSD CAM]
   16  *  Copyright (c) 2000, 2001
   17  *      MITSUNAGA Noriaki, NOKUBI Hirotaka and TAKAHASHI Yoshihiro.
   18  *      All rights reserved.
   19  * 
   20  *  Redistribution and use in source and binary forms, with or without
   21  *  modification, are permitted provided that the following conditions
   22  *  are met:
   23  *  1. Redistributions of source code must retain the above copyright
   24  *     notice, this list of conditions and the following disclaimer.
   25  *  2. Redistributions in binary form must reproduce the above copyright
   26  *     notice, this list of conditions and the following disclaimer in the
   27  *     documentation and/or other materials provided with the distribution.
   28  *  3. The name of the author may not be used to endorse or promote products
   29  *     derived from this software without specific prior written permission.
   30  * 
   31  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
   32  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
   33  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
   34  * DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
   35  * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
   36  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
   37  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
   38  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
   39  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
   40  * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
   41  * POSSIBILITY OF SUCH DAMAGE.
   42  */
   43 
   44 #ifndef _SCSI_LOW_H_
   45 #define _SCSI_LOW_H_
   46 
   47 /*================================================
   48  * Scsi low OSDEP 
   49  * (All os depend structures should be here!)
   50  ================================================*/
   51 /******** interface ******************************/
   52 #ifdef  __NetBSD__
   53 #define SCSI_LOW_INTERFACE_XS
   54 #endif  /* __NetBSD__ */
   55 
   56 #ifdef  __FreeBSD__
   57 #define SCSI_LOW_INTERFACE_CAM
   58 #define CAM
   59 #endif  /* __FreeBSD__ */
   60 
   61 /******** includes *******************************/
   62 #ifdef  __NetBSD__
   63 #include <i386/Cbus/dev/scsi_dvcfg.h>
   64 #include <dev/isa/ccbque.h>
   65 #endif  /* __NetBSD__ */
   66 
   67 #ifdef  __FreeBSD__
   68 #include <sys/device_port.h>
   69 #include <cam/cam.h>
   70 #include <cam/cam_ccb.h>
   71 #include <cam/cam_sim.h>
   72 #include <cam/cam_xpt_sim.h>
   73 #include <cam/cam_debug.h>
   74 
   75 #include <cam/scsi/scsi_dvcfg.h>
   76 #include <i386/isa/ccbque.h>
   77 #endif  /* __FreeBSD__ */
   78 
   79 /******** functions macro ************************/
   80 #ifdef  __NetBSD__
   81 #define SCSI_LOW_DEBUGGER(dev)  Debugger()
   82 #define SCSI_LOW_DELAY(mu)      delay((mu))
   83 #define SCSI_LOW_SPLSCSI        splbio
   84 #define SCSI_LOW_BZERO(pt, size)        memset((pt), 0, (size))
   85 #endif  /* __NetBSD__ */
   86 
   87 #ifdef  __FreeBSD__
   88 #undef  MSG_IDENTIFY
   89 #define SCSI_LOW_DEBUGGER(dev)  Debugger((dev))
   90 #define SCSI_LOW_DELAY(mu)      DELAY((mu))
   91 #define SCSI_LOW_SPLSCSI        splcam
   92 #define SCSI_LOW_BZERO(pt, size)        bzero((pt), (size))
   93 #endif  /* __FreeBSD__ */
   94 
   95 /******** os depend interface structures **********/
   96 #ifdef  __NetBSD__
   97 typedef struct scsipi_sense_data scsi_low_osdep_sense_data_t;
   98 
   99 struct scsi_low_osdep_interface {
  100         struct device si_dev;
  101 
  102         struct scsipi_link *si_splp;
  103 };
  104 
  105 struct scsi_low_osdep_targ_interface {
  106 };
  107 
  108 struct scsi_low_osdep_lun_interface {
  109         u_int sloi_quirks;
  110 };
  111 #endif  /* __NetBSD__ */
  112 
  113 #ifdef  __FreeBSD__
  114 typedef struct scsi_sense_data scsi_low_osdep_sense_data_t;
  115 
  116 struct scsi_low_osdep_interface {
  117         DEVPORT_DEVICE si_dev;
  118 
  119         struct cam_sim *sim;
  120         struct cam_path *path;
  121 
  122         int si_poll_count;
  123 
  124         struct callout_handle engage_ch;
  125         struct callout_handle timeout_ch;
  126 #ifdef  SCSI_LOW_POWFUNC
  127         struct callout_handle recover_ch;
  128 #endif
  129 };
  130 
  131 struct scsi_low_osdep_targ_interface {
  132 };
  133 
  134 struct scsi_low_osdep_lun_interface {
  135 };
  136 #endif  /* __FreeBSD__ */
  137 
  138 /******** os depend interface functions *************/
  139 struct slccb;
  140 struct scsi_low_softc;
  141 #define SCSI_LOW_TIMEOUT_STOP           0
  142 #define SCSI_LOW_TIMEOUT_START          1
  143 #define SCSI_LOW_TIMEOUT_CH_IO          0
  144 #define SCSI_LOW_TIMEOUT_CH_ENGAGE      1
  145 #define SCSI_LOW_TIMEOUT_CH_RECOVER     2
  146 
  147 struct scsi_low_osdep_funcs {
  148         int (*scsi_low_osdep_attach) \
  149                         (struct scsi_low_softc *);
  150         int (*scsi_low_osdep_world_start) \
  151                         (struct scsi_low_softc *);
  152         int (*scsi_low_osdep_dettach) \
  153                         (struct scsi_low_softc *);
  154         int (*scsi_low_osdep_ccb_setup) \
  155                         (struct scsi_low_softc *, struct slccb *);
  156         int (*scsi_low_osdep_done) \
  157                         (struct scsi_low_softc *, struct slccb *);
  158         void (*scsi_low_osdep_timeout) \
  159                         (struct scsi_low_softc *, int, int);
  160 };
  161 
  162 /*================================================
  163  * Generic Scsi Low header file 
  164  * (All os depend structures should be above!)
  165  ================================================*/
  166 /*************************************************
  167  * Scsi low definitions
  168  *************************************************/
  169 #define SCSI_LOW_SYNC           DVF_SCSI_SYNC
  170 #define SCSI_LOW_DISC           DVF_SCSI_DISC
  171 #define SCSI_LOW_WAIT           DVF_SCSI_WAIT
  172 #define SCSI_LOW_LINK           DVF_SCSI_LINK
  173 #define SCSI_LOW_QTAG           DVF_SCSI_QTAG
  174 #define SCSI_LOW_NOPARITY       DVF_SCSI_NOPARITY
  175 #define SCSI_LOW_SAVESP         DVF_SCSI_SAVESP
  176 #define SCSI_LOW_DEFCFG         DVF_SCSI_DEFCFG
  177 #define SCSI_LOW_BITS           DVF_SCSI_BITS
  178 
  179 #define SCSI_LOW_PERIOD(n)      DVF_SCSI_PERIOD(n)
  180 #define SCSI_LOW_OFFSET(n)      DVF_SCSI_OFFSET(n)
  181 
  182 /* host scsi id and targets macro */
  183 #ifndef SCSI_LOW_NTARGETS
  184 #define SCSI_LOW_NTARGETS                       8
  185 #endif  /* SCSI_LOW_NTARGETS */
  186 #define SCSI_LOW_NCCB                           128
  187 
  188 #define SCSI_LOW_MAX_RETRY                      3
  189 #define SCSI_LOW_MAX_SELECTION_RETRY            10
  190 
  191 /* timeout control macro */
  192 #define SCSI_LOW_TIMEOUT_HZ                     10
  193 #define SCSI_LOW_MIN_TOUT                       12
  194 #define SCSI_LOW_TIMEOUT_CHECK_INTERVAL         1
  195 #define SCSI_LOW_POWDOWN_TC                     15
  196 #define SCSI_LOW_MAX_PHCHANGES                  256
  197 #define SCSI2_RESET_DELAY                       5000000
  198 
  199 /* msg */
  200 #define SCSI_LOW_MAX_MSGLEN                     32
  201 #define SCSI_LOW_MSG_LOG_DATALEN                8
  202 
  203 /*************************************************
  204  * Scsi Data Pointer
  205  *************************************************/
  206 /* scsi pointer */
  207 struct sc_p {
  208         u_int8_t *scp_data;
  209         int scp_datalen;
  210 
  211         u_int8_t *scp_cmd;
  212         int scp_cmdlen;
  213 
  214         u_int8_t scp_direction;
  215 #define SCSI_LOW_RWUNK  (-1)
  216 #define SCSI_LOW_WRITE  0
  217 #define SCSI_LOW_READ   1
  218         u_int8_t scp_status;
  219         u_int8_t scp_spare[2];
  220 };
  221 
  222 /*************************************************
  223  * Command Control Block Structure
  224  *************************************************/
  225 typedef int scsi_low_tag_t;                     
  226 struct targ_info;
  227 
  228 #define SCSI_LOW_UNKLUN ((u_int) -1)
  229 #define SCSI_LOW_UNKTAG ((scsi_low_tag_t) -1)
  230 
  231 struct slccb {
  232         TAILQ_ENTRY(slccb) ccb_chain;
  233 
  234         void *osdep;                    /* os depend structure */
  235 
  236         struct targ_info *ti;           /* targ_info */
  237         struct lun_info *li;            /* lun info */
  238         struct buf *bp;                 /* io bufs */
  239 
  240         scsi_low_tag_t ccb_tag;         /* effective qtag */
  241         scsi_low_tag_t ccb_otag;        /* allocated qtag */
  242 
  243         /*****************************************
  244          * Scsi data pointers (original and saved)
  245          *****************************************/
  246         struct sc_p ccb_scp;            /* given */
  247         struct sc_p ccb_sscp;           /* saved scsi data pointer */
  248         int ccb_datalen;                /* transfered data counter */
  249 
  250         /*****************************************
  251          * Msgout 
  252          *****************************************/
  253         u_int ccb_msgoutflag;
  254         u_int ccb_omsgoutflag;
  255 
  256         /*****************************************
  257          * Error or Timeout counters
  258          *****************************************/
  259         u_int ccb_flags;
  260 #define CCB_INTERNAL    0x0001
  261 #define CCB_SENSE       0x0002
  262 #define CCB_CLEARQ      0x0004
  263 #define CCB_DISCQ       0x0008
  264 #define CCB_STARTQ      0x0010
  265 #define CCB_POLLED      0x0100  /* polling ccb */
  266 #define CCB_NORETRY     0x0200  /* do NOT retry */
  267 #define CCB_AUTOSENSE   0x0400  /* do a sence after CA */
  268 #define CCB_URGENT      0x0800  /* an urgent ccb */
  269 #define CCB_NOSDONE     0x1000  /* do not call an os done routine */
  270 #define CCB_SCSIIO      0x2000  /* a normal scsi io coming from upper layer */
  271 #define CCB_SILENT      0x4000  /* no terminate messages */
  272 
  273         u_int ccb_error;
  274 
  275         int ccb_rcnt;                   /* retry counter */
  276         int ccb_selrcnt;                /* selection retry counter */
  277         int ccb_tc;                     /* timer counter */
  278         int ccb_tcmax;                  /* max timeout */
  279 
  280         /*****************************************
  281          * Sense data buffer
  282          *****************************************/
  283         u_int8_t ccb_scsi_cmd[12];
  284         scsi_low_osdep_sense_data_t ccb_sense;
  285 };
  286 
  287 /*************************************************
  288  * Slccb functions
  289  *************************************************/
  290 GENERIC_CCB_ASSERT(scsi_low, slccb)
  291 
  292 /*************************************************
  293  * Target and Lun structures
  294  *************************************************/
  295 struct scsi_low_softc;
  296 LIST_HEAD(scsi_low_softc_tab, scsi_low_softc);
  297 TAILQ_HEAD(targ_info_tab, targ_info);
  298 LIST_HEAD(lun_info_tab, lun_info);
  299 
  300 struct lun_info {
  301         struct scsi_low_osdep_lun_interface li_sloi;
  302 
  303         int li_lun;
  304         struct targ_info *li_ti;                /* my target */
  305 
  306         LIST_ENTRY(lun_info) lun_chain;         /* targ_info link */
  307 
  308         struct slccbtab li_discq;                       /* disconnect queue */
  309 
  310         /*
  311          * qtag control
  312          */
  313         int li_maxnexus;
  314         int li_maxnqio; 
  315         int li_nqio;
  316         int li_disc;
  317 
  318 #define SCSI_LOW_MAXNEXUS (sizeof(u_int) * NBBY)
  319         u_int li_qtagbits;
  320 
  321 #ifdef  SCSI_LOW_ALT_QTAG_ALLOCATE
  322         u_int8_t li_qtagarray[SCSI_LOW_MAXNEXUS];
  323         u_int li_qd;
  324 #endif  /* SCSI_LOW_ALT_QTAG_ALLOCATE */
  325 
  326 #define SCSI_LOW_QFLAG_CA_QCLEAR        0x01
  327         u_int li_qflags;
  328 
  329         /*
  330          * lun state
  331          */
  332 #define SCSI_LOW_LUN_SLEEP      0x00
  333 #define SCSI_LOW_LUN_START      0x01
  334 #define SCSI_LOW_LUN_INQ        0x02
  335 #define SCSI_LOW_LUN_MODEQ      0x03
  336 #define SCSI_LOW_LUN_OK         0x04
  337         u_int li_state;                         /* target lun state */
  338 
  339         /*
  340          * lun control flags
  341          */
  342         u_int li_flags_valid;   /* valid flags */
  343 #define SCSI_LOW_LUN_FLAGS_USER_VALID   0x0001
  344 #define SCSI_LOW_LUN_FLAGS_DISK_VALID   0x0002
  345 #define SCSI_LOW_LUN_FLAGS_QUIRKS_VALID 0x0004
  346 #define SCSI_LOW_LUN_FLAGS_ALL_VALID \
  347         (SCSI_LOW_LUN_FLAGS_USER_VALID | \
  348          SCSI_LOW_LUN_FLAGS_DISK_VALID | SCSI_LOW_LUN_FLAGS_QUIRKS_VALID)
  349 
  350         u_int li_flags;         /* real lun control flags */
  351         u_int li_cfgflags;      /* lun control flags given by user */
  352         u_int li_diskflags;     /* lun control flags given by hardware info */
  353         u_int li_quirks;        /* lun control flags given by upper layer */
  354 
  355         /* inq buffer */
  356         struct scsi_low_inq_data {
  357                 u_int8_t sd_type;       
  358                 u_int8_t sd_sp1;
  359                 u_int8_t sd_version;
  360                 u_int8_t sd_resp;
  361                 u_int8_t sd_len;
  362                 u_int8_t sd_sp2[2];
  363                 u_int8_t sd_support;
  364         } __packed li_inq;
  365 
  366         /* modeq buffer */
  367         struct scsi_low_mode_sense_data {
  368                 u_int8_t sms_header[4];
  369                 struct {
  370                         u_int8_t cmp_page;
  371                         u_int8_t cmp_length;
  372                         u_int8_t cmp_rlec;
  373                         u_int8_t cmp_qc;
  374                         u_int8_t cmp_eca;
  375                         u_int8_t cmp_spare[3];
  376                 } __packed sms_cmp;     
  377         
  378         } li_sms;       
  379 };
  380 
  381 struct scsi_low_msg_log {
  382         int slml_ptr;
  383         struct {
  384                 u_int8_t msg[2];
  385         } slml_msg[SCSI_LOW_MSG_LOG_DATALEN];
  386 };
  387 
  388 struct targ_info {
  389         struct scsi_low_osdep_targ_interface ti_slti;
  390 
  391         TAILQ_ENTRY(targ_info) ti_chain;        /* targ_info link */
  392 
  393         struct scsi_low_softc *ti_sc;           /* our softc */
  394         u_int ti_id;                            /* scsi id */
  395 
  396         /*
  397          * Lun chain
  398          */
  399         struct lun_info_tab ti_litab;           /* lun chain */
  400 
  401         /*
  402          * total disconnected nexus
  403          */
  404         int ti_disc;
  405 
  406         /*
  407          * Scsi phase control
  408          */
  409 
  410 #define PH_NULL         0x00
  411 #define PH_ARBSTART     0x01
  412 #define PH_SELSTART     0x02
  413 #define PH_SELECTED     0x03
  414 #define PH_CMD          0x04
  415 #define PH_DATA         0x05
  416 #define PH_MSGIN        0x06
  417 #define PH_MSGOUT       0x07
  418 #define PH_STAT         0x08
  419 #define PH_DISC         0x09
  420 #define PH_RESEL        0x0a
  421         u_int ti_phase;                         /* scsi phase */
  422         u_int ti_ophase;                        /* old scsi phase */
  423 
  424         /*
  425          * Msg in
  426          */
  427         u_int ti_msginptr;                      /* msgin ptr */
  428         u_int ti_msginlen;                      /* expected msg length */
  429         int ti_msgin_parity_error;              /* parity error detected */
  430         u_int8_t ti_msgin[SCSI_LOW_MAX_MSGLEN]; /* msgin buffer */
  431 
  432         /*
  433          * Msg out
  434          */
  435         u_int ti_msgflags;                      /* msgs to be asserted */
  436         u_int ti_omsgflags;                     /* msgs asserted */
  437         u_int ti_emsgflags;                     /* a msg currently asserted */
  438 #define SCSI_LOW_MSG_RESET      0x00000001
  439 #define SCSI_LOW_MSG_REJECT     0x00000002
  440 #define SCSI_LOW_MSG_PARITY     0x00000004
  441 #define SCSI_LOW_MSG_ERROR      0x00000008
  442 #define SCSI_LOW_MSG_IDENTIFY   0x00000010
  443 #define SCSI_LOW_MSG_ABORT      0x00000020
  444 #define SCSI_LOW_MSG_TERMIO     0x00000040
  445 #define SCSI_LOW_MSG_SIMPLE_QTAG        0x00000080
  446 #define SCSI_LOW_MSG_ORDERED_QTAG       0x00000100
  447 #define SCSI_LOW_MSG_HEAD_QTAG          0x00000200
  448 #define SCSI_LOW_MSG_ABORT_QTAG 0x00000400
  449 #define SCSI_LOW_MSG_CLEAR_QTAG 0x00000800
  450 #define SCSI_LOW_MSG_WIDE       0x00001000
  451 #define SCSI_LOW_MSG_SYNCH      0x00002000
  452 #define SCSI_LOW_MSG_NOOP       0x00004000
  453 #define SCSI_LOW_MSG_LAST       0x00008000
  454 #define SCSI_LOW_MSG_ALL        0xffffffff
  455 
  456         /* msgout buffer */
  457         u_int8_t ti_msgoutstr[SCSI_LOW_MAX_MSGLEN];     /* scsi msgout */
  458         u_int ti_msgoutlen;                     /* msgout strlen */
  459 
  460         /*
  461          * target initialize msgout 
  462          */
  463         u_int ti_setup_msg;             /* setup msgout requests */
  464         u_int ti_setup_msg_done;
  465 
  466         /*
  467          * synch and wide data info
  468          */
  469         u_int ti_flags_valid;   /* valid flags */
  470 #define SCSI_LOW_TARG_FLAGS_USER_VALID          0x0001
  471 #define SCSI_LOW_TARG_FLAGS_DISK_VALID          0x0002
  472 #define SCSI_LOW_TARG_FLAGS_QUIRKS_VALID        0x0004
  473 #define SCSI_LOW_TARG_FLAGS_ALL_VALID \
  474         (SCSI_LOW_TARG_FLAGS_USER_VALID | \
  475          SCSI_LOW_TARG_FLAGS_DISK_VALID | SCSI_LOW_TARG_FLAGS_QUIRKS_VALID)
  476 
  477         u_int ti_diskflags;     /* given target disk flags */
  478         u_int ti_quirks;        /* given target quirk */
  479 
  480         struct synch {
  481                 u_int8_t offset;
  482                 u_int8_t period;
  483         } ti_osynch, ti_maxsynch;               /* synch data */
  484 
  485 #define SCSI_LOW_BUS_WIDTH_8    0
  486 #define SCSI_LOW_BUS_WIDTH_16   1
  487 #define SCSI_LOW_BUS_WIDTH_32   2
  488         u_int ti_owidth, ti_width;
  489 
  490         /*
  491          * lun info size.
  492          */
  493         int ti_lunsize; 
  494 
  495 #ifdef  SCSI_LOW_DIAGNOSTIC
  496         struct scsi_low_msg_log ti_log_msgout;
  497         struct scsi_low_msg_log ti_log_msgin;
  498 #endif  /* SCSI_LOW_DIAGNOSTIC */
  499 };
  500 
  501 /*************************************************
  502  * COMMON HEADER STRUCTURE
  503  *************************************************/
  504 struct scsi_low_softc;
  505 struct proc;
  506 typedef struct scsi_low_softc *sc_low_t;
  507 
  508 #define SCSI_LOW_START_OK       0
  509 #define SCSI_LOW_START_FAIL     1
  510 #define SCSI_LOW_INFO_ALLOC     0
  511 #define SCSI_LOW_INFO_REVOKE    1
  512 #define SCSI_LOW_INFO_DEALLOC   2
  513 #define SCSI_LOW_POWDOWN        1
  514 #define SCSI_LOW_ENGAGE         2
  515 
  516 #define SC_LOW_INIT_T (int (*)(sc_low_t, int))
  517 #define SC_LOW_BUSRST_T (void (*)(sc_low_t))
  518 #define SC_LOW_TARG_INIT_T (int (*)(sc_low_t, struct targ_info *, int))
  519 #define SC_LOW_LUN_INIT_T (int (*)(sc_low_t, struct targ_info *, struct lun_info *, int))
  520 #define SC_LOW_SELECT_T (int (*)(sc_low_t, struct slccb *))
  521 #define SC_LOW_ATTEN_T (void (*)(sc_low_t))
  522 #define SC_LOW_NEXUS_T (int (*)(sc_low_t))
  523 #define SC_LOW_MSG_T (int (*)(sc_low_t, struct targ_info *, u_int))
  524 #define SC_LOW_POLL_T (int (*)(void *))
  525 #define SC_LOW_POWER_T (int (*)(sc_low_t, u_int))
  526 #define SC_LOW_TIMEOUT_T (int (*)(sc_low_t))
  527 
  528 struct scsi_low_funcs {
  529         int (*scsi_low_init)(sc_low_t, int);
  530         void (*scsi_low_bus_reset)(sc_low_t);
  531         int (*scsi_low_targ_init)(sc_low_t, struct targ_info *, int);
  532         int (*scsi_low_lun_init)(sc_low_t, struct targ_info *, struct lun_info *, int);
  533         int (*scsi_low_start_bus)(sc_low_t, struct slccb *);
  534         int (*scsi_low_establish_lun_nexus)(sc_low_t);
  535         int (*scsi_low_establish_ccb_nexus)(sc_low_t);
  536         void (*scsi_low_attention)(sc_low_t);
  537         int (*scsi_low_msg)(sc_low_t, struct targ_info *, u_int);
  538         int (*scsi_low_timeout)(sc_low_t);
  539         int (*scsi_low_poll)(void *);
  540         int (*scsi_low_power)(sc_low_t, u_int);
  541         int (*scsi_low_ioctl)(sc_low_t, u_long, caddr_t, int, struct proc *);
  542 };
  543 
  544 struct scsi_low_softc {
  545         /* os depend structure */
  546         struct scsi_low_osdep_interface sl_si;
  547 #define sl_dev  sl_si.si_dev
  548         struct scsi_low_osdep_funcs *sl_osdep_fp;
  549         u_char sl_xname[16];
  550                                 
  551         /* our chain */
  552         LIST_ENTRY(scsi_low_softc) sl_chain;
  553 
  554         /* my targets */
  555         struct targ_info *sl_ti[SCSI_LOW_NTARGETS];
  556         struct targ_info_tab sl_titab;
  557 
  558         /* current active T_L_Q nexus */
  559         struct targ_info *sl_Tnexus;            /* Target nexus */
  560         struct lun_info *sl_Lnexus;             /* Lun nexus */
  561         struct slccb *sl_Qnexus;                        /* Qtag nexus */
  562         int sl_nexus_call;
  563 
  564         /* ccb start queue */
  565         struct slccbtab sl_start;       
  566 
  567         /* retry limit and phase change counter */
  568         int sl_max_retry;
  569         int sl_ph_count;
  570         int sl_timeout_count;
  571 
  572         /* selection & total num disconnect targets */
  573         int sl_nio;
  574         int sl_disc;
  575         int sl_retry_sel;
  576         struct slccb *sl_selid;
  577 
  578         /* attention */
  579         int sl_atten;                   /* ATN asserted */
  580         int sl_clear_atten;             /* negate ATN required */
  581 
  582         /* scsi phase suggested by scsi msg */
  583         u_int sl_msgphase;      
  584 #define MSGPH_NULL      0x00            /* no msg */
  585 #define MSGPH_DISC      0x01            /* disconnect msg */
  586 #define MSGPH_CMDC      0x02            /* cmd complete msg */
  587 #define MSGPH_ABORT     0x03            /* abort seq */
  588 #define MSGPH_TERM      0x04            /* current io terminate */
  589 #define MSGPH_LCTERM    0x05            /* cmd link terminated */
  590 #define MSGPH_RESET     0x06            /* reset target */
  591 
  592         /* error */
  593         u_int sl_error;                 /* error flags */
  594 #define FATALIO         0x0001          /* generic io error & retry io */
  595 #define ABORTIO         0x0002          /* generic io error & terminate io */
  596 #define TIMEOUTIO       0x0004          /* watch dog timeout */
  597 #define SELTIMEOUTIO    0x0008          /* selection timeout */
  598 #define PDMAERR         0x0010          /* dma xfer error */
  599 #define MSGERR          0x0020          /* msgsys error */
  600 #define PARITYERR       0x0040          /* parity error */
  601 #define BUSYERR         0x0080          /* target busy error */
  602 #define STATERR         0x0100          /* status error */
  603 #define UACAERR         0x0200          /* target CA state, no sense check */
  604 #define SENSEIO         0x1000          /* cmd not excuted but sense data ok */
  605 #define SENSEERR        0x2000          /* cmd not excuted and sense data bad */
  606 #define UBFERR          0x4000          /* unexpected bus free */
  607 #define PENDINGIO       0x8000          /* ccb start not yet */
  608 #define SCSI_LOW_ERRORBITS "\020\017ubferr\016senseerr\015senseio\012uacaerr\011staterr\010busy\007parity\006msgerr\005pdmaerr\004seltimeout\003timeout\002abort\001fatal"
  609 
  610         /* current scsi data pointer */
  611         struct sc_p sl_scp;
  612 
  613         /* power control */
  614         u_int sl_active;                /* host is busy state */
  615         int sl_powc;                    /* power down timer counter */
  616         u_int sl_rstep;                 /* resume step */
  617 
  618         /* configuration flags */
  619         u_int sl_flags;         
  620 #define HW_POWDOWN      0x0001
  621 #define HW_RESUME       0x0002
  622 #define HW_PDMASTART    0x0004
  623 #define HW_INACTIVE     0x0008
  624 #define HW_POWERCTRL    0x0010
  625 #define HW_INITIALIZING 0x0020
  626 #define HW_READ_PADDING         0x1000
  627 #define HW_WRITE_PADDING        0x2000
  628 
  629         u_int sl_cfgflags;
  630 #define CFG_NODISC              0x0001
  631 #define CFG_NOPARITY            0x0002
  632 #define CFG_NOATTEN             0x0004
  633 #define CFG_ASYNC               0x0008
  634 #define CFG_NOQTAG              0x0010
  635 
  636         int sl_show_result;
  637 #define SHOW_SYNCH_NEG  0x0001
  638 #define SHOW_WIDE_NEG   0x0002
  639 #define SHOW_CALCF_RES  0x0010
  640 #define SHOW_PROBE_RES  0x0020
  641 #define SHOW_ALL_NEG    -1
  642 
  643         /* host informations */
  644         u_int sl_hostid;
  645         int sl_nluns;
  646         int sl_ntargs;
  647         int sl_openings;
  648 
  649         /* interface functions */
  650         struct scsi_low_funcs *sl_funcs;
  651 
  652         /* targinfo size */
  653         int sl_targsize;
  654 
  655 #if     defined(i386) || defined(__i386__)
  656         u_int sl_irq;           /* XXX */
  657 #endif  /* i386 */
  658 };
  659 
  660 /*************************************************
  661  * SCSI LOW service functions
  662  *************************************************/
  663 /* 
  664  * Scsi low attachment function.
  665  */
  666 int scsi_low_attach(struct scsi_low_softc *, int, int, int, int, int);
  667 int scsi_low_dettach(struct scsi_low_softc *);
  668 
  669 /* 
  670  * Scsi low interface activate or deactivate functions
  671  */
  672 int scsi_low_is_busy(struct scsi_low_softc *);
  673 int scsi_low_activate(struct scsi_low_softc *);
  674 int scsi_low_deactivate(struct scsi_low_softc *);
  675 
  676 /* 
  677  * Scsi phase "bus service" functions.
  678  * These functions are corresponding to each scsi bus phaeses.
  679  */
  680 /* bus idle phase (other initiators or targets release bus) */
  681 void scsi_low_bus_idle(struct scsi_low_softc *);
  682 
  683 /* arbitration and selection phase */
  684 void scsi_low_arbit_fail(struct scsi_low_softc *, struct slccb *);
  685 static __inline void scsi_low_arbit_win(struct scsi_low_softc *);
  686 
  687 /* msgout phase */
  688 #define SCSI_LOW_MSGOUT_INIT            0x00000001
  689 #define SCSI_LOW_MSGOUT_UNIFY           0x00000002
  690 int scsi_low_msgout(struct scsi_low_softc *, struct targ_info *, u_int);
  691 
  692 /* msgin phase */
  693 #define SCSI_LOW_DATA_PE        0x80000000
  694 int scsi_low_msgin(struct scsi_low_softc *, struct targ_info *, u_int);
  695 
  696 /* statusin phase */
  697 static __inline int scsi_low_statusin(struct scsi_low_softc *, struct targ_info *, u_int);
  698 
  699 /* data phase */
  700 int scsi_low_data(struct scsi_low_softc *, struct targ_info *, struct buf **, int);
  701 static __inline void scsi_low_data_finish(struct scsi_low_softc *);
  702 
  703 /* cmd phase */
  704 int scsi_low_cmd(struct scsi_low_softc *, struct targ_info *);
  705 
  706 /* reselection phase */
  707 struct targ_info *scsi_low_reselected(struct scsi_low_softc *, u_int);
  708 
  709 /* disconnection phase */
  710 int scsi_low_disconnected(struct scsi_low_softc *, struct targ_info *);
  711 
  712 /* 
  713  * Scsi bus restart function.
  714  * Canncel all established nexuses => scsi system initialized => restart jobs.
  715  */
  716 #define SCSI_LOW_RESTART_HARD   1
  717 #define SCSI_LOW_RESTART_SOFT   0
  718 int scsi_low_restart(struct scsi_low_softc *, int, u_char *);
  719 
  720 /* 
  721  * Scsi utility fucntions
  722  */
  723 /* print current status */
  724 void scsi_low_print(struct scsi_low_softc *, struct targ_info *);
  725 
  726 /* bus reset utility */
  727 void scsi_low_bus_reset(struct scsi_low_softc *);
  728 
  729 /*************************************************
  730  * Message macro defs
  731  *************************************************/
  732 #define SCSI_LOW_SETUP_PHASE(ti, phase)                 \
  733 {                                                       \
  734         (ti)->ti_ophase = ti->ti_phase;                 \
  735         (ti)->ti_phase = (phase);                       \
  736 }
  737 
  738 #define SCSI_LOW_SETUP_MSGPHASE(slp, PHASE)             \
  739 {                                                       \
  740         (slp)->sl_msgphase = (PHASE);                   \
  741 }
  742 
  743 #define SCSI_LOW_ASSERT_ATN(slp)                        \
  744 {                                                       \
  745         (slp)->sl_atten = 1;                            \
  746 }
  747 
  748 #define SCSI_LOW_DEASSERT_ATN(slp)                      \
  749 {                                                       \
  750         (slp)->sl_atten = 0;                            \
  751 }
  752 
  753 /*************************************************
  754  * Inline functions
  755  *************************************************/
  756 static __inline void scsi_low_attention(struct scsi_low_softc *);
  757 static __inline int scsi_low_is_msgout_continue(struct targ_info *, u_int);
  758 static __inline int scsi_low_assert_msg(struct scsi_low_softc *, struct targ_info *, u_int, int);
  759 static __inline int scsi_low_is_disconnect_ok(struct slccb *);
  760 
  761 static __inline int
  762 scsi_low_is_msgout_continue(ti, mask)
  763         struct targ_info *ti;
  764         u_int mask;
  765 {
  766         
  767         return ((ti->ti_msgflags & (~mask)) != 0);
  768 }
  769 
  770 static __inline int
  771 scsi_low_is_disconnect_ok(cb)
  772         struct slccb *cb;
  773 {
  774 
  775         return ((cb->li->li_flags & SCSI_LOW_DISC) != 0 &&
  776                     (cb->ccb_flags & (CCB_SENSE | CCB_CLEARQ)) == 0);
  777 }
  778 
  779 static __inline void
  780 scsi_low_attention(slp)
  781         struct scsi_low_softc *slp;
  782 {
  783 
  784         if (slp->sl_atten != 0)
  785                 return;
  786 
  787         (*slp->sl_funcs->scsi_low_attention) (slp);
  788         SCSI_LOW_ASSERT_ATN(slp);
  789 }
  790 
  791 static __inline int
  792 scsi_low_assert_msg(slp, ti, msg, now)
  793         struct scsi_low_softc *slp;
  794         struct targ_info *ti;
  795         u_int msg;
  796         int now;
  797 {
  798 
  799         ti->ti_msgflags |= msg;
  800         if (now != 0)
  801                 scsi_low_attention(slp);
  802         return 0;
  803 }
  804 
  805 static __inline void
  806 scsi_low_arbit_win(slp)
  807         struct scsi_low_softc *slp;
  808 {
  809 
  810         slp->sl_selid = NULL;
  811 }
  812 
  813 static __inline void
  814 scsi_low_data_finish(slp)
  815         struct scsi_low_softc *slp;
  816 {
  817 
  818         if (slp->sl_Qnexus != NULL)
  819         {
  820                 slp->sl_Qnexus->ccb_datalen = slp->sl_scp.scp_datalen;
  821         }
  822 }
  823 
  824 static __inline int
  825 scsi_low_statusin(slp, ti, c)
  826         struct scsi_low_softc *slp;
  827         struct targ_info *ti;
  828         u_int c;
  829 {
  830 
  831         slp->sl_ph_count ++;
  832         if ((c & SCSI_LOW_DATA_PE) != 0)
  833         {
  834                 scsi_low_assert_msg(slp, ti, SCSI_LOW_MSG_ERROR, 0);
  835                 return EIO;
  836         }
  837         slp->sl_scp.scp_status = (u_int8_t) c;
  838         return 0;
  839 }
  840 
  841 /*************************************************
  842  * Message out defs
  843  *************************************************/
  844 /* XXX: use scsi_message.h */
  845 #define ST_GOOD         0x00
  846 #define ST_CHKCOND      0x02
  847 #define ST_MET          0x04
  848 #define ST_BUSY         0x08
  849 #define ST_INTERGOOD    0x10
  850 #define ST_INTERMET     0x14
  851 #define ST_CONFLICT     0x18
  852 #define ST_CMDTERM      0x22
  853 #define ST_QUEFULL      0x28
  854 #define ST_UNKNOWN      0xff
  855 
  856 #define MSG_COMP        0x00
  857 #define MSG_EXTEND      0x01
  858 
  859 #define MKMSG_EXTEND(XLEN, XCODE) ((((u_int)(XLEN)) << NBBY) | ((u_int)(XCODE)))
  860 #define MSG_EXTEND_MDPCODE      0x00
  861 #define MSG_EXTEND_MDPLEN       0x05
  862 #define MSG_EXTEND_SYNCHCODE    0x01
  863 #define MSG_EXTEND_SYNCHLEN     0x03
  864 #define MSG_EXTEND_WIDECODE     0x03
  865 #define MSG_EXTEND_WIDELEN      0x02
  866 
  867 #define MSG_SAVESP      0x02
  868 #define MSG_RESTORESP   0x03
  869 #define MSG_DISCON      0x04
  870 #define MSG_I_ERROR     0x05
  871 #define MSG_ABORT       0x06
  872 #define MSG_REJECT      0x07
  873 #define MSG_NOOP        0x08
  874 #define MSG_PARITY      0x09
  875 #define MSG_LCOMP       0x0a
  876 #define MSG_LCOMP_F     0x0b
  877 #define MSG_RESET       0x0c
  878 #define MSG_ABORT_QTAG  0x0d
  879 #define MSG_CLEAR_QTAG  0x0e
  880 #define MSG_TERM_IO     0x11
  881 #define MSG_SIMPLE_QTAG 0x20
  882 #define MSG_HEAD_QTAG   0x21
  883 #define MSG_ORDERED_QTAG        0x22
  884 #define MSG_IDENTIFY            0x80
  885 #define MSG_IDENTIFY_DISCPRIV   0x40
  886 #endif  /* !_SCSI_LOW_H_ */

Cache object: d6e23fa46e90bed5cc86da5a03d1d746


[ 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.