xref: /freebsd/sys/dev/tws/tws.h (revision b356ddf07671c7e0c960231344da7bddf5df42c4)
1 /*-
2  * SPDX-License-Identifier: BSD-3-Clause
3  *
4  * Copyright (c) 2010, LSI Corp.
5  * All rights reserved.
6  * Author : Manjunath Ranganathaiah
7  * Support: freebsdraid@lsi.com
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  *
13  * 1. Redistributions of source code must retain the above copyright
14  *    notice, this list of conditions and the following disclaimer.
15  * 2. Redistributions in binary form must reproduce the above copyright
16  *    notice, this list of conditions and the following disclaimer in
17  *    the documentation and/or other materials provided with the
18  *    distribution.
19  * 3. Neither the name of the <ORGANIZATION> nor the names of its
20  *    contributors may be used to endorse or promote products derived
21  *    from this software without specific prior written permission.
22  *
23  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
24  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
25  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
26  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
27  * COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
28  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
29  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
30  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
31  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
32  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
33  * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
34  * POSSIBILITY OF SUCH DAMAGE.
35  *
36  * $FreeBSD$
37  */
38 
39 #include <sys/param.h>        /* defines used in kernel.h */
40 #include <sys/bus.h>          /* structs, prototypes for pci bus stuff */
41 #include <sys/conf.h>         /* cdevsw struct */
42 #include <sys/errno.h>
43 #include <sys/kernel.h>       /* types used in module initialization */
44 #include <sys/lock.h>
45 #include <sys/malloc.h>
46 #include <sys/module.h>
47 #include <sys/mutex.h>
48 #include <sys/proc.h>
49 #include <sys/systm.h>
50 #include <sys/uio.h>          /* uio struct */
51 
52 #include <machine/bus.h>
53 #include <sys/rman.h>
54 #include <machine/resource.h>
55 
56 #include <dev/pci/pcivar.h>   /* For pci_get macros! */
57 #include <dev/pci/pcireg.h>
58 
59 #include <sys/types.h>
60 #include <sys/sysctl.h>
61 #include <sys/stat.h>
62 
63 
64 #define TWS_PULL_MODE_ENABLE 1
65 
66 MALLOC_DECLARE(M_TWS);
67 /* externs */
68 extern int tws_queue_depth;
69 
70 
71 #define TWS_DRIVER_VERSION_STRING "10.80.00.005"
72 #define TWS_MAX_NUM_UNITS             65
73 #define TWS_MAX_NUM_LUNS              32
74 #define TWS_MAX_IRQS                  2
75 #define TWS_SCSI_INITIATOR_ID         66
76 #define TWS_MAX_IO_SIZE               0x20000 /* 128kB */
77 #define TWS_SECTOR_SIZE               0x200
78 #define TWS_POLL_TIMEOUT              60
79 #define TWS_IO_TIMEOUT                60
80 #define TWS_IOCTL_TIMEOUT             60
81 #define TWS_RESET_TIMEOUT             60
82 
83 #define TWS_PCI_BAR0                  0x10
84 #define TWS_PCI_BAR1                  0x14
85 #define TWS_PCI_BAR2                  0x1C
86 
87 #define TWS_VENDOR_ID                 0x13C1
88 #define TWS_DEVICE_ID                 0x1010
89 
90 #define TWS_INVALID_REQID             0xFFFF
91 
92 /* bus tag related */
93 #define TWS_ALIGNMENT                 4
94 #define TWS_IN_MF_ALIGNMENT           16
95 #define TWS_OUT_MF_ALIGNMENT          4
96 
97 #define TWS_MAX_32BIT_SG_ELEMENTS     93     /* max 32-bit sg elements */
98 #define TWS_MAX_64BIT_SG_ELEMENTS     46     /* max 64-bit sg elements */
99 
100 #define TWS_MAX_QS                    4
101 #define TWS_MAX_REQS                  256
102 #define TWS_RESERVED_REQS             4
103 
104 /* Request states */
105 #define TWS_REQ_STATE_FREE            0
106 #define TWS_REQ_STATE_BUSY            1
107 #define TWS_REQ_STATE_TRAN            2
108 #define TWS_REQ_STATE_COMPLETE        3
109 
110 /* Request types */
111 #define TWS_REQ_TYPE_INTERNAL_CMD     0x0
112 #define TWS_REQ_TYPE_AEN_FETCH        0x1
113 #define TWS_REQ_TYPE_PASSTHRU         0x2
114 #define TWS_REQ_TYPE_GETSET_PARAM     0x3
115 #define TWS_REQ_TYPE_SCSI_IO          0x4
116 
117 /* Driver states */
118 
119 enum tws_states {
120     TWS_INIT=50,
121     TWS_UNINIT,
122     TWS_OFFLINE,
123     TWS_ONLINE,
124     TWS_RESET,
125 };
126 
127 /* events */
128 
129 enum tws_events {
130     TWS_INIT_START=100,
131     TWS_INIT_COMPLETE,
132     TWS_UNINIT_START,
133     TWS_RESET_START,
134     TWS_RESET_COMPLETE,
135     TWS_SCAN_FAILURE,
136 };
137 
138 enum tws_req_flags {
139     TWS_DIR_UNKNOWN = 0x1,
140     TWS_DIR_IN = 0x2,
141     TWS_DIR_OUT = 0x4,
142     TWS_DIR_NONE = 0x8,
143     TWS_DATA_CCB = 0x10,
144 };
145 
146 enum tws_intrs {
147      TWS_INTx,
148      TWS_MSI,
149      TWS_MSIX,
150 };
151 
152 struct tws_msix_info {
153     int tbl_res_id;
154     bus_space_tag_t tbl_tag;
155     bus_space_handle_t tbl_handle;
156     struct resource *tbl_res;
157 };
158 
159 struct tws_ioctl_lock {
160     u_int32_t       lock;
161     time_t          timeout;
162 };
163 
164 
165 #define TWS_TRACE_FNAME_LEN  10
166 #define TWS_TRACE_FUNC_LEN   15
167 #define TWS_TRACE_DESC_LEN   10
168 struct tws_trace_rec {
169     struct timespec ts;
170     char fname[TWS_TRACE_FNAME_LEN];
171     char func[TWS_TRACE_FUNC_LEN];
172     int linenum;
173     char desc[TWS_TRACE_DESC_LEN];
174     u_int64_t val1;
175     u_int64_t val2;
176 };
177 
178 struct tws_circular_q {
179     volatile int16_t head;
180     volatile int16_t tail;
181     u_int16_t depth;
182     u_int8_t  overflow;
183     void *    q;
184 };
185 
186 
187 
188 struct tws_stats {
189     u_int64_t reqs_in;
190     u_int64_t reqs_out;
191     u_int64_t reqs_errored;
192     u_int64_t spurios_intrs;
193     u_int64_t num_intrs;
194     u_int64_t num_aens;
195     u_int64_t ioctls;
196     u_int64_t scsi_ios;
197 };
198 
199 struct tws_init_connect_info {
200     u_int16_t     working_srl;
201     u_int16_t     working_branch;
202     u_int16_t     working_build;
203     u_int16_t     fw_on_ctlr_srl;
204     u_int16_t     fw_on_ctlr_branch;
205     u_int16_t     fw_on_ctlr_build;
206 
207 };
208 
209 
210 /* ------------ boolean types ------------------- */
211 
212 #ifndef __bool_true_false_are_defined
213 typedef enum _boolean { false, true } boolean;
214 #else
215 #define	boolean		bool
216 #endif
217 enum err { SUCCESS, FAILURE };
218 
219 /* ----------- per instance data ---------------- */
220 
221 /* The softc holds our per-instance data. */
222 struct tws_softc {
223     device_t    tws_dev;                  /* bus device */
224     struct cdev *tws_cdev;                /* controller device */
225     u_int32_t   device_id;                /* device id */
226     u_int32_t   subvendor_id;             /* device id */
227     u_int32_t   subdevice_id;             /* device id */
228     u_int8_t    tws_state;                /* driver state */
229     u_int8_t    tws_prev_state;           /* driver prev state */
230     struct sysctl_ctx_list tws_clist;     /* sysctl context */
231     struct sysctl_oid *tws_oidp;          /* sysctl context */
232     struct resource *reg_res;             /* register interface window */
233     struct resource *mfa_res;             /* mfa interface window */
234     int reg_res_id;                       /* register resource id */
235     int mfa_res_id;                       /* register resource id */
236     bus_space_handle_t bus_handle;        /* bus space handle */
237     bus_space_handle_t bus_mfa_handle;     /* bus space handle */
238     bus_space_tag_t bus_tag;              /* bus space tag */
239     bus_space_tag_t bus_mfa_tag;          /* bus space tag for mfa's */
240     u_int64_t mfa_base;                   /* mfa base address */
241     struct resource *irq_res[TWS_MAX_IRQS];/* interrupt resource */
242     int irq_res_id[TWS_MAX_IRQS];         /* intr resource id */
243     void *intr_handle[TWS_MAX_IRQS];      /* interrupt handle */
244     int irqs;                             /* intrs used */
245     struct tws_msix_info msix;            /* msix info */
246     struct cam_sim *sim;                  /* sim for this controller */
247     struct cam_path *path;                /* Ctlr path to CAM */
248     struct mtx q_lock;                    /* queue lock */
249     struct mtx sim_lock;                  /* sim lock */
250     struct mtx gen_lock;                  /* general driver  lock */
251     struct mtx io_lock;                   /* IO  lock */
252     struct tws_ioctl_lock ioctl_lock;     /* ioctl lock */
253     u_int32_t seq_id;                     /* Sequence id */
254     struct tws_circular_q aen_q;          /* aen q */
255     struct tws_circular_q trace_q;        /* trace q */
256     struct tws_stats stats;               /* I/O stats */
257     struct tws_init_connect_info cinfo;   /* compatibility info */
258     boolean is64bit;                      /* True - 64bit else 32bit */
259     u_int8_t intr_type;                   /* Interrupt type used */
260     bus_dma_tag_t parent_tag;             /* parent DMA tag */
261     bus_dma_tag_t cmd_tag;                /* command DMA tag */
262     bus_dmamap_t cmd_map;                 /* command map */
263     void *dma_mem;                        /* pointer to dmable memory */
264     u_int64_t dma_mem_phys;               /* phy addr */
265     bus_dma_tag_t data_tag;               /* data DMA tag */
266     void *ioctl_data_mem;                 /* ioctl dmable memory */
267     bus_dmamap_t ioctl_data_map;          /* ioctl data map */
268     struct tws_request *reqs;             /* pointer to requests */
269     struct tws_sense *sense_bufs;         /* pointer to sense buffers */
270     boolean obfl_q_overrun;               /* OBFL overrun flag  */
271     union ccb *scan_ccb;                  /* pointer to a ccb */
272     struct tws_request *q_head[TWS_MAX_QS]; /* head pointers to q's */
273     struct tws_request *q_tail[TWS_MAX_QS]; /* tail pointers to q's */
274     struct callout stats_timer;
275 };
276