xref: /freebsd/sys/dev/tws/tws_hdm.h (revision b00ab754)
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 
40 /* bit's defination */
41 
42 #define TWS_BIT0                              0x00000001
43 #define TWS_BIT1                              0x00000002
44 #define TWS_BIT2                              0x00000004
45 #define TWS_BIT3                              0x00000008
46 #define TWS_BIT4                              0x00000010
47 #define TWS_BIT5                              0x00000020
48 #define TWS_BIT6                              0x00000040
49 #define TWS_BIT7                              0x00000080
50 #define TWS_BIT8                              0x00000100
51 #define TWS_BIT9                              0x00000200
52 #define TWS_BIT10                             0x00000400
53 #define TWS_BIT11                             0x00000800
54 #define TWS_BIT12                             0x00001000
55 #define TWS_BIT13                             0x00002000
56 #define TWS_BIT14                             0x00004000
57 #define TWS_BIT15                             0x00008000
58 #define TWS_BIT16                             0x00010000
59 #define TWS_BIT17                             0x00020000
60 #define TWS_BIT18                             0x00040000
61 #define TWS_BIT19                             0x00080000
62 #define TWS_BIT20                             0x00100000
63 #define TWS_BIT21                             0x00200000
64 #define TWS_BIT22                             0x00400000
65 #define TWS_BIT23                             0x00800000
66 #define TWS_BIT24                             0x01000000
67 #define TWS_BIT25                             0x02000000
68 #define TWS_BIT26                             0x04000000
69 #define TWS_BIT27                             0x08000000
70 #define TWS_BIT28                             0x10000000
71 #define TWS_BIT29                             0x20000000
72 #define TWS_BIT30                             0x40000000
73 #define TWS_BIT31                             0x80000000
74 
75 #define TWS_SENSE_DATA_LENGTH                 18
76 #define TWS_ERROR_SPECIFIC_DESC_LEN           98
77 
78 /* response codes */
79 #define TWS_SENSE_SCSI_CURRENT_ERROR          0x70
80 #define TWS_SENSE_SCSI_DEFERRED_ERROR         0x71
81 
82 #define TWS_SRC_CTRL_ERROR                    3
83 #define TWS_SRC_CTRL_EVENT                    4
84 #define TWS_SRC_FREEBSD_DRIVER                5
85 #define TWS_SRC_FREEBSD_OS                    8
86 
87 
88 enum tws_sense_severity {
89     error = 1,
90     warning ,
91     info,
92     debug,
93 };
94 
95 /*
96  * Some errors of interest (in cmd_hdr->status_block.error) when a command
97  * is completed by the firmware with an error.
98  */
99 #define TWS_ERROR_LOGICAL_UNIT_NOT_SUPPORTED    0x010a
100 #define TWS_ERROR_NOT_SUPPORTED                 0x010D
101 #define TWS_ERROR_UNIT_OFFLINE                  0x0128
102 #define TWS_ERROR_MORE_DATA                     0x0231
103 
104 
105 /* AEN codes of interest. */
106 #define TWS_AEN_QUEUE_EMPTY                     0x00
107 #define TWS_AEN_SOFT_RESET                      0x01
108 #define TWS_AEN_SYNC_TIME_WITH_HOST             0x31
109 
110 
111 /* AEN severity */
112 #define TWS_SEVERITY_ERROR                      0x1
113 #define TWS_SEVERITY_WARNING                    0x2
114 #define TWS_SEVERITY_INFO                       0x3
115 #define TWS_SEVERITY_DEBUG                      0x4
116 
117 #define TWS_64BIT_SG_ADDRESSES                  0x00000001
118 #define TWS_BIT_EXTEND                          0x00000002
119 
120 #define TWS_BASE_FW_SRL                         24
121 #define TWS_BASE_FW_BRANCH                      0
122 #define TWS_BASE_FW_BUILD                       1
123 #define TWS_CURRENT_FW_SRL                      41
124 
125 #define TWS_CURRENT_FW_BRANCH                   8
126 #define TWS_CURRENT_FW_BUILD                    4
127 #define TWS_CURRENT_ARCH_ID                     0x000A
128 
129 
130 #define TWS_FIFO_EMPTY                          0xFFFFFFFFFFFFFFFFull
131 #define TWS_FIFO_EMPTY32                        0xFFFFFFFFull
132 
133 
134 /* Register offsets from base address. */
135 #define TWS_CONTROL_REGISTER_OFFSET             0x0
136 #define TWS_STATUS_REGISTER_OFFSET              0x4
137 #define TWS_COMMAND_QUEUE_OFFSET                0x8
138 #define TWS_RESPONSE_QUEUE_OFFSET               0xC
139 #define TWS_COMMAND_QUEUE_OFFSET_LOW            0x20
140 #define TWS_COMMAND_QUEUE_OFFSET_HIGH           0x24
141 #define TWS_LARGE_RESPONSE_QUEUE_OFFSET         0x30
142 
143 /* I2O offsets */
144 #define TWS_I2O0_STATUS                         0x0
145 
146 #define TWS_I2O0_HIBDB                          0x20
147 
148 #define TWS_I2O0_HISTAT                         0x30
149 #define TWS_I2O0_HIMASK                         0x34
150 
151 #define TWS_I2O0_HIBQP                          0x40
152 #define TWS_I2O0_HOBQP                          0x44
153 
154 #define TWS_I2O0_CTL                            0x74
155 
156 #define TWS_I2O0_IOBDB                          0x9C
157 #define TWS_I2O0_HOBDBC                         0xA0
158 
159 #define TWS_I2O0_SCRPD3                         0xBC
160 
161 #define TWS_I2O0_HIBQPL                         0xC0 /* 64bit inb port low */
162 #define TWS_I2O0_HIBQPH                         0xC4 /* 64bit inb port high */
163 #define TWS_I2O0_HOBQPL                         0xC8 /* 64bit out port low */
164 #define TWS_I2O0_HOBQPH                         0xCC /* 64bit out port high */
165 
166 /* IOP related */
167 #define TWS_I2O0_IOPOBQPL                       0xD8 /* OBFL */
168 #define TWS_I2O0_IOPOBQPH                       0xDC /* OBFH */
169 #define TWS_I2O0_SRC_ADDRH                      0xF8 /* Msg ASA */
170 
171 #define TWS_MSG_ACC_MASK                        0x20000000
172 #define TWS_32BIT_MASK                          0xFFFFFFFF
173 
174 /* revisit */
175 #define TWS_FW_CMD_NOP                     0x0
176 #define TWS_FW_CMD_INIT_CONNECTION         0x01
177 #define TWS_FW_CMD_EXECUTE_SCSI            0x10
178 
179 #define TWS_FW_CMD_ATA_PASSTHROUGH         0x11 // This is really a PASSTHROUGH for both ATA and SCSI commands.
180 #define TWS_FW_CMD_GET_PARAM               0x12
181 #define TWS_FW_CMD_SET_PARAM               0x13
182 
183 
184 #define BUILD_SGL_OFF__OPCODE(sgl_off, opcode)  \
185         ((sgl_off << 5) & 0xE0) | (opcode & 0x1F)       /* 3:5 */
186 
187 #define BUILD_RES__OPCODE(res, opcode)          \
188         ((res << 5) & 0xE0) | (opcode & 0x1F)           /* 3:5 */
189 
190 #define GET_OPCODE(sgl_off__opcode)     \
191         (sgl_off__opcode & 0x1F)                        /* 3:5 */
192 
193 
194 
195 /* end revisit */
196 
197 
198 /* Table #'s and id's of parameters of interest in firmware's param table. */
199 #define TWS_PARAM_VERSION_TABLE         0x0402
200 #define TWS_PARAM_VERSION_FW            3       /* firmware version [16] */
201 #define TWS_PARAM_VERSION_BIOS          4       /* BIOSs version [16] */
202 #define TWS_PARAM_CTLR_MODEL            8       /* Controller model [16] */
203 
204 #define TWS_PARAM_CONTROLLER_TABLE      0x0403
205 #define TWS_PARAM_CONTROLLER_PORT_COUNT 3       /* number of ports [1] */
206 
207 #define TWS_PARAM_TIME_TABLE            0x40A
208 #define TWS_PARAM_TIME_SCHED_TIME       0x3
209 
210 #define TWS_PARAM_PHYS_TABLE            0x0001
211 #define TWS_PARAM_CONTROLLER_PHYS_COUNT 2       /* number of phys */
212 
213 #define TWS_9K_PARAM_DESCRIPTOR         0x8000
214 
215 
216 /* ----------- request  ------------- */
217 
218 
219 #pragma pack(1)
220 
221 struct tws_cmd_init_connect {
222     u_int8_t        res1__opcode;   /* 3:5 */
223     u_int8_t        size;
224     u_int8_t        request_id;
225     u_int8_t        res2;
226     u_int8_t        status;
227     u_int8_t        flags;
228     u_int16_t       message_credits;
229     u_int32_t       features;
230     u_int16_t       fw_srl;
231     u_int16_t       fw_arch_id;
232     u_int16_t       fw_branch;
233     u_int16_t       fw_build;
234     u_int32_t       result;
235 };
236 
237 /* Structure for downloading firmware onto the controller. */
238 struct tws_cmd_download_firmware {
239     u_int8_t        sgl_off__opcode;/* 3:5 */
240     u_int8_t        size;
241     u_int8_t        request_id;
242     u_int8_t        unit;
243     u_int8_t        status;
244     u_int8_t        flags;
245     u_int16_t       param;
246     u_int8_t        sgl[1];
247 };
248 
249 /* Structure for hard resetting the controller. */
250 struct tws_cmd_reset_firmware {
251     u_int8_t        res1__opcode;   /* 3:5 */
252     u_int8_t        size;
253     u_int8_t        request_id;
254     u_int8_t        unit;
255     u_int8_t        status;
256     u_int8_t        flags;
257     u_int8_t        res2;
258     u_int8_t        param;
259 };
260 
261 
262 /* Structure for sending get/set param commands. */
263 struct tws_cmd_param {
264     u_int8_t        sgl_off__opcode;/* 3:5 */
265     u_int8_t        size;
266     u_int8_t        request_id;
267     u_int8_t        host_id__unit;  /* 4:4 */
268     u_int8_t        status;
269     u_int8_t        flags;
270     u_int16_t       param_count;
271     u_int8_t        sgl[1];
272 };
273 
274 /* Generic command packet. */
275 struct tws_cmd_generic {
276     u_int8_t        sgl_off__opcode;/* 3:5 */
277     u_int8_t        size;
278     u_int8_t        request_id;
279     u_int8_t        host_id__unit;  /* 4:4 */
280     u_int8_t        status;
281     u_int8_t        flags;
282     u_int16_t       count;  /* block cnt, parameter cnt, message credits */
283 };
284 
285 
286 
287 
288 /* Command packet header. */
289 struct tws_command_header {
290     u_int8_t        sense_data[TWS_SENSE_DATA_LENGTH];
291     struct { /* status block - additional sense data */
292         u_int16_t       srcnum;
293         u_int8_t        reserved;
294         u_int8_t        status;
295         u_int16_t       error;
296         u_int8_t        res__srcid;     /* 4:4 */
297         u_int8_t        res__severity;  /* 5:3 */
298     } status_block;
299     u_int8_t        err_specific_desc[TWS_ERROR_SPECIFIC_DESC_LEN];
300     struct { /* sense buffer descriptor */
301         u_int8_t        size_header;
302         u_int16_t       request_id;
303         u_int8_t        size_sense;
304     } header_desc;
305 };
306 
307 /* Command - 1024 byte size including header (128+24+896)*/
308 union tws_command_giga {
309     struct tws_cmd_init_connect       init_connect;
310     struct tws_cmd_download_firmware  download_fw;
311     struct tws_cmd_reset_firmware     reset_fw;
312     struct tws_cmd_param              param;
313     struct tws_cmd_generic            generic;
314     u_int8_t        padding[1024 - sizeof(struct tws_command_header)];
315 };
316 
317 /* driver command pkt - 1024 byte size including header(128+24+744+128) */
318 /* h/w & f/w supported command size excluding header 768 */
319 struct tws_command_apache {
320     u_int8_t        res__opcode;    /* 3:5 */
321     u_int8_t        unit;
322     u_int16_t       lun_l4__req_id; /* 4:12 */
323     u_int8_t        status;
324     u_int8_t        sgl_offset;     /* offset (in bytes) to sg_list,
325                                      from the end of sgl_entries */
326     u_int16_t       lun_h4__sgl_entries;
327     u_int8_t        cdb[16];
328     u_int8_t        sg_list[744];   /* 768 - 24 */
329     u_int8_t        padding[128];   /* make it 1024 bytes */
330 };
331 
332 struct tws_command_packet {
333     struct tws_command_header hdr;
334     union {
335         union tws_command_giga pkt_g;
336         struct tws_command_apache pkt_a;
337     } cmd;
338 };
339 
340 /* Structure describing payload for get/set param commands. */
341 struct tws_getset_param {
342     u_int16_t       table_id;
343     u_int8_t        parameter_id;
344     u_int8_t        reserved;
345     u_int16_t       parameter_size_bytes;
346     u_int16_t       parameter_actual_size_bytes;
347     u_int8_t        data[1];
348 };
349 
350 struct tws_outbound_response {
351     u_int32_t     not_mfa   :1;   /* 1 if the structure is valid else MFA */
352     u_int32_t     reserved  :7;   /* reserved bits */
353     u_int32_t     status    :8;   /* should be 0 */
354     u_int32_t     request_id:16;  /* request id */
355 };
356 
357 
358 /* Scatter/Gather list entry with 32 bit addresses. */
359 struct tws_sg_desc32 {
360     u_int32_t     address;
361     u_int32_t     length  :24;
362     u_int32_t     flag    :8;
363 };
364 
365 /* Scatter/Gather list entry with 64 bit addresses. */
366 struct tws_sg_desc64 {
367     u_int64_t     address;
368     u_int64_t     length   :32;
369     u_int64_t     reserved :24;
370     u_int64_t     flag     :8;
371 };
372 
373 /*
374  * Packet that describes an AEN/error generated by the controller,
375  * shared with user
376  */
377 struct tws_event_packet {
378     u_int32_t       sequence_id;
379     u_int32_t       time_stamp_sec;
380     u_int16_t       aen_code;
381     u_int8_t        severity;
382     u_int8_t        retrieved;
383     u_int8_t        repeat_count;
384     u_int8_t        parameter_len;
385     u_int8_t        parameter_data[TWS_ERROR_SPECIFIC_DESC_LEN];
386     u_int32_t       event_src;
387     u_int8_t        severity_str[20];
388 };
389 
390 
391 
392 #pragma pack()
393 
394 struct tws_sense {
395     struct tws_command_header *hdr;
396     u_int64_t  hdr_pkt_phy;
397 };
398 
399 struct tws_request {
400     struct tws_command_packet *cmd_pkt; /* command pkt */
401     u_int64_t    cmd_pkt_phy;    /* cmd pkt physical address */
402     void         *data;          /* ptr to data being passed to fw */
403     u_int32_t    length;         /* length of data being passed to fw */
404 
405     u_int32_t    state;          /* request state */
406     u_int32_t    type;           /* request type */
407     u_int32_t    flags;          /* request flags */
408 
409     u_int32_t    error_code;     /* error during request processing */
410 
411     u_int32_t    request_id;     /* request id for tracking with fw */
412     void         (*cb)(struct tws_request *);      /* callback func */
413     bus_dmamap_t dma_map;        /* dma map */
414     union ccb    *ccb_ptr;       /* pointer to ccb */
415     struct callout timeout;	 /* request timeout timer */
416     struct tws_softc *sc;        /* pointer back to ctlr softc */
417 
418     struct tws_request *next;    /* pointer to next request */
419     struct tws_request *prev;    /* pointer to prev request */
420 };
421 
422 
423