xref: /dragonfly/sys/dev/raid/mfi/mfireg.h (revision 92fc8b5c)
1 /*-
2  * Copyright (c) 2006 IronPort Systems
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in the
12  *    documentation and/or other materials provided with the distribution.
13  *
14  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
15  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
18  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
20  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
22  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
23  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
24  * SUCH DAMAGE.
25  */
26 /*-
27  * Copyright (c) 2007 LSI Corp.
28  * Copyright (c) 2007 Rajesh Prabhakaran.
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  *
40  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
41  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
42  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
43  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
44  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
45  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
46  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
47  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
48  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
49  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
50  * SUCH DAMAGE.
51  *
52  * $FreeBSD: src/sys/dev/mfi/mfireg.h,v 1.14 2010/10/21 10:38:52 pluknet Exp $
53  */
54 
55 #ifndef _MFIREG_H
56 #define _MFIREG_H
57 
58 /*
59  * MegaRAID SAS MFI firmware definitions
60  *
61  * Calling this driver 'MegaRAID SAS' is a bit misleading.  It's a completely
62  * new firmware interface from the old AMI MegaRAID one, and there is no
63  * reason why this interface should be limited to just SAS.  In any case, LSI
64  * seems to also call this interface 'MFI', so that will be used here.
65  */
66 
67 /*
68  * Start with the register set.  All registers are 32 bits wide.
69  * The usual Intel IOP style setup.
70  */
71 #define MFI_IMSG0	0x10	/* Inbound message 0 */
72 #define MFI_IMSG1	0x14	/* Inbound message 1 */
73 #define MFI_OMSG0	0x18	/* Outbound message 0 */
74 #define MFI_OMSG1	0x1c	/* Outbound message 1 */
75 #define MFI_IDB		0x20	/* Inbound doorbell */
76 #define MFI_ISTS	0x24	/* Inbound interrupt status */
77 #define MFI_IMSK	0x28	/* Inbound interrupt mask */
78 #define MFI_ODB		0x2c	/* Outbound doorbell */
79 #define MFI_OSTS	0x30	/* Outbound interrupt status */
80 #define MFI_OMSK	0x34	/* Outbound interrupt mask */
81 #define MFI_IQP		0x40	/* Inbound queue port */
82 #define MFI_OQP		0x44	/* Outbound queue port */
83 
84 /*
85  * 1078 specific related register
86  */
87 #define MFI_ODR0	0x9c 		/* outbound doorbell register0 */
88 #define MFI_ODCR0	0xa0 		/* outbound doorbell clear register0  */
89 #define MFI_OSP0	0xb0 		/* outbound scratch pad0  */
90 #define MFI_1078_EIM	0x80000004 	/* 1078 enable intrrupt mask  */
91 #define MFI_RMI		0x2 		/* reply message interrupt  */
92 #define MFI_1078_RM	0x80000000 	/* reply 1078 message interrupt  */
93 #define MFI_ODC		0x4 		/* outbound doorbell change interrupt */
94 
95 /*
96  * GEN2 specific changes
97  */
98 #define MFI_GEN2_EIM	0x00000005	/* GEN2 enable interrupt mask */
99 #define MFI_GEN2_RM	0x00000001	/* reply GEN2 message interrupt */
100 
101 /* Bits for MFI_OSTS */
102 #define MFI_OSTS_INTR_VALID	0x00000002
103 
104 /*
105  * Firmware state values.  Found in OMSG0 during initialization.
106  */
107 #define MFI_FWSTATE_MASK		0xf0000000
108 #define MFI_FWSTATE_UNDEFINED		0x00000000
109 #define MFI_FWSTATE_BB_INIT		0x10000000
110 #define MFI_FWSTATE_FW_INIT		0x40000000
111 #define MFI_FWSTATE_WAIT_HANDSHAKE	0x60000000
112 #define MFI_FWSTATE_FW_INIT_2		0x70000000
113 #define MFI_FWSTATE_DEVICE_SCAN		0x80000000
114 #define MFI_FWSTATE_FLUSH_CACHE		0xa0000000
115 #define MFI_FWSTATE_READY		0xb0000000
116 #define MFI_FWSTATE_OPERATIONAL		0xc0000000
117 #define MFI_FWSTATE_FAULT		0xf0000000
118 #define MFI_FWSTATE_MAXSGL_MASK		0x00ff0000
119 #define MFI_FWSTATE_MAXCMD_MASK		0x0000ffff
120 
121 /*
122  * Control bits to drive the card to ready state.  These go into the IDB
123  * register.
124  */
125 #define MFI_FWINIT_ABORT	0x00000000 /* Abort all pending commands */
126 #define MFI_FWINIT_READY	0x00000002 /* Move from operational to ready */
127 #define MFI_FWINIT_MFIMODE	0x00000004 /* unknown */
128 #define MFI_FWINIT_CLEAR_HANDSHAKE 0x00000008 /* Respond to WAIT_HANDSHAKE */
129 
130 /* MFI Commands */
131 typedef enum {
132 	MFI_CMD_INIT =		0x00,
133 	MFI_CMD_LD_READ,
134 	MFI_CMD_LD_WRITE,
135 	MFI_CMD_LD_SCSI_IO,
136 	MFI_CMD_PD_SCSI_IO,
137 	MFI_CMD_DCMD,
138 	MFI_CMD_ABORT,
139 	MFI_CMD_SMP,
140 	MFI_CMD_STP
141 } mfi_cmd_t;
142 
143 /* Direct commands */
144 typedef enum {
145 	MFI_DCMD_CTRL_GETINFO =		0x01010000,
146 	MFI_DCMD_CTRL_MFC_DEFAULTS_GET =0x010e0201,
147 	MFI_DCMD_CTRL_MFC_DEFAULTS_SET =0x010e0202,
148 	MFI_DCMD_CTRL_FLUSHCACHE =	0x01101000,
149 	MFI_DCMD_CTRL_SHUTDOWN =	0x01050000,
150 	MFI_DCMD_CTRL_EVENT_GETINFO =	0x01040100,
151 	MFI_DCMD_CTRL_EVENT_GET =	0x01040300,
152 	MFI_DCMD_CTRL_EVENT_WAIT =	0x01040500,
153 	MFI_DCMD_PR_GET_STATUS =	0x01070100,
154 	MFI_DCMD_PR_GET_PROPERTIES =	0x01070200,
155 	MFI_DCMD_PR_SET_PROPERTIES =	0x01070300,
156 	MFI_DCMD_PR_START =		0x01070400,
157 	MFI_DCMD_PR_STOP =		0x01070500,
158 	MFI_DCMD_TIME_SECS_GET =	0x01080201,
159 	MFI_DCMD_FLASH_FW_OPEN =	0x010f0100,
160 	MFI_DCMD_FLASH_FW_DOWNLOAD =	0x010f0200,
161 	MFI_DCMD_FLASH_FW_FLASH =	0x010f0300,
162 	MFI_DCMD_FLASH_FW_CLOSE =	0x010f0400,
163 	MFI_DCMD_PD_GET_LIST =		0x02010000,
164 	MFI_DCMD_PD_GET_INFO = 		0x02020000,
165 	MFI_DCMD_PD_STATE_SET =		0x02030100,
166 	MFI_DCMD_PD_REBUILD_START =	0x02040100,
167 	MFI_DCMD_PD_REBUILD_ABORT =	0x02040200,
168 	MFI_DCMD_PD_CLEAR_START =	0x02050100,
169 	MFI_DCMD_PD_CLEAR_ABORT =	0x02050200,
170 	MFI_DCMD_PD_GET_PROGRESS =	0x02060000,
171 	MFI_DCMD_PD_LOCATE_START =	0x02070100,
172 	MFI_DCMD_PD_LOCATE_STOP =	0x02070200,
173 	MFI_DCMD_LD_GET_LIST =		0x03010000,
174 	MFI_DCMD_LD_GET_INFO =		0x03020000,
175 	MFI_DCMD_LD_GET_PROP =		0x03030000,
176 	MFI_DCMD_LD_SET_PROP =		0x03040000,
177 	MFI_DCMD_LD_INIT_START =	0x03060100,
178 	MFI_DCMD_LD_DELETE =		0x03090000,
179 	MFI_DCMD_CFG_READ =		0x04010000,
180 	MFI_DCMD_CFG_ADD =		0x04020000,
181 	MFI_DCMD_CFG_CLEAR =		0x04030000,
182 	MFI_DCMD_CFG_MAKE_SPARE =	0x04040000,
183 	MFI_DCMD_CFG_REMOVE_SPARE =	0x04050000,
184 	MFI_DCMD_CFG_FOREIGN_IMPORT =	0x04060400,
185 	MFI_DCMD_BBU_GET_STATUS =	0x05010000,
186 	MFI_DCMD_BBU_GET_CAPACITY_INFO =0x05020000,
187 	MFI_DCMD_BBU_GET_DESIGN_INFO =	0x05030000,
188 	MFI_DCMD_CLUSTER =		0x08000000,
189 	MFI_DCMD_CLUSTER_RESET_ALL =	0x08010100,
190 	MFI_DCMD_CLUSTER_RESET_LD =	0x08010200
191 } mfi_dcmd_t;
192 
193 /* Modifiers for MFI_DCMD_CTRL_FLUSHCACHE */
194 #define MFI_FLUSHCACHE_CTRL	0x01
195 #define MFI_FLUSHCACHE_DISK	0x02
196 
197 /* Modifiers for MFI_DCMD_CTRL_SHUTDOWN */
198 #define MFI_SHUTDOWN_SPINDOWN	0x01
199 
200 /*
201  * MFI Frame flags
202  */
203 #define MFI_FRAME_POST_IN_REPLY_QUEUE		0x0000
204 #define MFI_FRAME_DONT_POST_IN_REPLY_QUEUE	0x0001
205 #define MFI_FRAME_SGL32				0x0000
206 #define MFI_FRAME_SGL64				0x0002
207 #define MFI_FRAME_SENSE32			0x0000
208 #define MFI_FRAME_SENSE64			0x0004
209 #define MFI_FRAME_DIR_NONE			0x0000
210 #define MFI_FRAME_DIR_WRITE			0x0008
211 #define MFI_FRAME_DIR_READ			0x0010
212 #define MFI_FRAME_DIR_BOTH			0x0018
213 
214 /* MFI Status codes */
215 typedef enum {
216 	MFI_STAT_OK =			0x00,
217 	MFI_STAT_INVALID_CMD,
218 	MFI_STAT_INVALID_DCMD,
219 	MFI_STAT_INVALID_PARAMETER,
220 	MFI_STAT_INVALID_SEQUENCE_NUMBER,
221 	MFI_STAT_ABORT_NOT_POSSIBLE,
222 	MFI_STAT_APP_HOST_CODE_NOT_FOUND,
223 	MFI_STAT_APP_IN_USE,
224 	MFI_STAT_APP_NOT_INITIALIZED,
225 	MFI_STAT_ARRAY_INDEX_INVALID,
226 	MFI_STAT_ARRAY_ROW_NOT_EMPTY,
227 	MFI_STAT_CONFIG_RESOURCE_CONFLICT,
228 	MFI_STAT_DEVICE_NOT_FOUND,
229 	MFI_STAT_DRIVE_TOO_SMALL,
230 	MFI_STAT_FLASH_ALLOC_FAIL,
231 	MFI_STAT_FLASH_BUSY,
232 	MFI_STAT_FLASH_ERROR =		0x10,
233 	MFI_STAT_FLASH_IMAGE_BAD,
234 	MFI_STAT_FLASH_IMAGE_INCOMPLETE,
235 	MFI_STAT_FLASH_NOT_OPEN,
236 	MFI_STAT_FLASH_NOT_STARTED,
237 	MFI_STAT_FLUSH_FAILED,
238 	MFI_STAT_HOST_CODE_NOT_FOUNT,
239 	MFI_STAT_LD_CC_IN_PROGRESS,
240 	MFI_STAT_LD_INIT_IN_PROGRESS,
241 	MFI_STAT_LD_LBA_OUT_OF_RANGE,
242 	MFI_STAT_LD_MAX_CONFIGURED,
243 	MFI_STAT_LD_NOT_OPTIMAL,
244 	MFI_STAT_LD_RBLD_IN_PROGRESS,
245 	MFI_STAT_LD_RECON_IN_PROGRESS,
246 	MFI_STAT_LD_WRONG_RAID_LEVEL,
247 	MFI_STAT_MAX_SPARES_EXCEEDED,
248 	MFI_STAT_MEMORY_NOT_AVAILABLE =	0x20,
249 	MFI_STAT_MFC_HW_ERROR,
250 	MFI_STAT_NO_HW_PRESENT,
251 	MFI_STAT_NOT_FOUND,
252 	MFI_STAT_NOT_IN_ENCL,
253 	MFI_STAT_PD_CLEAR_IN_PROGRESS,
254 	MFI_STAT_PD_TYPE_WRONG,
255 	MFI_STAT_PR_DISABLED,
256 	MFI_STAT_ROW_INDEX_INVALID,
257 	MFI_STAT_SAS_CONFIG_INVALID_ACTION,
258 	MFI_STAT_SAS_CONFIG_INVALID_DATA,
259 	MFI_STAT_SAS_CONFIG_INVALID_PAGE,
260 	MFI_STAT_SAS_CONFIG_INVALID_TYPE,
261 	MFI_STAT_SCSI_DONE_WITH_ERROR,
262 	MFI_STAT_SCSI_IO_FAILED,
263 	MFI_STAT_SCSI_RESERVATION_CONFLICT,
264 	MFI_STAT_SHUTDOWN_FAILED =	0x30,
265 	MFI_STAT_TIME_NOT_SET,
266 	MFI_STAT_WRONG_STATE,
267 	MFI_STAT_LD_OFFLINE,
268 	MFI_STAT_PEER_NOTIFICATION_REJECTED,
269 	MFI_STAT_PEER_NOTIFICATION_FAILED,
270 	MFI_STAT_RESERVATION_IN_PROGRESS,
271 	MFI_STAT_I2C_ERRORS_DETECTED,
272 	MFI_STAT_PCI_ERRORS_DETECTED,
273 	MFI_STAT_DIAG_FAILED,
274 	MFI_STAT_BOOT_MSG_PENDING,
275 	MFI_STAT_FOREIGN_CONFIG_INCOMPLETE,
276 	MFI_STAT_INVALID_STATUS =	0xFF
277 } mfi_status_t;
278 
279 typedef enum {
280 	MFI_EVT_CLASS_DEBUG =		-2,
281 	MFI_EVT_CLASS_PROGRESS =	-1,
282 	MFI_EVT_CLASS_INFO =		0,
283 	MFI_EVT_CLASS_WARNING =		1,
284 	MFI_EVT_CLASS_CRITICAL =	2,
285 	MFI_EVT_CLASS_FATAL =		3,
286 	MFI_EVT_CLASS_DEAD =		4
287 } mfi_evt_class_t;
288 
289 typedef enum {
290 	MFI_EVT_LOCALE_LD =		0x0001,
291 	MFI_EVT_LOCALE_PD =		0x0002,
292 	MFI_EVT_LOCALE_ENCL =		0x0004,
293 	MFI_EVT_LOCALE_BBU =		0x0008,
294 	MFI_EVT_LOCALE_SAS =		0x0010,
295 	MFI_EVT_LOCALE_CTRL =		0x0020,
296 	MFI_EVT_LOCALE_CONFIG =		0x0040,
297 	MFI_EVT_LOCALE_CLUSTER =	0x0080,
298 	MFI_EVT_LOCALE_ALL =		0xffff
299 } mfi_evt_locale_t;
300 
301 typedef enum {
302 	MR_EVT_ARGS_NONE =		0x00,
303 	MR_EVT_ARGS_CDB_SENSE,
304 	MR_EVT_ARGS_LD,
305 	MR_EVT_ARGS_LD_COUNT,
306 	MR_EVT_ARGS_LD_LBA,
307 	MR_EVT_ARGS_LD_OWNER,
308 	MR_EVT_ARGS_LD_LBA_PD_LBA,
309 	MR_EVT_ARGS_LD_PROG,
310 	MR_EVT_ARGS_LD_STATE,
311 	MR_EVT_ARGS_LD_STRIP,
312 	MR_EVT_ARGS_PD,
313 	MR_EVT_ARGS_PD_ERR,
314 	MR_EVT_ARGS_PD_LBA,
315 	MR_EVT_ARGS_PD_LBA_LD,
316 	MR_EVT_ARGS_PD_PROG,
317 	MR_EVT_ARGS_PD_STATE,
318 	MR_EVT_ARGS_PCI,
319 	MR_EVT_ARGS_RATE,
320 	MR_EVT_ARGS_STR,
321 	MR_EVT_ARGS_TIME,
322 	MR_EVT_ARGS_ECC
323 } mfi_evt_args;
324 
325 typedef enum {
326 	MR_LD_CACHE_WRITE_BACK =	0x01,
327 	MR_LD_CACHE_WRITE_ADAPTIVE =	0x02,
328 	MR_LD_CACHE_READ_AHEAD =	0x04,
329 	MR_LD_CACHE_READ_ADAPTIVE =	0x08,
330 	MR_LD_CACHE_WRITE_CACHE_BAD_BBU=0x10,
331 	MR_LD_CACHE_ALLOW_WRITE_CACHE =	0x20,
332 	MR_LD_CACHE_ALLOW_READ_CACHE =	0x40
333 } mfi_ld_cache;
334 #define	MR_LD_CACHE_MASK	0x7f
335 
336 #define	MR_LD_CACHE_POLICY_READ_AHEAD_NONE		0
337 #define	MR_LD_CACHE_POLICY_READ_AHEAD_ALWAYS		MR_LD_CACHE_READ_AHEAD
338 #define	MR_LD_CACHE_POLICY_READ_AHEAD_ADAPTIVE		\
339 	(MR_LD_CACHE_READ_AHEAD | MR_LD_CACHE_READ_ADAPTIVE)
340 #define	MR_LD_CACHE_POLICY_WRITE_THROUGH		0
341 #define	MR_LD_CACHE_POLICY_WRITE_BACK			MR_LD_CACHE_WRITE_BACK
342 #define	MR_LD_CACHE_POLICY_IO_CACHED			\
343 	(MR_LD_CACHE_ALLOW_WRITE_CACHE | MR_LD_CACHE_ALLOW_READ_CACHE)
344 #define	MR_LD_CACHE_POLICY_IO_DIRECT			0
345 
346 typedef enum {
347 	MR_PD_CACHE_UNCHANGED  =	0,
348 	MR_PD_CACHE_ENABLE =		1,
349 	MR_PD_CACHE_DISABLE =		2
350 } mfi_pd_cache;
351 
352 /*
353  * Other propertities and definitions
354  */
355 #define MFI_MAX_PD_CHANNELS	2
356 #define MFI_MAX_LD_CHANNELS	2
357 #define MFI_MAX_CHANNELS	(MFI_MAX_PD_CHANNELS + MFI_MAX_LD_CHANNELS)
358 #define MFI_MAX_CHANNEL_DEVS	128
359 #define MFI_DEFAULT_ID		-1
360 #define MFI_MAX_LUN		8
361 #define MFI_MAX_LD		64
362 #define	MFI_MAX_PD		256
363 
364 #define MFI_FRAME_SIZE		64
365 #define MFI_MBOX_SIZE		12
366 
367 /* Firmware flashing can take 40s */
368 #define MFI_POLL_TIMEOUT_SECS	50
369 
370 /* Allow for speedier math calculations */
371 #define MFI_SECTOR_LEN		512
372 
373 /* Scatter Gather elements */
374 struct mfi_sg32 {
375 	uint32_t	addr;
376 	uint32_t	len;
377 } __packed;
378 
379 struct mfi_sg64 {
380 	uint64_t	addr;
381 	uint32_t	len;
382 } __packed;
383 
384 union mfi_sgl {
385 	struct mfi_sg32	sg32[1];
386 	struct mfi_sg64	sg64[1];
387 } __packed;
388 
389 /* Message frames.  All messages have a common header */
390 struct mfi_frame_header {
391 	uint8_t		cmd;
392 	uint8_t		sense_len;
393 	uint8_t		cmd_status;
394 	uint8_t		scsi_status;
395 	uint8_t		target_id;
396 	uint8_t		lun_id;
397 	uint8_t		cdb_len;
398 	uint8_t		sg_count;
399 	uint32_t	context;
400 	uint32_t	pad0;
401 	uint16_t	flags;
402 #define MFI_FRAME_DATAOUT	0x08
403 #define MFI_FRAME_DATAIN	0x10
404 	uint16_t	timeout;
405 	uint32_t	data_len;
406 } __packed;
407 
408 struct mfi_init_frame {
409 	struct mfi_frame_header	header;
410 	uint32_t	qinfo_new_addr_lo;
411 	uint32_t	qinfo_new_addr_hi;
412 	uint32_t	qinfo_old_addr_lo;
413 	uint32_t	qinfo_old_addr_hi;
414 	uint32_t	reserved[6];
415 } __packed;
416 
417 #define MFI_IO_FRAME_SIZE 40
418 struct mfi_io_frame {
419 	struct mfi_frame_header	header;
420 	uint32_t	sense_addr_lo;
421 	uint32_t	sense_addr_hi;
422 	uint32_t	lba_lo;
423 	uint32_t	lba_hi;
424 	union mfi_sgl	sgl;
425 } __packed;
426 
427 #define MFI_PASS_FRAME_SIZE 48
428 struct mfi_pass_frame {
429 	struct mfi_frame_header header;
430 	uint32_t	sense_addr_lo;
431 	uint32_t	sense_addr_hi;
432 	uint8_t		cdb[16];
433 	union mfi_sgl	sgl;
434 } __packed;
435 
436 #define MFI_DCMD_FRAME_SIZE 40
437 struct mfi_dcmd_frame {
438 	struct mfi_frame_header header;
439 	uint32_t	opcode;
440 	uint8_t		mbox[MFI_MBOX_SIZE];
441 	union mfi_sgl	sgl;
442 } __packed;
443 
444 struct mfi_abort_frame {
445 	struct mfi_frame_header header;
446 	uint32_t	abort_context;
447 	uint32_t	pad;
448 	uint32_t	abort_mfi_addr_lo;
449 	uint32_t	abort_mfi_addr_hi;
450 	uint32_t	reserved[6];
451 } __packed;
452 
453 struct mfi_smp_frame {
454 	struct mfi_frame_header header;
455 	uint64_t	sas_addr;
456 	union {
457 		struct mfi_sg32 sg32[2];
458 		struct mfi_sg64 sg64[2];
459 	} sgl;
460 } __packed;
461 
462 struct mfi_stp_frame {
463 	struct mfi_frame_header header;
464 	uint16_t	fis[10];
465 	uint32_t	stp_flags;
466 	union {
467 		struct mfi_sg32 sg32[2];
468 		struct mfi_sg64 sg64[2];
469 	} sgl;
470 } __packed;
471 
472 union mfi_frame {
473 	struct mfi_frame_header header;
474 	struct mfi_init_frame	init;
475 	struct mfi_io_frame	io;
476 	struct mfi_pass_frame	pass;
477 	struct mfi_dcmd_frame	dcmd;
478 	struct mfi_abort_frame	abort;
479 	struct mfi_smp_frame	smp;
480 	struct mfi_stp_frame	stp;
481 	uint8_t			bytes[MFI_FRAME_SIZE];
482 };
483 
484 #define MFI_SENSE_LEN 128
485 struct mfi_sense {
486 	uint8_t		data[MFI_SENSE_LEN];
487 };
488 
489 /* The queue init structure that is passed with the init message */
490 struct mfi_init_qinfo {
491 	uint32_t	flags;
492 	uint32_t	rq_entries;
493 	uint32_t	rq_addr_lo;
494 	uint32_t	rq_addr_hi;
495 	uint32_t	pi_addr_lo;
496 	uint32_t	pi_addr_hi;
497 	uint32_t	ci_addr_lo;
498 	uint32_t	ci_addr_hi;
499 } __packed;
500 
501 /* SAS (?) controller properties, part of mfi_ctrl_info */
502 struct mfi_ctrl_props {
503 	uint16_t	seq_num;
504 	uint16_t	pred_fail_poll_interval;
505 	uint16_t	intr_throttle_cnt;
506 	uint16_t	intr_throttle_timeout;
507 	uint8_t		rebuild_rate;
508 	uint8_t		patrol_read_rate;
509 	uint8_t		bgi_rate;
510 	uint8_t		cc_rate;
511 	uint8_t		recon_rate;
512 	uint8_t		cache_flush_interval;
513 	uint8_t		spinup_drv_cnt;
514 	uint8_t		spinup_delay;
515 	uint8_t		cluster_enable;
516 	uint8_t		coercion_mode;
517 	uint8_t		alarm_enable;
518 	uint8_t		disable_auto_rebuild;
519 	uint8_t		disable_battery_warn;
520 	uint8_t		ecc_bucket_size;
521 	uint16_t	ecc_bucket_leak_rate;
522 	uint8_t		restore_hotspare_on_insertion;
523 	uint8_t		expose_encl_devices;
524 	uint8_t		reserved[38];
525 } __packed;
526 
527 /* PCI information about the card. */
528 struct mfi_info_pci {
529 	uint16_t	vendor;
530 	uint16_t	device;
531 	uint16_t	subvendor;
532 	uint16_t	subdevice;
533 	uint8_t		reserved[24];
534 } __packed;
535 
536 /* Host (front end) interface information */
537 struct mfi_info_host {
538 	uint8_t		type;
539 #define MFI_INFO_HOST_PCIX	0x01
540 #define MFI_INFO_HOST_PCIE	0x02
541 #define MFI_INFO_HOST_ISCSI	0x04
542 #define MFI_INFO_HOST_SAS3G	0x08
543 	uint8_t		reserved[6];
544 	uint8_t		port_count;
545 	uint64_t	port_addr[8];
546 } __packed;
547 
548 /* Device (back end) interface information */
549 struct mfi_info_device {
550 	uint8_t		type;
551 #define MFI_INFO_DEV_SPI	0x01
552 #define MFI_INFO_DEV_SAS3G	0x02
553 #define MFI_INFO_DEV_SATA1	0x04
554 #define MFI_INFO_DEV_SATA3G	0x08
555 	uint8_t		reserved[6];
556 	uint8_t		port_count;
557 	uint64_t	port_addr[8];
558 } __packed;
559 
560 /* Firmware component information */
561 struct mfi_info_component {
562 	char		 name[8];
563 	char		 version[32];
564 	char		 build_date[16];
565 	char		 build_time[16];
566 } __packed;
567 
568 /* Controller default settings */
569 struct mfi_defaults {
570 	uint64_t	sas_addr;
571 	uint8_t		phy_polarity;
572 	uint8_t		background_rate;
573 	uint8_t		stripe_size;
574 	uint8_t		flush_time;
575 	uint8_t		write_back;
576 	uint8_t		read_ahead;
577 	uint8_t		cache_when_bbu_bad;
578 	uint8_t		cached_io;
579 	uint8_t		smart_mode;
580 	uint8_t		alarm_disable;
581 	uint8_t		coercion;
582 	uint8_t		zrc_config;
583 	uint8_t		dirty_led_shows_drive_activity;
584 	uint8_t		bios_continue_on_error;
585 	uint8_t		spindown_mode;
586 	uint8_t		allowed_device_types;
587 	uint8_t		allow_mix_in_enclosure;
588 	uint8_t		allow_mix_in_ld;
589 	uint8_t		allow_sata_in_cluster;
590 	uint8_t		max_chained_enclosures;
591 	uint8_t		disable_ctrl_r;
592 	uint8_t		enabel_web_bios;
593 	uint8_t		phy_polarity_split;
594 	uint8_t		direct_pd_mapping;
595 	uint8_t		bios_enumerate_lds;
596 	uint8_t		restored_hot_spare_on_insertion;
597 	uint8_t		expose_enclosure_devices;
598 	uint8_t		maintain_pd_fail_history;
599 	uint8_t		resv[28];
600 } __packed;
601 
602 /* Controller default settings */
603 struct mfi_bios_data {
604 	uint16_t	boot_target_id;
605 	uint8_t		do_not_int_13;
606 	uint8_t		continue_on_error;
607 	uint8_t		verbose;
608 	uint8_t		geometry;
609 	uint8_t		expose_all_drives;
610 	uint8_t		reserved[56];
611 	uint8_t		check_sum;
612 } __packed;
613 
614 /* SAS (?) controller info, returned from MFI_DCMD_CTRL_GETINFO. */
615 struct mfi_ctrl_info {
616 	struct mfi_info_pci	pci;
617 	struct mfi_info_host	host;
618 	struct mfi_info_device	device;
619 
620 	/* Firmware components that are present and active. */
621 	uint32_t		image_check_word;
622 	uint32_t		image_component_count;
623 	struct mfi_info_component image_component[8];
624 
625 	/* Firmware components that have been flashed but are inactive */
626 	uint32_t		pending_image_component_count;
627 	struct mfi_info_component pending_image_component[8];
628 
629 	uint8_t			max_arms;
630 	uint8_t			max_spans;
631 	uint8_t			max_arrays;
632 	uint8_t			max_lds;
633 	char			product_name[80];
634 	char			serial_number[32];
635 	uint32_t		hw_present;
636 #define MFI_INFO_HW_BBU		0x01
637 #define MFI_INFO_HW_ALARM	0x02
638 #define MFI_INFO_HW_NVRAM	0x04
639 #define MFI_INFO_HW_UART	0x08
640 	uint32_t		current_fw_time;
641 	uint16_t		max_cmds;
642 	uint16_t		max_sg_elements;
643 	uint32_t		max_request_size;
644 	uint16_t		lds_present;
645 	uint16_t		lds_degraded;
646 	uint16_t		lds_offline;
647 	uint16_t		pd_present;
648 	uint16_t		pd_disks_present;
649 	uint16_t		pd_disks_pred_failure;
650 	uint16_t		pd_disks_failed;
651 	uint16_t		nvram_size;
652 	uint16_t		memory_size;
653 	uint16_t		flash_size;
654 	uint16_t		ram_correctable_errors;
655 	uint16_t		ram_uncorrectable_errors;
656 	uint8_t			cluster_allowed;
657 	uint8_t			cluster_active;
658 	uint16_t		max_strips_per_io;
659 
660 	uint32_t		raid_levels;
661 #define MFI_INFO_RAID_0		0x01
662 #define MFI_INFO_RAID_1		0x02
663 #define MFI_INFO_RAID_5		0x04
664 #define MFI_INFO_RAID_1E	0x08
665 #define MFI_INFO_RAID_6		0x10
666 
667 	uint32_t		adapter_ops;
668 #define MFI_INFO_AOPS_RBLD_RATE		0x0001
669 #define MFI_INFO_AOPS_CC_RATE		0x0002
670 #define MFI_INFO_AOPS_BGI_RATE		0x0004
671 #define MFI_INFO_AOPS_RECON_RATE	0x0008
672 #define MFI_INFO_AOPS_PATROL_RATE	0x0010
673 #define MFI_INFO_AOPS_ALARM_CONTROL	0x0020
674 #define MFI_INFO_AOPS_CLUSTER_SUPPORTED	0x0040
675 #define MFI_INFO_AOPS_BBU		0x0080
676 #define MFI_INFO_AOPS_SPANNING_ALLOWED	0x0100
677 #define MFI_INFO_AOPS_DEDICATED_SPARES	0x0200
678 #define MFI_INFO_AOPS_REVERTIBLE_SPARES	0x0400
679 #define MFI_INFO_AOPS_FOREIGN_IMPORT	0x0800
680 #define MFI_INFO_AOPS_SELF_DIAGNOSTIC	0x1000
681 #define MFI_INFO_AOPS_MIXED_ARRAY	0x2000
682 #define MFI_INFO_AOPS_GLOBAL_SPARES	0x4000
683 
684 	uint32_t		ld_ops;
685 #define MFI_INFO_LDOPS_READ_POLICY	0x01
686 #define MFI_INFO_LDOPS_WRITE_POLICY	0x02
687 #define MFI_INFO_LDOPS_IO_POLICY	0x04
688 #define MFI_INFO_LDOPS_ACCESS_POLICY	0x08
689 #define MFI_INFO_LDOPS_DISK_CACHE_POLICY 0x10
690 
691 	struct {
692 		uint8_t		min;
693 		uint8_t		max;
694 		uint8_t		reserved[2];
695 	} __packed stripe_sz_ops;
696 
697 	uint32_t		pd_ops;
698 #define MFI_INFO_PDOPS_FORCE_ONLINE	0x01
699 #define MFI_INFO_PDOPS_FORCE_OFFLINE	0x02
700 #define MFI_INFO_PDOPS_FORCE_REBUILD	0x04
701 
702 	uint32_t		pd_mix_support;
703 #define MFI_INFO_PDMIX_SAS		0x01
704 #define MFI_INFO_PDMIX_SATA		0x02
705 #define MFI_INFO_PDMIX_ENCL		0x04
706 #define MFI_INFO_PDMIX_LD		0x08
707 #define MFI_INFO_PDMIX_SATA_CLUSTER	0x10
708 
709 	uint8_t			ecc_bucket_count;
710 	uint8_t			reserved2[11];
711 	struct mfi_ctrl_props	properties;
712 	char			package_version[0x60];
713 	uint8_t			pad[0x800 - 0x6a0];
714 } __packed;
715 
716 /* keep track of an event. */
717 union mfi_evt {
718 	struct {
719 		uint16_t	locale;
720 		uint8_t		reserved;
721 		int8_t		class;
722 	} members;
723 	uint32_t		word;
724 } __packed;
725 
726 /* event log state. */
727 struct mfi_evt_log_state {
728 	uint32_t		newest_seq_num;
729 	uint32_t		oldest_seq_num;
730 	uint32_t		clear_seq_num;
731 	uint32_t		shutdown_seq_num;
732 	uint32_t		boot_seq_num;
733 } __packed;
734 
735 struct mfi_progress {
736 	uint16_t		progress;
737 	uint16_t		elapsed_seconds;
738 } __packed;
739 
740 struct mfi_evt_ld {
741 	uint16_t		target_id;
742 	uint8_t			ld_index;
743 	uint8_t			reserved;
744 } __packed;
745 
746 struct mfi_evt_pd {
747 	uint16_t		device_id;
748 	uint8_t			enclosure_index;
749 	uint8_t			slot_number;
750 } __packed;
751 
752 /* SAS (?) event detail, returned from MFI_DCMD_CTRL_EVENT_WAIT. */
753 struct mfi_evt_detail {
754 	uint32_t		seq;
755 	uint32_t		time;
756 	uint32_t		code;
757 	union mfi_evt		class;
758 	uint8_t			arg_type;
759 	uint8_t			reserved1[15];
760 
761 	union {
762 		struct {
763 			struct mfi_evt_pd	pd;
764 			uint8_t			cdb_len;
765 			uint8_t			sense_len;
766 			uint8_t			reserved[2];
767 			uint8_t			cdb[16];
768 			uint8_t			sense[64];
769 		} cdb_sense;
770 
771 		struct mfi_evt_ld		ld;
772 
773 		struct {
774 			struct mfi_evt_ld	ld;
775 			uint64_t		count;
776 		} ld_count;
777 
778 		struct {
779 			uint64_t		lba;
780 			struct mfi_evt_ld	ld;
781 		} ld_lba;
782 
783 		struct {
784 			struct mfi_evt_ld	ld;
785 			uint32_t		pre_owner;
786 			uint32_t		new_owner;
787 		} ld_owner;
788 
789 		struct {
790 			uint64_t		ld_lba;
791 			uint64_t		pd_lba;
792 			struct mfi_evt_ld	ld;
793 			struct mfi_evt_pd	pd;
794 		} ld_lba_pd_lba;
795 
796 		struct {
797 			struct mfi_evt_ld	ld;
798 			struct mfi_progress	prog;
799 		} ld_prog;
800 
801 		struct {
802 			struct mfi_evt_ld	ld;
803 			uint32_t		prev_state;
804 			uint32_t		new_state;
805 		} ld_state;
806 
807 		struct {
808 			uint64_t		strip;
809 			struct mfi_evt_ld	ld;
810 		} ld_strip;
811 
812 		struct mfi_evt_pd		pd;
813 
814 		struct {
815 			struct mfi_evt_pd	pd;
816 			uint32_t		err;
817 		} pd_err;
818 
819 		struct {
820 			uint64_t		lba;
821 			struct mfi_evt_pd	pd;
822 		} pd_lba;
823 
824 		struct {
825 			uint64_t		lba;
826 			struct mfi_evt_pd	pd;
827 			struct mfi_evt_ld	ld;
828 		} pd_lba_ld;
829 
830 		struct {
831 			struct mfi_evt_pd	pd;
832 			struct mfi_progress	prog;
833 		} pd_prog;
834 
835 		struct {
836 			struct mfi_evt_pd	ld;
837 			uint32_t		prev_state;
838 			uint32_t		new_state;
839 		} pd_state;
840 
841 		struct {
842 			uint16_t		venderId;
843 			uint16_t		deviceId;
844 			uint16_t		subVenderId;
845 			uint16_t		subDeviceId;
846 		} pci;
847 
848 		uint32_t			rate;
849 
850 		char				str[96];
851 
852 		struct {
853 			uint32_t		rtc;
854 			uint16_t		elapsedSeconds;
855 		} time;
856 
857 		struct {
858 			uint32_t		ecar;
859 			uint32_t		elog;
860 			char			str[64];
861 		} ecc;
862 
863 		uint8_t		b[96];
864 		uint16_t	s[48];
865 		uint32_t	w[24];
866 		uint64_t	d[12];
867 	} args;
868 
869 	char description[128];
870 } __packed;
871 
872 struct mfi_evt_list {
873 	uint32_t		count;
874 	uint32_t		reserved;
875 	struct mfi_evt_detail	event[1];
876 } __packed;
877 
878 union mfi_pd_ref {
879 	struct {
880 		uint16_t	device_id;
881 		uint16_t	seq_num;
882 	} v;
883 	uint32_t	ref;
884 } __packed;
885 
886 union mfi_pd_ddf_type {
887 	struct {
888 		union {
889 			struct {
890 				uint16_t	forced_pd_guid	: 1;
891 				uint16_t	in_vd		: 1;
892 				uint16_t	is_global_spare	: 1;
893 				uint16_t	is_spare	: 1;
894 				uint16_t	is_foreign	: 1;
895 				uint16_t	reserved	: 7;
896 				uint16_t	intf		: 4;
897 			} pd_type;
898 			uint16_t	type;
899 		} v;
900 		uint16_t		reserved;
901 	} ddf;
902 	struct {
903 		uint32_t		reserved;
904 	} non_disk;
905 	uint32_t			type;
906 } __packed;
907 
908 struct mfi_pd_progress {
909 	uint32_t			active;
910 #define	MFI_PD_PROGRESS_REBUILD	(1<<0)
911 #define	MFI_PD_PROGRESS_PATROL	(1<<1)
912 #define	MFI_PD_PROGRESS_CLEAR	(1<<2)
913 	struct mfi_progress		rbld;
914 	struct mfi_progress		patrol;
915 	struct mfi_progress		clear;
916 	struct mfi_progress		reserved[4];
917 } __packed;
918 
919 struct mfi_pd_info {
920 	union mfi_pd_ref		ref;
921 	uint8_t				inquiry_data[96];
922 	uint8_t				vpd_page83[64];
923 	uint8_t				not_supported;
924 	uint8_t				scsi_dev_type;
925 	uint8_t				connected_port_bitmap;
926 	uint8_t				device_speed;
927 	uint32_t			media_err_count;
928 	uint32_t			other_err_count;
929 	uint32_t			pred_fail_count;
930 	uint32_t			last_pred_fail_event_seq_num;
931 	uint16_t			fw_state;	/* MFI_PD_STATE_* */
932 	uint8_t				disabled_for_removal;
933 	uint8_t				link_speed;
934 	union mfi_pd_ddf_type		state;
935 	struct {
936 		uint8_t			count;
937 		uint8_t			is_path_broken;
938 		uint8_t			reserved[6];
939 		uint64_t		sas_addr[4];
940 	} path_info;
941 	uint64_t			raw_size;
942 	uint64_t			non_coerced_size;
943 	uint64_t			coerced_size;
944 	uint16_t			encl_device_id;
945 	uint8_t				encl_index;
946 	uint8_t				slot_number;
947 	struct mfi_pd_progress		prog_info;
948 	uint8_t				bad_block_table_full;
949 	uint8_t				unusable_in_current_config;
950 	uint8_t				vpd_page83_ext[64];
951 	uint8_t				reserved[512-358];
952 } __packed;
953 
954 struct mfi_pd_address {
955 	uint16_t		device_id;
956 	uint16_t		encl_device_id;
957 	uint8_t			encl_index;
958 	uint8_t			slot_number;
959 	uint8_t			scsi_dev_type;	/* 0 = disk */
960 	uint8_t			connect_port_bitmap;
961 	uint64_t		sas_addr[2];
962 } __packed;
963 
964 struct mfi_pd_list {
965 	uint32_t		size;
966 	uint32_t		count;
967 	struct mfi_pd_address	addr[0];
968 } __packed;
969 
970 enum mfi_pd_state {
971 	MFI_PD_STATE_UNCONFIGURED_GOOD = 0x00,
972 	MFI_PD_STATE_UNCONFIGURED_BAD = 0x01,
973 	MFI_PD_STATE_HOT_SPARE = 0x02,
974 	MFI_PD_STATE_OFFLINE = 0x10,
975 	MFI_PD_STATE_FAILED = 0x11,
976 	MFI_PD_STATE_REBUILD = 0x14,
977 	MFI_PD_STATE_ONLINE = 0x18,
978 	MFI_PD_STATE_COPYBACK = 0x20,
979 	MFI_PD_STATE_SYSTEM = 0x40
980 };
981 
982 union mfi_ld_ref {
983 	struct {
984 		uint8_t		target_id;
985 		uint8_t		reserved;
986 		uint16_t	seq;
987 	} v;
988 	uint32_t		ref;
989 } __packed;
990 
991 struct mfi_ld_list {
992 	uint32_t		ld_count;
993 	uint32_t		reserved1;
994 	struct {
995 		union mfi_ld_ref	ld;
996 		uint8_t		state;
997 		uint8_t		reserved2[3];
998 		uint64_t	size;
999 	} ld_list[MFI_MAX_LD];
1000 } __packed;
1001 
1002 enum mfi_ld_access {
1003 	MFI_LD_ACCESS_RW =	0,
1004 	MFI_LD_ACCSSS_RO = 	2,
1005 	MFI_LD_ACCESS_BLOCKED =	3,
1006 };
1007 #define MFI_LD_ACCESS_MASK	3
1008 
1009 enum mfi_ld_state {
1010 	MFI_LD_STATE_OFFLINE =			0,
1011 	MFI_LD_STATE_PARTIALLY_DEGRADED =	1,
1012 	MFI_LD_STATE_DEGRADED =			2,
1013 	MFI_LD_STATE_OPTIMAL =			3
1014 };
1015 
1016 struct mfi_ld_props {
1017 	union mfi_ld_ref	ld;
1018 	char			name[16];
1019 	uint8_t			default_cache_policy;
1020 	uint8_t			access_policy;
1021 	uint8_t			disk_cache_policy;
1022 	uint8_t			current_cache_policy;
1023 	uint8_t			no_bgi;
1024 	uint8_t			reserved[7];
1025 } __packed;
1026 
1027 struct mfi_ld_params {
1028 	uint8_t			primary_raid_level;
1029 	uint8_t			raid_level_qualifier;
1030 	uint8_t			secondary_raid_level;
1031 	uint8_t			stripe_size;
1032 	uint8_t			num_drives;
1033 	uint8_t			span_depth;
1034 	uint8_t			state;
1035 	uint8_t			init_state;
1036 #define	MFI_LD_PARAMS_INIT_NO		0
1037 #define	MFI_LD_PARAMS_INIT_QUICK	1
1038 #define	MFI_LD_PARAMS_INIT_FULL		2
1039 	uint8_t			is_consistent;
1040 	uint8_t			reserved[23];
1041 } __packed;
1042 
1043 struct mfi_ld_progress {
1044 	uint32_t		active;
1045 #define	MFI_LD_PROGRESS_CC	(1<<0)
1046 #define	MFI_LD_PROGRESS_BGI	(1<<1)
1047 #define	MFI_LD_PROGRESS_FGI	(1<<2)
1048 #define	MFI_LD_PROGRESS_RECON	(1<<3)
1049 	struct mfi_progress	cc;
1050 	struct mfi_progress	bgi;
1051 	struct mfi_progress	fgi;
1052 	struct mfi_progress	recon;
1053 	struct mfi_progress	reserved[4];
1054 } __packed;
1055 
1056 struct mfi_span {
1057 	uint64_t		start_block;
1058 	uint64_t		num_blocks;
1059 	uint16_t		array_ref;
1060 	uint8_t			reserved[6];
1061 } __packed;
1062 
1063 #define	MFI_MAX_SPAN_DEPTH	8
1064 struct mfi_ld_config {
1065 	struct mfi_ld_props	properties;
1066 	struct mfi_ld_params	params;
1067 	struct mfi_span		span[MFI_MAX_SPAN_DEPTH];
1068 } __packed;
1069 
1070 struct mfi_ld_info {
1071 	struct mfi_ld_config	ld_config;
1072 	uint64_t		size;
1073 	struct mfi_ld_progress	progress;
1074 	uint16_t		cluster_owner;
1075 	uint8_t			reconstruct_active;
1076 	uint8_t			reserved1[1];
1077 	uint8_t			vpd_page83[64];
1078 	uint8_t			reserved2[16];
1079 } __packed;
1080 
1081 #define MAX_ARRAYS 16
1082 struct mfi_spare {
1083 	union mfi_pd_ref	ref;
1084 	uint8_t			spare_type;
1085 #define	MFI_SPARE_DEDICATED	(1 << 0)
1086 #define	MFI_SPARE_REVERTIBLE	(1 << 1)
1087 #define	MFI_SPARE_ENCL_AFFINITY	(1 << 2)
1088 	uint8_t			reserved[2];
1089 	uint8_t			array_count;
1090 	uint16_t		array_ref[MAX_ARRAYS];
1091 } __packed;
1092 
1093 struct mfi_array {
1094 	uint64_t			size;
1095 	uint8_t				num_drives;
1096 	uint8_t				reserved;
1097 	uint16_t			array_ref;
1098 	uint8_t				pad[20];
1099 	struct {
1100 		union mfi_pd_ref	ref;	/* 0xffff == missing drive */
1101 		uint16_t		fw_state;	/* MFI_PD_STATE_* */
1102 		struct {
1103 			uint8_t		pd;
1104 			uint8_t		slot;
1105 		} encl;
1106 	} pd[0];
1107 } __packed;
1108 
1109 struct mfi_config_data {
1110 	uint32_t		size;
1111 	uint16_t		array_count;
1112 	uint16_t		array_size;
1113 	uint16_t		log_drv_count;
1114 	uint16_t		log_drv_size;
1115 	uint16_t		spares_count;
1116 	uint16_t		spares_size;
1117 	uint8_t			reserved[16];
1118 	struct mfi_array	array[0];
1119 	struct mfi_ld_config	ld[0];
1120 	struct mfi_spare	spare[0];
1121 } __packed;
1122 
1123 struct mfi_bbu_capacity_info {
1124 	uint16_t		relative_charge;
1125 	uint16_t		absolute_charge;
1126 	uint16_t		remaining_capacity;
1127 	uint16_t		full_charge_capacity;
1128 	uint16_t		run_time_to_empty;
1129 	uint16_t		average_time_to_empty;
1130 	uint16_t		average_time_to_full;
1131 	uint16_t		cycle_count;
1132 	uint16_t		max_error;
1133 	uint16_t		remaining_capacity_alarm;
1134 	uint16_t		remaining_time_alarm;
1135 	uint8_t			reserved[26];
1136 } __packed;
1137 
1138 struct mfi_bbu_design_info {
1139 	uint32_t		mfg_date;
1140 	uint16_t		design_capacity;
1141 	uint16_t		design_voltage;
1142 	uint16_t		spec_info;
1143 	uint16_t		serial_number;
1144 	uint16_t		pack_stat_config;
1145 	uint8_t			mfg_name[12];
1146 	uint8_t			device_name[8];
1147 	uint8_t			device_chemistry[8];
1148 	uint8_t			mfg_data[8];
1149 	uint8_t			reserved[17];
1150 } __packed;
1151 
1152 struct mfi_ibbu_state {
1153 	uint16_t		gas_guage_status;
1154 	uint16_t		relative_charge;
1155 	uint16_t		charger_system_state;
1156 	uint16_t		charger_system_ctrl;
1157 	uint16_t		charging_current;
1158 	uint16_t		absolute_charge;
1159 	uint16_t		max_error;
1160 	uint8_t			reserved[18];
1161 } __packed;
1162 
1163 struct mfi_bbu_state {
1164 	uint16_t		gas_guage_status;
1165 	uint16_t		relative_charge;
1166 	uint16_t		charger_status;
1167 	uint16_t		remaining_capacity;
1168 	uint16_t		full_charge_capacity;
1169 	uint8_t			is_SOH_good;
1170 	uint8_t			reserved[21];
1171 } __packed;
1172 
1173 union mfi_bbu_status_detail {
1174 	struct mfi_ibbu_state	ibbu;
1175 	struct mfi_bbu_state	bbu;
1176 };
1177 
1178 struct mfi_bbu_status {
1179 	uint8_t			battery_type;
1180 #define	MFI_BBU_TYPE_NONE	0
1181 #define	MFI_BBU_TYPE_IBBU	1
1182 #define	MFI_BBU_TYPE_BBU	2
1183 	uint8_t			reserved;
1184 	uint16_t		voltage;
1185 	int16_t			current;
1186 	uint16_t		temperature;
1187 	uint32_t		fw_status;
1188 #define	MFI_BBU_STATE_PACK_MISSING	(1 << 0)
1189 #define	MFI_BBU_STATE_VOLTAGE_LOW	(1 << 1)
1190 #define	MFI_BBU_STATE_TEMPERATURE_HIGH	(1 << 2)
1191 #define	MFI_BBU_STATE_CHARGE_ACTIVE	(1 << 0)
1192 #define	MFI_BBU_STATE_DISCHARGE_ACTIVE	(1 << 0)
1193 	uint8_t			pad[20];
1194 	union mfi_bbu_status_detail detail;
1195 } __packed;
1196 
1197 enum mfi_pr_state {
1198 	MFI_PR_STATE_STOPPED = 0,
1199 	MFI_PR_STATE_READY = 1,
1200 	MFI_PR_STATE_ACTIVE = 2,
1201 	MFI_PR_STATE_ABORTED = 0xff
1202 };
1203 
1204 struct mfi_pr_status {
1205 	uint32_t		num_iteration;
1206 	uint8_t			state;
1207 	uint8_t			num_pd_done;
1208 	uint8_t			reserved[10];
1209 };
1210 
1211 enum mfi_pr_opmode {
1212 	MFI_PR_OPMODE_AUTO = 0,
1213 	MFI_PR_OPMODE_MANUAL = 1,
1214 	MFI_PR_OPMODE_DISABLED = 2
1215 };
1216 
1217 struct mfi_pr_properties {
1218 	uint8_t			op_mode;
1219 	uint8_t			max_pd;
1220 	uint8_t			reserved;
1221 	uint8_t			exclude_ld_count;
1222 	uint16_t		excluded_ld[MFI_MAX_LD];
1223 	uint8_t			cur_pd_map[MFI_MAX_PD / 8];
1224 	uint8_t			last_pd_map[MFI_MAX_PD / 8];
1225 	uint32_t		next_exec;
1226 	uint32_t		exec_freq;
1227 	uint32_t		clear_freq;
1228 };
1229 
1230 #define MFI_SCSI_MAX_TARGETS	128
1231 #define MFI_SCSI_MAX_LUNS	8
1232 #define MFI_SCSI_INITIATOR_ID	255
1233 #define MFI_SCSI_MAX_CMDS	8
1234 #define MFI_SCSI_MAX_CDB_LEN	16
1235 
1236 #endif /* _MFIREG_H */
1237