Initial import from FreeBSD RELENG_4:
[dragonfly.git] / sys / dev / raid / mlx / mlxreg.h
1 /*-
2  * Copyright (c) 1999 Michael Smith
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  *      $FreeBSD: src/sys/dev/mlx/mlxreg.h,v 1.5.2.3 2001/06/25 04:37:51 msmith Exp $
27  */
28
29 #define MLX_BLKSIZE     512             /* fixed feature */
30
31 /*
32  * Selected command codes.
33  */
34 #define MLX_CMD_ENQUIRY_OLD     0x05
35 #define MLX_CMD_ENQUIRY         0x53
36 #define MLX_CMD_ENQUIRY2        0x1c
37 #define MLX_CMD_ENQSYSDRIVE     0x19
38 #define MLX_CMD_READSG          0xb6
39 #define MLX_CMD_WRITESG         0xb7
40 #define MLX_CMD_READSG_OLD      0x82
41 #define MLX_CMD_WRITESG_OLD     0x83
42 #define MLX_CMD_FLUSH           0x0a
43 #define MLX_CMD_LOGOP           0x72
44 #define MLX_CMD_REBUILDASYNC    0x16
45 #define MLX_CMD_CHECKASYNC      0x1e
46 #define MLX_CMD_REBUILDSTAT     0x0c
47 #define MLX_CMD_STOPCHANNEL     0x13
48 #define MLX_CMD_STARTCHANNEL    0x12
49 #define MLX_CMD_READ_CONFIG     0x4e
50 #define MLX_CMD_DIRECT_CDB      0x04
51 #define MLX_CMD_DEVICE_STATE    0x50
52
53 #ifdef _KERNEL
54
55 #define MLX_CFG_BASE0   0x10            /* first region */
56 #define MLX_CFG_BASE1   0x14            /* second region (type 3 only) */
57
58 /*
59  * Status values.
60  */
61 #define MLX_STATUS_OK           0x0000
62 #define MLX_STATUS_RDWROFFLINE  0x0002  /* read/write claims drive is offline */
63 #define MLX_STATUS_WEDGED       0xdead  /* controller not listening */
64 #define MLX_STATUS_LOST         0xbeef  /* never came back */
65 #define MLX_STATUS_BUSY         0xffff  /* command is in controller */
66
67 /*
68  * Accessor defines for the V3 interface.
69  */
70 #define MLX_V3_MAILBOX          0x00
71 #define MLX_V3_STATUS_IDENT     0x0d
72 #define MLX_V3_STATUS           0x0e
73 #define MLX_V3_IDBR             0x40
74 #define MLX_V3_ODBR             0x41
75 #define MLX_V3_IER              0x43
76 #define MLX_V3_FWERROR          0x3f
77 #define MLX_V3_FWERROR_PARAM1   0x00
78 #define MLX_V3_FWERROR_PARAM2   0x01
79
80 #define MLX_V3_PUT_MAILBOX(sc, idx, val) bus_space_write_1(sc->mlx_btag, sc->mlx_bhandle, MLX_V3_MAILBOX + idx, val)
81 #define MLX_V3_GET_STATUS_IDENT(sc)      bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V3_STATUS_IDENT)
82 #define MLX_V3_GET_STATUS(sc)            bus_space_read_2 (sc->mlx_btag, sc->mlx_bhandle, MLX_V3_STATUS)
83 #define MLX_V3_GET_IDBR(sc)              bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V3_IDBR)
84 #define MLX_V3_PUT_IDBR(sc, val)         bus_space_write_1(sc->mlx_btag, sc->mlx_bhandle, MLX_V3_IDBR, val)
85 #define MLX_V3_GET_ODBR(sc)              bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V3_ODBR)
86 #define MLX_V3_PUT_ODBR(sc, val)         bus_space_write_1(sc->mlx_btag, sc->mlx_bhandle, MLX_V3_ODBR, val)
87 #define MLX_V3_PUT_IER(sc, val)          bus_space_write_1(sc->mlx_btag, sc->mlx_bhandle, MLX_V3_IER, val)
88 #define MLX_V3_GET_FWERROR(sc)           bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V3_FWERROR)
89 #define MLX_V3_PUT_FWERROR(sc, val)      bus_space_write_1(sc->mlx_btag, sc->mlx_bhandle, MLX_V3_FWERROR, val)
90 #define MLX_V3_GET_FWERROR_PARAM1(sc)    bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V3_FWERROR_PARAM1)
91 #define MLX_V3_GET_FWERROR_PARAM2(sc)    bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V3_FWERROR_PARAM2)
92
93 #define MLX_V3_IDB_FULL         (1<<0)          /* mailbox is full */
94 #define MLX_V3_IDB_INIT_BUSY    (1<<1)          /* initialisation in progress */
95
96 #define MLX_V3_IDB_SACK         (1<<1)          /* acknowledge status read */
97
98 #define MLX_V3_ODB_SAVAIL       (1<<0)          /* status is available */
99
100 #define MLX_V3_FWERROR_PEND     (1<<2)          /* firmware error pending */
101
102 /*
103  * Accessor defines for the V4 interface.
104  */
105 #define MLX_V4_MAILBOX          0x1000
106 #define MLX_V4_MAILBOX_LENGTH           16
107 #define MLX_V4_STATUS_IDENT     0x1018
108 #define MLX_V4_STATUS           0x101a
109 #define MLX_V4_IDBR             0x0020
110 #define MLX_V4_ODBR             0x002c
111 #define MLX_V4_IER              0x0034
112 #define MLX_V4_FWERROR          0x103f
113 #define MLX_V4_FWERROR_PARAM1   0x1000
114 #define MLX_V4_FWERROR_PARAM2   0x1001
115
116 /* use longword access? */
117 #define MLX_V4_PUT_MAILBOX(sc, idx, val) bus_space_write_1(sc->mlx_btag, sc->mlx_bhandle, MLX_V4_MAILBOX + idx, val)
118 #define MLX_V4_GET_STATUS_IDENT(sc)      bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V4_STATUS_IDENT)
119 #define MLX_V4_GET_STATUS(sc)            bus_space_read_2 (sc->mlx_btag, sc->mlx_bhandle, MLX_V4_STATUS)
120 #define MLX_V4_GET_IDBR(sc)              bus_space_read_4 (sc->mlx_btag, sc->mlx_bhandle, MLX_V4_IDBR)
121 #define MLX_V4_PUT_IDBR(sc, val)         bus_space_write_4(sc->mlx_btag, sc->mlx_bhandle, MLX_V4_IDBR, val)
122 #define MLX_V4_GET_ODBR(sc)              bus_space_read_4 (sc->mlx_btag, sc->mlx_bhandle, MLX_V4_ODBR)
123 #define MLX_V4_PUT_ODBR(sc, val)         bus_space_write_4(sc->mlx_btag, sc->mlx_bhandle, MLX_V4_ODBR, val)
124 #define MLX_V4_PUT_IER(sc, val)          bus_space_write_4(sc->mlx_btag, sc->mlx_bhandle, MLX_V4_IER, val)
125 #define MLX_V4_GET_FWERROR(sc)           bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V4_FWERROR)
126 #define MLX_V4_PUT_FWERROR(sc, val)      bus_space_write_1(sc->mlx_btag, sc->mlx_bhandle, MLX_V4_FWERROR, val)
127 #define MLX_V4_GET_FWERROR_PARAM1(sc)    bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V4_FWERROR_PARAM1)
128 #define MLX_V4_GET_FWERROR_PARAM2(sc)    bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V4_FWERROR_PARAM2)
129
130 #define MLX_V4_IDB_FULL         (1<<0)          /* mailbox is full */
131 #define MLX_V4_IDB_INIT_BUSY    (1<<1)          /* initialisation in progress */
132
133 #define MLX_V4_IDB_HWMBOX_CMD   (1<<0)          /* posted hardware mailbox command */
134 #define MLX_V4_IDB_SACK         (1<<1)          /* acknowledge status read */
135 #define MLX_V4_IDB_MEMMBOX_CMD  (1<<4)          /* posted memory mailbox command */
136
137 #define MLX_V4_ODB_HWSAVAIL     (1<<0)          /* status is available for hardware mailbox */
138 #define MLX_V4_ODB_MEMSAVAIL    (1<<1)          /* status is available for memory mailbox */
139
140 #define MLX_V4_ODB_HWMBOX_ACK   (1<<0)          /* ack status read from hardware mailbox */
141 #define MLX_V4_ODB_MEMMBOX_ACK  (1<<1)          /* ack status read from memory mailbox */
142
143 #define MLX_V4_IER_MASK         0xfb            /* message unit interrupt mask */
144 #define MLX_V4_IER_DISINT       (1<<2)          /* interrupt disable bit */
145
146 #define MLX_V4_FWERROR_PEND     (1<<2)          /* firmware error pending */
147
148 /*
149  * Accessor defines for the V5 interface
150  */
151 #define MLX_V5_MAILBOX          0x50
152 #define MLX_V5_MAILBOX_LENGTH           16
153 #define MLX_V5_STATUS_IDENT     0x5d
154 #define MLX_V5_STATUS           0x5e
155 #define MLX_V5_IDBR             0x60
156 #define MLX_V5_ODBR             0x61
157 #define MLX_V5_IER              0x34
158 #define MLX_V5_FWERROR          0x63
159 #define MLX_V5_FWERROR_PARAM1   0x50
160 #define MLX_V5_FWERROR_PARAM2   0x51
161
162 #define MLX_V5_PUT_MAILBOX(sc, idx, val) bus_space_write_1(sc->mlx_btag, sc->mlx_bhandle, MLX_V5_MAILBOX + idx, val)
163 #define MLX_V5_GET_STATUS_IDENT(sc)      bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V5_STATUS_IDENT)
164 #define MLX_V5_GET_STATUS(sc)            bus_space_read_2 (sc->mlx_btag, sc->mlx_bhandle, MLX_V5_STATUS)
165 #define MLX_V5_GET_IDBR(sc)              bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V5_IDBR)
166 #define MLX_V5_PUT_IDBR(sc, val)         bus_space_write_1(sc->mlx_btag, sc->mlx_bhandle, MLX_V5_IDBR, val)
167 #define MLX_V5_GET_ODBR(sc)              bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V5_ODBR)
168 #define MLX_V5_PUT_ODBR(sc, val)         bus_space_write_1(sc->mlx_btag, sc->mlx_bhandle, MLX_V5_ODBR, val)
169 #define MLX_V5_PUT_IER(sc, val)          bus_space_write_1(sc->mlx_btag, sc->mlx_bhandle, MLX_V5_IER, val)
170 #define MLX_V5_GET_FWERROR(sc)           bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V5_FWERROR)
171 #define MLX_V5_PUT_FWERROR(sc, val)      bus_space_write_1(sc->mlx_btag, sc->mlx_bhandle, MLX_V5_FWERROR, val)
172 #define MLX_V5_GET_FWERROR_PARAM1(sc)    bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V5_FWERROR_PARAM1)
173 #define MLX_V5_GET_FWERROR_PARAM2(sc)    bus_space_read_1 (sc->mlx_btag, sc->mlx_bhandle, MLX_V5_FWERROR_PARAM2)
174
175 #define MLX_V5_IDB_EMPTY        (1<<0)          /* mailbox is empty */
176 #define MLX_V5_IDB_INIT_DONE    (1<<1)          /* initialisation has completed */
177
178 #define MLX_V5_IDB_HWMBOX_CMD   (1<<0)          /* posted hardware mailbox command */
179 #define MLX_V5_IDB_SACK         (1<<1)          /* acknowledge status read */
180 #define MLX_V5_IDB_RESET        (1<<3)          /* reset request */
181 #define MLX_V5_IDB_MEMMBOX_CMD  (1<<4)          /* posted memory mailbox command */
182
183 #define MLX_V5_ODB_HWSAVAIL     (1<<0)          /* status is available for hardware mailbox */
184 #define MLX_V5_ODB_MEMSAVAIL    (1<<1)          /* status is available for memory mailbox */
185
186 #define MLX_V5_ODB_HWMBOX_ACK   (1<<0)          /* ack status read from hardware mailbox */
187 #define MLX_V5_ODB_MEMMBOX_ACK  (1<<1)          /* ack status read from memory mailbox */
188
189 #define MLX_V5_IER_DISINT       (1<<2)          /* interrupt disable bit */
190
191 #define MLX_V5_FWERROR_PEND     (1<<2)          /* firmware error pending */
192
193 #endif /* _KERNEL */
194
195 /*
196  * Scatter-gather list format, type 1, kind 00.
197  */
198 struct mlx_sgentry 
199 {
200     u_int32_t   sg_addr;
201     u_int32_t   sg_count;
202 } __attribute__ ((packed));
203
204 /*
205  * Command result buffers, as placed in system memory by the controller.
206  */
207
208 struct mlx_enquiry_old  /* MLX_CMD_ENQUIRY_OLD */
209 {
210     u_int8_t            me_num_sys_drvs;
211     u_int8_t            res1[3];
212     u_int32_t           me_drvsize[8];
213     u_int16_t           me_flash_age;
214     u_int8_t            me_status_flags;
215     u_int8_t            me_free_state_change_count;
216     u_int8_t            me_fwminor;
217     u_int8_t            me_fwmajor;
218     u_int8_t            me_rebuild_flag;
219     u_int8_t            me_max_commands;
220     u_int8_t            me_offline_sd_count;
221     u_int8_t            res3;
222     u_int8_t            me_critical_sd_count;
223     u_int8_t            res4[3];
224     u_int8_t            me_dead_count;
225     u_int8_t            res5;
226     u_int8_t            me_rebuild_count;
227     u_int8_t            me_misc_flags;
228     struct 
229     {
230         u_int8_t        dd_targ;
231         u_int8_t        dd_chan;
232     } __attribute__ ((packed)) me_dead[20];
233 } __attribute__ ((packed));
234
235 struct mlx_enquiry      /* MLX_CMD_ENQUIRY */
236 {
237     u_int8_t            me_num_sys_drvs;
238     u_int8_t            res1[3];
239     u_int32_t           me_drvsize[32];
240     u_int16_t           me_flash_age;
241     u_int8_t            me_status_flags;
242 #define MLX_ENQ_SFLAG_DEFWRERR  (1<<0)  /* deferred write error indicator */
243 #define MLX_ENQ_SFLAG_BATTLOW   (1<<1)  /* battery low */
244     u_int8_t            res2;
245     u_int8_t            me_fwminor;
246     u_int8_t            me_fwmajor;
247     u_int8_t            me_rebuild_flag;
248     u_int8_t            me_max_commands;
249     u_int8_t            me_offline_sd_count;
250     u_int8_t            res3;
251     u_int16_t           me_event_log_seq_num;
252     u_int8_t            me_critical_sd_count;
253     u_int8_t            res4[3];
254     u_int8_t            me_dead_count;
255     u_int8_t            res5;
256     u_int8_t            me_rebuild_count;
257     u_int8_t            me_misc_flags;
258 #define MLX_ENQ_MISC_BBU        (1<<3)  /* battery backup present */
259     struct 
260     {
261         u_int8_t        dd_targ;
262         u_int8_t        dd_chan;
263     } __attribute__ ((packed)) me_dead[20];
264 } __attribute__ ((packed));
265
266 struct mlx_enquiry2     /* MLX_CMD_ENQUIRY2 */
267 {
268     u_int32_t           me_hardware_id;
269     u_int32_t           me_firmware_id;
270     u_int32_t           res1;
271     u_int8_t            me_configured_channels;
272     u_int8_t            me_actual_channels;
273     u_int8_t            me_max_targets;
274     u_int8_t            me_max_tags;
275     u_int8_t            me_max_sys_drives;
276     u_int8_t            me_max_arms;
277     u_int8_t            me_max_spans;
278     u_int8_t            res2;
279     u_int32_t           res3;
280     u_int32_t           me_mem_size;
281     u_int32_t           me_cache_size;
282     u_int32_t           me_flash_size;
283     u_int32_t           me_nvram_size;
284     u_int16_t           me_mem_type;
285     u_int16_t           me_clock_speed;
286     u_int16_t           me_mem_speed;
287     u_int16_t           me_hardware_speed;
288     u_int8_t            res4[12];
289     u_int16_t           me_max_commands;
290     u_int16_t           me_max_sg;
291     u_int16_t           me_max_dp;
292     u_int16_t           me_max_iod;
293     u_int16_t           me_max_comb;
294     u_int8_t            me_latency;
295     u_int8_t            res5;
296     u_int8_t            me_scsi_timeout;
297     u_int8_t            res6;
298     u_int16_t           me_min_freelines;
299     u_int8_t            res7[8];
300     u_int8_t            me_rate_const;
301     u_int8_t            res8[11];
302     u_int16_t           me_physblk;
303     u_int16_t           me_logblk;
304     u_int16_t           me_maxblk;
305     u_int16_t           me_blocking_factor;
306     u_int16_t           me_cacheline;
307     u_int8_t            me_scsi_cap;
308     u_int8_t            res9[5];
309     u_int16_t           me_firmware_build;
310     u_int8_t            me_fault_mgmt_type;
311     u_int8_t            res10;
312     u_int32_t           me_firmware_features;
313     u_int8_t            res11[8];
314 } __attribute__ ((packed));
315
316 struct mlx_enq_sys_drive /* MLX_CMD_ENQSYSDRIVE returns an array of 32 of these */
317 {
318     u_int32_t           sd_size;
319     u_int8_t            sd_state;
320     u_int8_t            sd_raidlevel;
321     u_int16_t           res1;
322 } __attribute__ ((packed));
323
324 struct mlx_eventlog_entry       /* MLX_CMD_LOGOP/MLX_LOGOP_GET */
325 {
326     u_int8_t            el_type;
327     u_int8_t            el_length;
328     u_char              el_target:5;
329     u_char              el_channel:3;
330     u_char              el_lun:6;
331     u_char              res1:2;
332     u_int16_t           el_seqno;
333     u_char              el_errorcode:7;
334     u_char              el_valid:1;
335     u_int8_t            el_segment;
336     u_char              el_sensekey:4;
337     u_char              res2:1;
338     u_char              el_ILI:1;
339     u_char              el_EOM:1;
340     u_char              el_filemark:1;
341     u_int8_t            el_information[4];
342     u_int8_t            el_addsense;
343     u_int8_t            el_csi[4];
344     u_int8_t            el_asc;
345     u_int8_t            el_asq;
346     u_int8_t            res3[12];
347 } __attribute__ ((packed));
348
349 #define MLX_LOGOP_GET           0x00    /* operation codes for MLX_CMD_LOGOP */
350 #define MLX_LOGMSG_SENSE        0x00    /* log message contents codes */
351
352 struct mlx_rebuild_stat /* MLX_CMD_REBUILDSTAT */
353 {
354     u_int32_t   rb_drive;
355     u_int32_t   rb_size;
356     u_int32_t   rb_remaining;
357 } __attribute__ ((packed));
358
359 struct mlx_config2
360 {
361     u_int16_t   cf_flags1;
362 #define MLX_CF2_ACTV_NEG        (1<<1)
363 #define MLX_CF2_NORSTRTRY       (1<<7)
364 #define MLX_CF2_STRGWRK         (1<<8)
365 #define MLX_CF2_HPSUPP          (1<<9)
366 #define MLX_CF2_NODISCN         (1<<10)
367 #define MLX_CF2_ARM             (1<<13)
368 #define MLX_CF2_OFM             (1<<15)
369 #define MLX_CF2_AEMI (MLX_CF2_ARM | MLX_CF2_OFM)
370     u_int8_t    cf_oemid;
371     u_int8_t    cf_oem_model;
372     u_int8_t    cf_physical_sector;
373     u_int8_t    cf_logical_sector;
374     u_int8_t    cf_blockfactor;
375     u_int8_t    cf_flags2;
376 #define MLX_CF2_READAH          (1<<0)
377 #define MLX_CF2_BIOSDLY         (1<<1)
378 #define MLX_CF2_REASS1S         (1<<4)
379 #define MLX_CF2_FUAENABL        (1<<6)
380 #define MLX_CF2_R5ALLS          (1<<7)
381     u_int8_t    cf_rcrate;
382     u_int8_t    cf_res1;
383     u_int8_t    cf_blocks_per_cache_line;
384     u_int8_t    cf_blocks_per_stripe;
385     u_int8_t    cf_scsi_param_0;
386     u_int8_t    cf_scsi_param_1;
387     u_int8_t    cf_scsi_param_2;
388     u_int8_t    cf_scsi_param_3;
389     u_int8_t    cf_scsi_param_4;
390     u_int8_t    cf_scsi_param_5;
391     u_int8_t    cf_scsi_initiator_id;    
392     u_int8_t    cf_res2;
393     u_int8_t    cf_startup_mode;
394     u_int8_t    cf_simultaneous_spinup_devices;
395     u_int8_t    cf_delay_between_spinups;
396     u_int8_t    cf_res3;
397     u_int16_t   cf_checksum;
398 } __attribute__ ((packed));
399
400 struct mlx_sys_drv_span
401 {
402     u_int32_t   sp_start_lba;
403     u_int32_t   sp_nblks;
404     u_int8_t    sp_arm[8];
405 } __attribute__ ((packed));
406
407 struct mlx_sys_drv
408 {
409     u_int8_t    sd_status;
410     u_int8_t    sd_ext_status;
411     u_int8_t    sd_mod1;
412     u_int8_t    sd_mod2;
413     u_int8_t    sd_raidlevel;
414 #define MLX_SYS_DRV_WRITEBACK   (1<<7)
415 #define MLX_SYS_DRV_RAID0       0
416 #define MLX_SYS_DRV_RAID1       1
417 #define MLX_SYS_DRV_RAID3       3
418 #define MLX_SYS_DRV_RAID5       5
419 #define MLX_SYS_DRV_RAID6       6
420 #define MLX_SYS_DRV_JBOD        7
421     u_int8_t    sd_valid_arms;
422     u_int8_t    sd_valid_spans;
423     u_int8_t    sd_init_state;
424 #define MLX_SYS_DRV_INITTED     0x81;
425     struct mlx_sys_drv_span sd_span[4];
426 } __attribute__ ((packed));
427
428 struct mlx_phys_drv
429 {
430     u_int8_t    pd_flags1;
431 #define MLX_PHYS_DRV_PRESENT    (1<<0)
432     u_int8_t    pd_flags2;
433 #define MLX_PHYS_DRV_OTHER      0x00
434 #define MLX_PHYS_DRV_DISK       0x01
435 #define MLX_PHYS_DRV_SEQUENTIAL 0x02
436 #define MLX_PHYS_DRV_CDROM      0x03
437 #define MLX_PHYS_DRV_FAST20     (1<<3)
438 #define MLX_PHYS_DRV_SYNC       (1<<4)
439 #define MLX_PHYS_DRV_FAST       (1<<5)
440 #define MLX_PHYS_DRV_WIDE       (1<<6)
441 #define MLX_PHYS_DRV_TAG        (1<<7)
442     u_int8_t    pd_status;
443 #define MLX_PHYS_DRV_DEAD       0x00
444 #define MLX_PHYS_DRV_WRONLY     0x02
445 #define MLX_PHYS_DRV_ONLINE     0x03
446 #define MLX_PHYS_DRV_STANDBY    0x10
447     u_int8_t    pd_res1;
448     u_int8_t    pd_period;
449     u_int8_t    pd_offset;
450     u_int32_t   pd_config_size;
451 } __attribute__ ((packed));
452
453 struct mlx_core_cfg
454 {
455     u_int8_t    cc_num_sys_drives;
456     u_int8_t    cc_res1[3];
457     struct mlx_sys_drv  cc_sys_drives[32];
458     struct mlx_phys_drv cc_phys_drives[5 * 16];
459 } __attribute__ ((packed));
460
461 struct mlx_dcdb
462 {
463     u_int8_t    dcdb_target:4;
464     u_int8_t    dcdb_channel:4;
465     u_int8_t    dcdb_flags;
466 #define MLX_DCDB_NO_DATA        0x00
467 #define MLX_DCDB_DATA_IN        0x01
468 #define MLX_DCDB_DATA_OUT       0x02
469 #define MLX_DCDB_EARLY_STATUS           (1<<2)
470 #define MLX_DCDB_TIMEOUT_10S    0x10
471 #define MLX_DCDB_TIMEOUT_60S    0x20
472 #define MLX_DCDB_TIMEOUT_20M    0x30
473 #define MLX_DCDB_TIMEOUT_24H    0x40
474 #define MLX_DCDB_NO_AUTO_SENSE  (1<<6)
475 #define MLX_DCDB_DISCONNECT     (1<<7)
476     u_int16_t   dcdb_datasize;
477     u_int32_t   dcdb_physaddr;
478     u_int8_t    dcdb_cdb_length:4;
479     u_int8_t    dcdb_datasize_high:4;
480     u_int8_t    dcdb_sense_length;
481     u_int8_t    dcdb_cdb[12];
482     u_int8_t    dcdb_sense[64];
483     u_int8_t    dcdb_status;
484     u_int8_t    res1;
485 } __attribute__ ((packed));
486
487 struct mlx_bbtable_entry 
488 {
489     u_int32_t   bbt_block_number;
490     u_int8_t    bbt_extent;
491     u_int8_t    res1;
492     u_int8_t    bbt_entry_type;
493     u_int8_t    bbt_system_drive:5;
494     u_int8_t    res2:3;
495 } __attribute__ ((packed));
496
497 #ifdef _KERNEL
498 /*
499  * Inlines to build various command structures
500  */
501 static __inline void
502 mlx_make_type1(struct mlx_command *mc,
503                u_int8_t code, 
504                u_int16_t f1,
505                u_int32_t f2,
506                u_int8_t f3,
507                u_int32_t f4,
508                u_int8_t f5) 
509 {
510     mc->mc_mailbox[0x0] = code;
511     mc->mc_mailbox[0x2] = f1 & 0xff;
512     mc->mc_mailbox[0x3] = (((f2 >> 24) & 0x3) << 6) | ((f1 >> 8) & 0x3f);
513     mc->mc_mailbox[0x4] = f2 & 0xff;
514     mc->mc_mailbox[0x5] = (f2 >> 8) & 0xff;
515     mc->mc_mailbox[0x6] = (f2 >> 16) & 0xff;
516     mc->mc_mailbox[0x7] = f3;
517     mc->mc_mailbox[0x8] = f4 & 0xff;
518     mc->mc_mailbox[0x9] = (f4 >> 8) & 0xff;
519     mc->mc_mailbox[0xa] = (f4 >> 16) & 0xff;
520     mc->mc_mailbox[0xb] = (f4 >> 24) & 0xff;
521     mc->mc_mailbox[0xc] = f5;
522 }
523
524 static __inline void
525 mlx_make_type2(struct mlx_command *mc,
526                u_int8_t code, 
527                u_int8_t f1,
528                u_int8_t f2,
529                u_int8_t f3,
530                u_int8_t f4,
531                u_int8_t f5,
532                u_int8_t f6,
533                u_int32_t f7,
534                u_int8_t f8)
535 {
536     mc->mc_mailbox[0x0] = code;
537     mc->mc_mailbox[0x2] = f1;
538     mc->mc_mailbox[0x3] = f2;
539     mc->mc_mailbox[0x4] = f3;
540     mc->mc_mailbox[0x5] = f4;
541     mc->mc_mailbox[0x6] = f5;
542     mc->mc_mailbox[0x7] = f6;
543     mc->mc_mailbox[0x8] = f7 & 0xff;
544     mc->mc_mailbox[0x9] = (f7 >> 8) & 0xff;
545     mc->mc_mailbox[0xa] = (f7 >> 16) & 0xff;
546     mc->mc_mailbox[0xb] = (f7 >> 24) & 0xff;
547     mc->mc_mailbox[0xc] = f8;
548 }
549
550 static __inline void
551 mlx_make_type3(struct mlx_command *mc,
552                u_int8_t code, 
553                u_int8_t f1,
554                u_int8_t f2,
555                u_int16_t f3,
556                u_int8_t f4,
557                u_int8_t f5,
558                u_int32_t f6,
559                u_int8_t f7)
560 {
561     mc->mc_mailbox[0x0] = code;
562     mc->mc_mailbox[0x2] = f1;
563     mc->mc_mailbox[0x3] = f2;
564     mc->mc_mailbox[0x4] = f3 & 0xff;
565     mc->mc_mailbox[0x5] = (f3 >> 8) & 0xff;
566     mc->mc_mailbox[0x6] = f4;
567     mc->mc_mailbox[0x7] = f5;
568     mc->mc_mailbox[0x8] = f6 & 0xff;
569     mc->mc_mailbox[0x9] = (f6 >> 8) & 0xff;
570     mc->mc_mailbox[0xa] = (f6 >> 16) & 0xff;
571     mc->mc_mailbox[0xb] = (f6 >> 24) & 0xff;
572     mc->mc_mailbox[0xc] = f7;
573 }
574
575 static __inline void
576 mlx_make_type4(struct mlx_command *mc,
577                u_int8_t code, 
578                u_int16_t f1,
579                u_int32_t f2,
580                u_int32_t f3,
581                u_int8_t f4)
582 {
583     mc->mc_mailbox[0x0] = code;
584     mc->mc_mailbox[0x2] = f1 & 0xff;
585     mc->mc_mailbox[0x3] = (f1 >> 8) & 0xff;
586     mc->mc_mailbox[0x4] = f2 & 0xff;
587     mc->mc_mailbox[0x5] = (f2 >> 8) & 0xff;
588     mc->mc_mailbox[0x6] = (f2 >> 16) & 0xff;
589     mc->mc_mailbox[0x7] = (f2 >> 24) & 0xff;
590     mc->mc_mailbox[0x8] = f3 & 0xff;
591     mc->mc_mailbox[0x9] = (f3 >> 8) & 0xff;
592     mc->mc_mailbox[0xa] = (f3 >> 16) & 0xff;
593     mc->mc_mailbox[0xb] = (f3 >> 24) & 0xff;
594     mc->mc_mailbox[0xc] = f4;
595 }
596
597 static __inline void
598 mlx_make_type5(struct mlx_command *mc,
599                u_int8_t code, 
600                u_int8_t f1,
601                u_int8_t f2,
602                u_int32_t f3,
603                u_int32_t f4,
604                u_int8_t f5)
605 {
606     mc->mc_mailbox[0x0] = code;
607     mc->mc_mailbox[0x2] = f1;
608     mc->mc_mailbox[0x3] = f2;
609     mc->mc_mailbox[0x4] = f3 & 0xff;
610     mc->mc_mailbox[0x5] = (f3 >> 8) & 0xff;
611     mc->mc_mailbox[0x6] = (f3 >> 16) & 0xff;
612     mc->mc_mailbox[0x7] = (f3 >> 24) & 0xff;
613     mc->mc_mailbox[0x8] = f4 & 0xff;
614     mc->mc_mailbox[0x9] = (f4 >> 8) & 0xff;
615     mc->mc_mailbox[0xa] = (f4 >> 16) & 0xff;
616     mc->mc_mailbox[0xb] = (f4 >> 24) & 0xff;
617     mc->mc_mailbox[0xc] = f5;
618 }
619
620 #endif /* _KERNEL */