1 /*
2  * CDDL HEADER START
3  *
4  * The contents of this file are subject to the terms of the
5  * Common Development and Distribution License (the "License").
6  * You may not use this file except in compliance with the License.
7  *
8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9  * or http://www.opensolaris.org/os/licensing.
10  * See the License for the specific language governing permissions
11  * and limitations under the License.
12  *
13  * When distributing Covered Code, include this CDDL HEADER in each
14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15  * If applicable, add the following below this CDDL HEADER, with the
16  * fields enclosed by brackets "[]" replaced with your own identifying
17  * information: Portions Copyright [yyyy] [name of copyright owner]
18  *
19  * CDDL HEADER END
20  */
21 
22 /*
23  * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
24  * Use is subject to license terms.
25  */
26 
27 /*
28  * Copyright (c) 2000 to 2009, LSI Corporation.
29  * All rights reserved.
30  *
31  * Redistribution and use in source and binary forms of all code within
32  * this file that is exclusively owned by LSI, with or without
33  * modification, is permitted provided that, in addition to the CDDL 1.0
34  * License requirements, the following conditions are met:
35  *
36  *    Neither the name of the author nor the names of its contributors may be
37  *    used to endorse or promote products derived from this software without
38  *    specific prior written permission.
39  *
40  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
41  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
42  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
43  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
44  * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
45  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
46  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
47  * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
48  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
49  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
50  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
51  * DAMAGE.
52  */
53 
54 /*
55  * mptsas - This is a driver based on LSI Logic's MPT2.0 interface.
56  *
57  */
58 
59 #if defined(lint) || defined(DEBUG)
60 #define	MPTSAS_DEBUG
61 #endif
62 
63 /*
64  * standard header files.
65  */
66 #include <sys/note.h>
67 #include <sys/scsi/scsi.h>
68 #include <sys/pci.h>
69 #include <sys/file.h>
70 #include <sys/policy.h>
71 #include <sys/sysevent.h>
72 #include <sys/sysevent/eventdefs.h>
73 #include <sys/sysevent/dr.h>
74 #include <sys/sata/sata_defs.h>
75 
76 #pragma pack(1)
77 #include <sys/scsi/adapters/mpt_sas/mpi/mpi2_type.h>
78 #include <sys/scsi/adapters/mpt_sas/mpi/mpi2.h>
79 #include <sys/scsi/adapters/mpt_sas/mpi/mpi2_cnfg.h>
80 #include <sys/scsi/adapters/mpt_sas/mpi/mpi2_init.h>
81 #include <sys/scsi/adapters/mpt_sas/mpi/mpi2_ioc.h>
82 #include <sys/scsi/adapters/mpt_sas/mpi/mpi2_sas.h>
83 #pragma pack()
84 
85 /*
86  * private header files.
87  *
88  */
89 #include <sys/scsi/impl/scsi_reset_notify.h>
90 #include <sys/scsi/adapters/mpt_sas/mptsas_var.h>
91 #include <sys/scsi/adapters/mpt_sas/mptsas_ioctl.h>
92 #include <sys/raidioctl.h>
93 
94 #include <sys/fs/dv_node.h>	/* devfs_clean */
95 
96 /*
97  * FMA header files
98  */
99 #include <sys/ddifm.h>
100 #include <sys/fm/protocol.h>
101 #include <sys/fm/util.h>
102 #include <sys/fm/io/ddi.h>
103 
104 /*
105  * autoconfiguration data and routines.
106  */
107 static int mptsas_attach(dev_info_t *dip, ddi_attach_cmd_t cmd);
108 static int mptsas_detach(dev_info_t *devi, ddi_detach_cmd_t cmd);
109 static int mptsas_power(dev_info_t *dip, int component, int level);
110 
111 /*
112  * cb_ops function
113  */
114 static int mptsas_ioctl(dev_t dev, int cmd, intptr_t data, int mode,
115 	cred_t *credp, int *rval);
116 #ifndef	__sparc
117 static int mptsas_quiesce(dev_info_t *devi);
118 #endif	/* __sparc */
119 
120 /*
121  * Resource initilaization for hardware
122  */
123 static void mptsas_setup_cmd_reg(mptsas_t *mpt);
124 static void mptsas_disable_bus_master(mptsas_t *mpt);
125 static void mptsas_hba_fini(mptsas_t *mpt);
126 static void mptsas_cfg_fini(mptsas_t *mptsas_blkp);
127 static int mptsas_alloc_request_frames(mptsas_t *mpt);
128 static int mptsas_alloc_reply_frames(mptsas_t *mpt);
129 static int mptsas_alloc_free_queue(mptsas_t *mpt);
130 static int mptsas_alloc_post_queue(mptsas_t *mpt);
131 static int mptsas_alloc_extra_sgl_frame(mptsas_t *mpt, mptsas_cmd_t *cmd);
132 static void mptsas_free_extra_sgl_frame(mptsas_t *mpt, mptsas_cmd_t *cmd);
133 
134 /*
135  * SCSA function prototypes
136  */
137 static int mptsas_scsi_start(struct scsi_address *ap, struct scsi_pkt *pkt);
138 static int mptsas_scsi_reset(struct scsi_address *ap, int level);
139 static int mptsas_scsi_abort(struct scsi_address *ap, struct scsi_pkt *pkt);
140 static int mptsas_scsi_getcap(struct scsi_address *ap, char *cap, int tgtonly);
141 static int mptsas_scsi_setcap(struct scsi_address *ap, char *cap, int value,
142     int tgtonly);
143 static void mptsas_scsi_dmafree(struct scsi_address *ap, struct scsi_pkt *pkt);
144 static struct scsi_pkt *mptsas_scsi_init_pkt(struct scsi_address *ap,
145     struct scsi_pkt *pkt, struct buf *bp, int cmdlen, int statuslen,
146 	int tgtlen, int flags, int (*callback)(), caddr_t arg);
147 static void mptsas_scsi_sync_pkt(struct scsi_address *ap, struct scsi_pkt *pkt);
148 static void mptsas_scsi_destroy_pkt(struct scsi_address *ap,
149     struct scsi_pkt *pkt);
150 static int mptsas_scsi_tgt_init(dev_info_t *hba_dip, dev_info_t *tgt_dip,
151     scsi_hba_tran_t *hba_tran, struct scsi_device *sd);
152 static void mptsas_scsi_tgt_free(dev_info_t *hba_dip, dev_info_t *tgt_dip,
153     scsi_hba_tran_t *hba_tran, struct scsi_device *sd);
154 static int mptsas_scsi_reset_notify(struct scsi_address *ap, int flag,
155     void (*callback)(caddr_t), caddr_t arg);
156 static int mptsas_get_name(struct scsi_device *sd, char *name, int len);
157 static int mptsas_get_bus_addr(struct scsi_device *sd, char *name, int len);
158 static int mptsas_scsi_quiesce(dev_info_t *dip);
159 static int mptsas_scsi_unquiesce(dev_info_t *dip);
160 static int mptsas_bus_config(dev_info_t *pdip, uint_t flags,
161     ddi_bus_config_op_t op, void *arg, dev_info_t **childp);
162 
163 /*
164  * SMP functions
165  */
166 static int mptsas_smp_start(struct smp_pkt *smp_pkt);
167 static int mptsas_getcap(struct sas_addr *ap, char *cap);
168 static int mptsas_capchk(char *cap, int tgtonly, int *cidxp);
169 
170 /*
171  * internal function prototypes.
172  */
173 static int mptsas_quiesce_bus(mptsas_t *mpt);
174 static int mptsas_unquiesce_bus(mptsas_t *mpt);
175 
176 static int mptsas_alloc_handshake_msg(mptsas_t *mpt, size_t alloc_size);
177 static void mptsas_free_handshake_msg(mptsas_t *mpt);
178 
179 static void mptsas_ncmds_checkdrain(void *arg);
180 
181 static int mptsas_prepare_pkt(mptsas_cmd_t *cmd);
182 static int mptsas_accept_pkt(mptsas_t *mpt, mptsas_cmd_t *sp);
183 static int mptsas_accept_txwq_and_pkt(mptsas_t *mpt, mptsas_cmd_t *sp);
184 static void mptsas_accept_tx_waitq(mptsas_t *mpt);
185 
186 static int mptsas_do_detach(dev_info_t *dev);
187 static int mptsas_do_scsi_reset(mptsas_t *mpt, uint16_t devhdl);
188 static int mptsas_do_scsi_abort(mptsas_t *mpt, int target, int lun,
189     struct scsi_pkt *pkt);
190 
191 static void mptsas_handle_qfull(mptsas_t *mpt, mptsas_cmd_t *cmd);
192 static void mptsas_handle_event(void *args);
193 static int mptsas_handle_event_sync(void *args);
194 static void mptsas_handle_dr(void *args);
195 static void mptsas_handle_topo_change(mptsas_topo_change_list_t *topo_node,
196     dev_info_t *pdip);
197 
198 static void mptsas_restart_cmd(void *);
199 
200 static void mptsas_flush_hba(mptsas_t *mpt);
201 static void mptsas_flush_target(mptsas_t *mpt, ushort_t target, int lun,
202 	uint8_t tasktype);
203 static void mptsas_set_pkt_reason(mptsas_t *mpt, mptsas_cmd_t *cmd,
204     uchar_t reason, uint_t stat);
205 
206 static uint_t mptsas_intr(caddr_t arg1, caddr_t arg2);
207 static void mptsas_process_intr(mptsas_t *mpt,
208     pMpi2ReplyDescriptorsUnion_t reply_desc_union);
209 static void mptsas_handle_scsi_io_success(mptsas_t *mpt,
210     pMpi2ReplyDescriptorsUnion_t reply_desc);
211 static void mptsas_handle_address_reply(mptsas_t *mpt,
212     pMpi2ReplyDescriptorsUnion_t reply_desc);
213 static int mptsas_wait_intr(mptsas_t *mpt, int polltime);
214 static void mptsas_sge_setup(mptsas_t *mpt, mptsas_cmd_t *cmd,
215     uint32_t *control, pMpi2SCSIIORequest_t frame, ddi_acc_handle_t acc_hdl);
216 
217 static void mptsas_watch(void *arg);
218 static void mptsas_watchsubr(mptsas_t *mpt);
219 static void mptsas_cmd_timeout(mptsas_t *mpt, uint16_t devhdl);
220 
221 static void mptsas_start_passthru(mptsas_t *mpt, mptsas_cmd_t *cmd);
222 static int mptsas_do_passthru(mptsas_t *mpt, uint8_t *request, uint8_t *reply,
223     uint8_t *data, uint32_t request_size, uint32_t reply_size,
224     uint32_t data_size, uint32_t direction, uint8_t *dataout,
225     uint32_t dataout_size, short timeout, int mode);
226 static int mptsas_free_devhdl(mptsas_t *mpt, uint16_t devhdl);
227 
228 static int mptsas_pkt_alloc_extern(mptsas_t *mpt, mptsas_cmd_t *cmd,
229     int cmdlen, int tgtlen, int statuslen, int kf);
230 static void mptsas_pkt_destroy_extern(mptsas_t *mpt, mptsas_cmd_t *cmd);
231 
232 static int mptsas_kmem_cache_constructor(void *buf, void *cdrarg, int kmflags);
233 static void mptsas_kmem_cache_destructor(void *buf, void *cdrarg);
234 
235 static int mptsas_cache_frames_constructor(void *buf, void *cdrarg,
236     int kmflags);
237 static void mptsas_cache_frames_destructor(void *buf, void *cdrarg);
238 
239 static void mptsas_check_scsi_io_error(mptsas_t *mpt, pMpi2SCSIIOReply_t reply,
240     mptsas_cmd_t *cmd);
241 static void mptsas_check_task_mgt(mptsas_t *mpt,
242     pMpi2SCSIManagementReply_t reply, mptsas_cmd_t *cmd);
243 static int mptsas_send_scsi_cmd(mptsas_t *mpt, struct scsi_address *ap,
244     mptsas_target_t *ptgt, uchar_t *cdb, int cdblen, struct buf *data_bp,
245     int *resid);
246 
247 static int mptsas_alloc_active_slots(mptsas_t *mpt, int flag);
248 static int mptsas_start_cmd(mptsas_t *mpt, mptsas_cmd_t *cmd);
249 
250 static void mptsas_restart_hba(mptsas_t *mpt);
251 static void mptsas_restart_waitq(mptsas_t *mpt);
252 
253 static void mptsas_deliver_doneq_thread(mptsas_t *mpt);
254 static void mptsas_doneq_add(mptsas_t *mpt, mptsas_cmd_t *cmd);
255 static void mptsas_doneq_mv(mptsas_t *mpt, uint64_t t);
256 
257 static mptsas_cmd_t *mptsas_doneq_thread_rm(mptsas_t *mpt, uint64_t t);
258 static void mptsas_doneq_empty(mptsas_t *mpt);
259 static void mptsas_doneq_thread(mptsas_doneq_thread_arg_t *arg);
260 
261 static mptsas_cmd_t *mptsas_waitq_rm(mptsas_t *mpt);
262 static void mptsas_waitq_delete(mptsas_t *mpt, mptsas_cmd_t *cmd);
263 static mptsas_cmd_t *mptsas_tx_waitq_rm(mptsas_t *mpt);
264 static void mptsas_tx_waitq_delete(mptsas_t *mpt, mptsas_cmd_t *cmd);
265 
266 
267 static void mptsas_start_watch_reset_delay();
268 static void mptsas_setup_bus_reset_delay(mptsas_t *mpt);
269 static void mptsas_watch_reset_delay(void *arg);
270 static int mptsas_watch_reset_delay_subr(mptsas_t *mpt);
271 
272 /*
273  * helper functions
274  */
275 static void mptsas_dump_cmd(mptsas_t *mpt, mptsas_cmd_t *cmd);
276 
277 static dev_info_t *mptsas_find_child(dev_info_t *pdip, char *name);
278 static dev_info_t *mptsas_find_child_phy(dev_info_t *pdip, uint8_t phy);
279 static dev_info_t *mptsas_find_child_addr(dev_info_t *pdip, uint64_t sasaddr,
280     int lun);
281 static mdi_pathinfo_t *mptsas_find_path_addr(dev_info_t *pdip, uint64_t sasaddr,
282     int lun);
283 static mdi_pathinfo_t *mptsas_find_path_phy(dev_info_t *pdip, uint8_t phy);
284 static dev_info_t *mptsas_find_smp_child(dev_info_t *pdip, char *str_wwn);
285 
286 static int mptsas_parse_address(char *name, uint64_t *wwid, uint8_t *phy,
287     int *lun);
288 static int mptsas_parse_smp_name(char *name, uint64_t *wwn);
289 
290 static mptsas_target_t *mptsas_phy_to_tgt(dev_info_t *pdip, uint8_t phy);
291 static mptsas_target_t *mptsas_wwid_to_ptgt(mptsas_t *mpt, int port,
292     uint64_t wwid);
293 static mptsas_smp_t *mptsas_wwid_to_psmp(mptsas_t *mpt, int port,
294     uint64_t wwid);
295 
296 static int mptsas_inquiry(mptsas_t *mpt, mptsas_target_t *ptgt, int lun,
297     uchar_t page, unsigned char *buf, int len, int *rlen, uchar_t evpd);
298 
299 static int mptsas_get_target_device_info(mptsas_t *mpt, uint32_t page_address,
300     uint16_t *handle, mptsas_target_t **pptgt);
301 static void mptsas_update_phymask(mptsas_t *mpt);
302 
303 /*
304  * Enumeration / DR functions
305  */
306 static void mptsas_config_all(dev_info_t *pdip);
307 static int mptsas_config_one_addr(dev_info_t *pdip, uint64_t sasaddr, int lun,
308     dev_info_t **lundip);
309 static int mptsas_config_one_phy(dev_info_t *pdip, uint8_t phy, int lun,
310     dev_info_t **lundip);
311 
312 static int mptsas_config_target(dev_info_t *pdip, mptsas_target_t *ptgt);
313 static int mptsas_offline_target(dev_info_t *pdip, char *name);
314 
315 static int mptsas_config_raid(dev_info_t *pdip, uint16_t target,
316     dev_info_t **dip);
317 
318 static int mptsas_config_luns(dev_info_t *pdip, mptsas_target_t *ptgt);
319 static int mptsas_probe_lun(dev_info_t *pdip, int lun,
320     dev_info_t **dip, mptsas_target_t *ptgt);
321 
322 static int mptsas_create_lun(dev_info_t *pdip, struct scsi_inquiry *sd_inq,
323     dev_info_t **dip, mptsas_target_t *ptgt, int lun);
324 
325 static int mptsas_create_phys_lun(dev_info_t *pdip, struct scsi_inquiry *sd,
326     char *guid, dev_info_t **dip, mptsas_target_t *ptgt, int lun);
327 static int mptsas_create_virt_lun(dev_info_t *pdip, struct scsi_inquiry *sd,
328     char *guid, dev_info_t **dip, mdi_pathinfo_t **pip, mptsas_target_t *ptgt,
329     int lun);
330 
331 static void mptsas_offline_missed_luns(dev_info_t *pdip,
332     uint16_t *repluns, int lun_cnt, mptsas_target_t *ptgt);
333 static int mptsas_offline_lun(dev_info_t *pdip, dev_info_t *rdip,
334     mdi_pathinfo_t *rpip, uint_t flags);
335 
336 static int mptsas_config_smp(dev_info_t *pdip, uint64_t sas_wwn,
337     dev_info_t **smp_dip);
338 static int mptsas_offline_smp(dev_info_t *pdip, mptsas_smp_t *smp_node,
339     uint_t flags);
340 
341 static int mptsas_event_query(mptsas_t *mpt, mptsas_event_query_t *data,
342     int mode, int *rval);
343 static int mptsas_event_enable(mptsas_t *mpt, mptsas_event_enable_t *data,
344     int mode, int *rval);
345 static int mptsas_event_report(mptsas_t *mpt, mptsas_event_report_t *data,
346     int mode, int *rval);
347 static void mptsas_record_event(void *args);
348 
349 static void mptsas_hash_init(mptsas_hash_table_t *hashtab);
350 static void mptsas_hash_uninit(mptsas_hash_table_t *hashtab, size_t datalen);
351 static void mptsas_hash_add(mptsas_hash_table_t *hashtab, void *data);
352 static void * mptsas_hash_rem(mptsas_hash_table_t *hashtab, uint64_t key1,
353     uint8_t key2);
354 static void * mptsas_hash_search(mptsas_hash_table_t *hashtab, uint64_t key1,
355     uint8_t key2);
356 static void * mptsas_hash_traverse(mptsas_hash_table_t *hashtab, int pos);
357 
358 mptsas_target_t *mptsas_tgt_alloc(mptsas_hash_table_t *, uint16_t, uint64_t,
359     uint32_t, uint8_t, uint8_t);
360 static mptsas_smp_t *mptsas_smp_alloc(mptsas_hash_table_t *hashtab,
361     mptsas_smp_t *data);
362 static void mptsas_smp_free(mptsas_hash_table_t *hashtab, uint64_t wwid,
363     uint8_t physport);
364 static void mptsas_tgt_free(mptsas_hash_table_t *, uint64_t, uint8_t);
365 static void * mptsas_search_by_devhdl(mptsas_hash_table_t *, uint16_t);
366 static int mptsas_online_smp(dev_info_t *pdip, mptsas_smp_t *smp_node,
367     dev_info_t **smp_dip);
368 
369 /*
370  * Power management functions
371  */
372 static void mptsas_idle_pm(void *arg);
373 static int mptsas_init_pm(mptsas_t *mpt);
374 
375 /*
376  * MPT MSI tunable:
377  *
378  * By default MSI is enabled on all supported platforms.
379  */
380 boolean_t mptsas_enable_msi = B_TRUE;
381 
382 static int mptsas_add_intrs(mptsas_t *, int);
383 static void mptsas_rem_intrs(mptsas_t *);
384 
385 /*
386  * FMA Prototypes
387  */
388 static void mptsas_fm_init(mptsas_t *mpt);
389 static void mptsas_fm_fini(mptsas_t *mpt);
390 static int mptsas_fm_error_cb(dev_info_t *, ddi_fm_error_t *, const void *);
391 
392 extern pri_t minclsyspri, maxclsyspri;
393 
394 /*
395  * This device is created by the SCSI pseudo nexus driver (SCSI vHCI).  It is
396  * under this device that the paths to a physical device are created when
397  * MPxIO is used.
398  */
399 extern dev_info_t	*scsi_vhci_dip;
400 
401 /*
402  * Tunable timeout value for Inquiry VPD page 0x83
403  * By default the value is 30 seconds.
404  */
405 int mptsas_inq83_retry_timeout = 30;
406 
407 /*
408  * This is used to allocate memory for message frame storage, not for
409  * data I/O DMA. All message frames must be stored in the first 4G of
410  * physical memory.
411  */
412 ddi_dma_attr_t mptsas_dma_attrs = {
413 	DMA_ATTR_V0,	/* attribute layout version		*/
414 	0x0ull,		/* address low - should be 0 (longlong)	*/
415 	0xffffffffull,	/* address high - 32-bit max range	*/
416 	0x00ffffffull,	/* count max - max DMA object size	*/
417 	4,		/* allocation alignment requirements	*/
418 	0x78,		/* burstsizes - binary encoded values	*/
419 	1,		/* minxfer - gran. of DMA engine	*/
420 	0x00ffffffull,	/* maxxfer - gran. of DMA engine	*/
421 	0xffffffffull,	/* max segment size (DMA boundary)	*/
422 	MPTSAS_MAX_DMA_SEGS, /* scatter/gather list length	*/
423 	512,		/* granularity - device transfer size	*/
424 	0		/* flags, set to 0			*/
425 };
426 
427 /*
428  * This is used for data I/O DMA memory allocation. (full 64-bit DMA
429  * physical addresses are supported.)
430  */
431 ddi_dma_attr_t mptsas_dma_attrs64 = {
432 	DMA_ATTR_V0,	/* attribute layout version		*/
433 	0x0ull,		/* address low - should be 0 (longlong)	*/
434 	0xffffffffffffffffull,	/* address high - 64-bit max	*/
435 	0x00ffffffull,	/* count max - max DMA object size	*/
436 	4,		/* allocation alignment requirements	*/
437 	0x78,		/* burstsizes - binary encoded values	*/
438 	1,		/* minxfer - gran. of DMA engine	*/
439 	0x00ffffffull,	/* maxxfer - gran. of DMA engine	*/
440 	0xffffffffull,	/* max segment size (DMA boundary)	*/
441 	MPTSAS_MAX_DMA_SEGS, /* scatter/gather list length	*/
442 	512,		/* granularity - device transfer size	*/
443 	DDI_DMA_RELAXED_ORDERING	/* flags, enable relaxed ordering */
444 };
445 
446 ddi_device_acc_attr_t mptsas_dev_attr = {
447 	DDI_DEVICE_ATTR_V0,
448 	DDI_STRUCTURE_LE_ACC,
449 	DDI_STRICTORDER_ACC
450 };
451 
452 static struct cb_ops mptsas_cb_ops = {
453 	scsi_hba_open,		/* open */
454 	scsi_hba_close,		/* close */
455 	nodev,			/* strategy */
456 	nodev,			/* print */
457 	nodev,			/* dump */
458 	nodev,			/* read */
459 	nodev,			/* write */
460 	mptsas_ioctl,		/* ioctl */
461 	nodev,			/* devmap */
462 	nodev,			/* mmap */
463 	nodev,			/* segmap */
464 	nochpoll,		/* chpoll */
465 	ddi_prop_op,		/* cb_prop_op */
466 	NULL,			/* streamtab */
467 	D_MP,			/* cb_flag */
468 	CB_REV,			/* rev */
469 	nodev,			/* aread */
470 	nodev			/* awrite */
471 };
472 
473 static struct dev_ops mptsas_ops = {
474 	DEVO_REV,		/* devo_rev, */
475 	0,			/* refcnt  */
476 	ddi_no_info,		/* info */
477 	nulldev,		/* identify */
478 	nulldev,		/* probe */
479 	mptsas_attach,		/* attach */
480 	mptsas_detach,		/* detach */
481 	nodev,			/* reset */
482 	&mptsas_cb_ops,		/* driver operations */
483 	NULL,			/* bus operations */
484 	mptsas_power,		/* power management */
485 #ifdef	__sparc
486 	ddi_quiesce_not_needed
487 #else
488 	mptsas_quiesce		/* quiesce */
489 #endif	/* __sparc */
490 };
491 
492 
493 #define	MPTSAS_MOD_STRING "MPTSAS HBA Driver 00.00.00.18"
494 #define	CDATE "MPTSAS was compiled on "__DATE__
495 /* LINTED E_STATIC_UNUSED */
496 static char *MPTWASCOMPILEDON = CDATE;
497 
498 static struct modldrv modldrv = {
499 	&mod_driverops,	/* Type of module. This one is a driver */
500 	MPTSAS_MOD_STRING, /* Name of the module. */
501 	&mptsas_ops,	/* driver ops */
502 };
503 
504 static struct modlinkage modlinkage = {
505 	MODREV_1, &modldrv, NULL
506 };
507 #define	TARGET_PROP	"target"
508 #define	LUN_PROP	"lun"
509 #define	SAS_PROP	"sas-mpt"
510 #define	MDI_GUID	"wwn"
511 #define	NDI_GUID	"guid"
512 #define	MPTSAS_DEV_GONE	"mptsas_dev_gone"
513 
514 /*
515  * Local static data
516  */
517 #if defined(MPTSAS_DEBUG)
518 uint32_t mptsas_debug_flags = 0;
519 #endif	/* defined(MPTSAS_DEBUG) */
520 uint32_t mptsas_debug_resets = 0;
521 
522 static kmutex_t		mptsas_global_mutex;
523 static void		*mptsas_state;		/* soft	state ptr */
524 static krwlock_t	mptsas_global_rwlock;
525 
526 static kmutex_t		mptsas_log_mutex;
527 static char		mptsas_log_buf[256];
528 _NOTE(MUTEX_PROTECTS_DATA(mptsas_log_mutex, mptsas_log_buf))
529 
530 static mptsas_t *mptsas_head, *mptsas_tail;
531 static clock_t mptsas_scsi_watchdog_tick;
532 static clock_t mptsas_tick;
533 static timeout_id_t mptsas_reset_watch;
534 static timeout_id_t mptsas_timeout_id;
535 static int mptsas_timeouts_enabled = 0;
536 
537 /*
538  * warlock directives
539  */
540 _NOTE(SCHEME_PROTECTS_DATA("unique per pkt", scsi_pkt \
541 	mptsas_cmd NcrTableIndirect buf scsi_cdb scsi_status))
542 _NOTE(SCHEME_PROTECTS_DATA("unique per pkt", smp_pkt))
543 _NOTE(SCHEME_PROTECTS_DATA("stable data", scsi_device scsi_address))
544 _NOTE(SCHEME_PROTECTS_DATA("No Mutex Needed", mptsas_tgt_private))
545 _NOTE(SCHEME_PROTECTS_DATA("No Mutex Needed", scsi_hba_tran::tran_tgt_private))
546 
547 #ifdef MPTSAS_DEBUG
548 void debug_enter(char *);
549 #endif
550 
551 /*
552  * Notes:
553  *	- scsi_hba_init(9F) initializes SCSI HBA modules
554  *	- must call scsi_hba_fini(9F) if modload() fails
555  */
556 int
557 _init(void)
558 {
559 	int status;
560 	/* CONSTCOND */
561 	ASSERT(NO_COMPETING_THREADS);
562 
563 	NDBG0(("_init"));
564 
565 	status = ddi_soft_state_init(&mptsas_state, MPTSAS_SIZE,
566 	    MPTSAS_INITIAL_SOFT_SPACE);
567 	if (status != 0) {
568 		return (status);
569 	}
570 
571 	if ((status = scsi_hba_init(&modlinkage)) != 0) {
572 		ddi_soft_state_fini(&mptsas_state);
573 		return (status);
574 	}
575 
576 	mutex_init(&mptsas_global_mutex, NULL, MUTEX_DRIVER, NULL);
577 	rw_init(&mptsas_global_rwlock, NULL, RW_DRIVER, NULL);
578 	mutex_init(&mptsas_log_mutex, NULL, MUTEX_DRIVER, NULL);
579 
580 	if ((status = mod_install(&modlinkage)) != 0) {
581 		mutex_destroy(&mptsas_log_mutex);
582 		rw_destroy(&mptsas_global_rwlock);
583 		mutex_destroy(&mptsas_global_mutex);
584 		ddi_soft_state_fini(&mptsas_state);
585 		scsi_hba_fini(&modlinkage);
586 	}
587 
588 	return (status);
589 }
590 
591 /*
592  * Notes:
593  *	- scsi_hba_fini(9F) uninitializes SCSI HBA modules
594  */
595 int
596 _fini(void)
597 {
598 	int	status;
599 	/* CONSTCOND */
600 	ASSERT(NO_COMPETING_THREADS);
601 
602 	NDBG0(("_fini"));
603 
604 	if ((status = mod_remove(&modlinkage)) == 0) {
605 		ddi_soft_state_fini(&mptsas_state);
606 		scsi_hba_fini(&modlinkage);
607 		mutex_destroy(&mptsas_global_mutex);
608 		rw_destroy(&mptsas_global_rwlock);
609 		mutex_destroy(&mptsas_log_mutex);
610 	}
611 	return (status);
612 }
613 
614 /*
615  * The loadable-module _info(9E) entry point
616  */
617 int
618 _info(struct modinfo *modinfop)
619 {
620 	/* CONSTCOND */
621 	ASSERT(NO_COMPETING_THREADS);
622 	NDBG0(("mptsas _info"));
623 
624 	return (mod_info(&modlinkage, modinfop));
625 }
626 
627 
628 static int
629 mptsas_iport_attach(dev_info_t *dip, ddi_attach_cmd_t cmd)
630 {
631 	dev_info_t		*pdip;
632 	mptsas_t		*mpt;
633 	scsi_hba_tran_t		*hba_tran;
634 	char			*iport = NULL;
635 	char			phymask[8];
636 	uint8_t			phy_mask = 0;
637 	int			physport = -1;
638 	int			dynamic_port = 0;
639 	uint32_t		page_address;
640 	char			initiator_wwnstr[MPTSAS_WWN_STRLEN];
641 	int			rval = DDI_FAILURE;
642 	int			i = 0;
643 	uint64_t		wwid = 0;
644 	uint8_t			portwidth = 0;
645 
646 	/* CONSTCOND */
647 	ASSERT(NO_COMPETING_THREADS);
648 
649 	switch (cmd) {
650 	case DDI_ATTACH:
651 		break;
652 
653 	case DDI_RESUME:
654 		/*
655 		 * If this a scsi-iport node, nothing to do here.
656 		 */
657 		return (DDI_SUCCESS);
658 
659 	default:
660 		return (DDI_FAILURE);
661 	}
662 
663 	pdip = ddi_get_parent(dip);
664 
665 	if ((hba_tran = ndi_flavorv_get(pdip, SCSA_FLAVOR_SCSI_DEVICE)) ==
666 	    NULL) {
667 		cmn_err(CE_WARN, "Failed attach iport because fail to "
668 		    "get tran vector for the HBA node");
669 		return (DDI_FAILURE);
670 	}
671 
672 	mpt = TRAN2MPT(hba_tran);
673 	ASSERT(mpt != NULL);
674 	if (mpt == NULL)
675 		return (DDI_FAILURE);
676 
677 	if ((hba_tran = ndi_flavorv_get(dip, SCSA_FLAVOR_SCSI_DEVICE)) ==
678 	    NULL) {
679 		mptsas_log(mpt, CE_WARN, "Failed attach iport because fail to "
680 		    "get tran vector for the iport node");
681 		return (DDI_FAILURE);
682 	}
683 
684 	/*
685 	 * Overwrite parent's tran_hba_private to iport's tran vector
686 	 */
687 	hba_tran->tran_hba_private = mpt;
688 
689 	ddi_report_dev(dip);
690 
691 	/*
692 	 * Get SAS address for initiator port according dev_handle
693 	 */
694 	iport = ddi_get_name_addr(dip);
695 	if (iport && strncmp(iport, "v0", 2) == 0) {
696 		return (DDI_SUCCESS);
697 	}
698 
699 	mutex_enter(&mpt->m_mutex);
700 	for (i = 0; i < MPTSAS_MAX_PHYS; i++) {
701 		bzero(phymask, sizeof (phymask));
702 		(void) sprintf(phymask, "%x", mpt->m_phy_info[i].phy_mask);
703 		if (strcmp(phymask, iport) == 0) {
704 			break;
705 		}
706 	}
707 
708 	if (i == MPTSAS_MAX_PHYS) {
709 		mptsas_log(mpt, CE_WARN, "Failed attach port %s because port"
710 		    "seems not exist", iport);
711 		mutex_exit(&mpt->m_mutex);
712 		return (DDI_FAILURE);
713 	}
714 
715 	phy_mask = mpt->m_phy_info[i].phy_mask;
716 	physport = mpt->m_phy_info[i].port_num;
717 
718 	if (mpt->m_phy_info[i].port_flags & AUTO_PORT_CONFIGURATION)
719 		dynamic_port = 1;
720 	else
721 		dynamic_port = 0;
722 
723 	page_address = (MPI2_SASPORT_PGAD_FORM_PORT_NUM |
724 	    (MPI2_SASPORT_PGAD_PORTNUMBER_MASK & physport));
725 
726 	rval = mptsas_get_sas_port_page0(mpt, page_address, &wwid, &portwidth);
727 	if (rval != DDI_SUCCESS) {
728 		mptsas_log(mpt, CE_WARN, "Failed attach port %s because get"
729 		    "SAS address of initiator failed!", iport);
730 		mutex_exit(&mpt->m_mutex);
731 		return (DDI_FAILURE);
732 	}
733 	mutex_exit(&mpt->m_mutex);
734 
735 	bzero(initiator_wwnstr, sizeof (initiator_wwnstr));
736 	(void) sprintf(initiator_wwnstr, "%016"PRIx64,
737 	    wwid);
738 
739 	if (ddi_prop_update_string(DDI_DEV_T_NONE, dip,
740 	    "initiator-port", initiator_wwnstr) !=
741 	    DDI_PROP_SUCCESS) {
742 		(void) ddi_prop_remove(DDI_DEV_T_NONE, dip, "initiator-port");
743 		return (DDI_FAILURE);
744 	}
745 
746 	if (ddi_prop_update_int(DDI_DEV_T_NONE, dip,
747 	    "phymask", phy_mask) !=
748 	    DDI_PROP_SUCCESS) {
749 		(void) ddi_prop_remove(DDI_DEV_T_NONE, dip, "phymask");
750 		return (DDI_FAILURE);
751 	}
752 
753 	if (ddi_prop_update_int(DDI_DEV_T_NONE, dip,
754 	    "dynamic-port", dynamic_port) !=
755 	    DDI_PROP_SUCCESS) {
756 		(void) ddi_prop_remove(DDI_DEV_T_NONE, dip, "dynamic-port");
757 		return (DDI_FAILURE);
758 	}
759 	/*
760 	 * register sas hba iport with mdi (MPxIO/vhci)
761 	 */
762 	if (mdi_phci_register(MDI_HCI_CLASS_SCSI,
763 	    dip, 0) == MDI_SUCCESS) {
764 		mpt->m_mpxio_enable = TRUE;
765 	}
766 	return (DDI_SUCCESS);
767 }
768 
769 /*
770  * Notes:
771  *	Set up all device state and allocate data structures,
772  *	mutexes, condition variables, etc. for device operation.
773  *	Add interrupts needed.
774  *	Return DDI_SUCCESS if device is ready, else return DDI_FAILURE.
775  */
776 static int
777 mptsas_attach(dev_info_t *dip, ddi_attach_cmd_t cmd)
778 {
779 	mptsas_t		*mpt = NULL;
780 	int			instance, i, j;
781 	int			doneq_thread_num;
782 	char			buf[64];
783 	char			intr_added = 0;
784 	char			map_setup = 0;
785 	char			config_setup = 0;
786 	char			hba_attach_setup = 0;
787 	char			sas_attach_setup = 0;
788 	char			mutex_init_done = 0;
789 	char			event_taskq_create = 0;
790 	char			dr_taskq_create = 0;
791 	char			doneq_thread_create = 0;
792 	scsi_hba_tran_t		*hba_tran;
793 	int			intr_types;
794 	uint_t			mem_bar = MEM_SPACE;
795 	uint8_t			mask = 0x0;
796 	int			tran_flags = 0;
797 	int			rval = DDI_FAILURE;
798 
799 	/* CONSTCOND */
800 	ASSERT(NO_COMPETING_THREADS);
801 
802 	if (scsi_hba_iport_unit_address(dip)) {
803 		return (mptsas_iport_attach(dip, cmd));
804 	}
805 
806 	switch (cmd) {
807 	case DDI_ATTACH:
808 		break;
809 
810 	case DDI_RESUME:
811 		if ((hba_tran = ddi_get_driver_private(dip)) == NULL)
812 			return (DDI_FAILURE);
813 
814 		mpt = TRAN2MPT(hba_tran);
815 
816 		if (!mpt) {
817 			return (DDI_FAILURE);
818 		}
819 
820 		/*
821 		 * Reset hardware and softc to "no outstanding commands"
822 		 * Note	that a check condition can result on first command
823 		 * to a	target.
824 		 */
825 		mutex_enter(&mpt->m_mutex);
826 
827 		/*
828 		 * raise power.
829 		 */
830 		if (mpt->m_options & MPTSAS_OPT_PM) {
831 			mutex_exit(&mpt->m_mutex);
832 			(void) pm_busy_component(dip, 0);
833 			if (mpt->m_power_level != PM_LEVEL_D0) {
834 				rval = pm_raise_power(dip, 0, PM_LEVEL_D0);
835 			} else {
836 				rval = pm_power_has_changed(dip, 0,
837 				    PM_LEVEL_D0);
838 			}
839 			if (rval == DDI_SUCCESS) {
840 				mutex_enter(&mpt->m_mutex);
841 			} else {
842 				/*
843 				 * The pm_raise_power() call above failed,
844 				 * and that can only occur if we were unable
845 				 * to reset the hardware.  This is probably
846 				 * due to unhealty hardware, and because
847 				 * important filesystems(such as the root
848 				 * filesystem) could be on the attached disks,
849 				 * it would not be a good idea to continue,
850 				 * as we won't be entirely certain we are
851 				 * writing correct data.  So we panic() here
852 				 * to not only prevent possible data corruption,
853 				 * but to give developers or end users a hope
854 				 * of identifying and correcting any problems.
855 				 */
856 				fm_panic("mptsas could not reset hardware "
857 				    "during resume");
858 			}
859 		}
860 
861 		mpt->m_suspended = 0;
862 
863 		/*
864 		 * Reinitialize ioc
865 		 */
866 		if (mptsas_init_chip(mpt, FALSE) == DDI_FAILURE) {
867 			mutex_exit(&mpt->m_mutex);
868 			if (mpt->m_options & MPTSAS_OPT_PM) {
869 				(void) pm_idle_component(dip, 0);
870 			}
871 			fm_panic("mptsas init chip fail during resume");
872 		}
873 		/*
874 		 * mptsas_update_driver_data needs interrupts so enable them
875 		 * first.
876 		 */
877 		MPTSAS_ENABLE_INTR(mpt);
878 		mptsas_update_driver_data(mpt);
879 
880 		/* start requests, if possible */
881 		mptsas_restart_hba(mpt);
882 
883 		mutex_exit(&mpt->m_mutex);
884 
885 		/*
886 		 * Restart watch thread
887 		 */
888 		mutex_enter(&mptsas_global_mutex);
889 		if (mptsas_timeout_id == 0) {
890 			mptsas_timeout_id = timeout(mptsas_watch, NULL,
891 			    mptsas_tick);
892 			mptsas_timeouts_enabled = 1;
893 		}
894 		mutex_exit(&mptsas_global_mutex);
895 
896 		/* report idle status to pm framework */
897 		if (mpt->m_options & MPTSAS_OPT_PM) {
898 			(void) pm_idle_component(dip, 0);
899 		}
900 
901 		return (DDI_SUCCESS);
902 
903 	default:
904 		return (DDI_FAILURE);
905 
906 	}
907 
908 	instance = ddi_get_instance(dip);
909 
910 	/*
911 	 * Allocate softc information.
912 	 */
913 	if (ddi_soft_state_zalloc(mptsas_state, instance) != DDI_SUCCESS) {
914 		mptsas_log(NULL, CE_WARN,
915 		    "mptsas%d: cannot allocate soft state", instance);
916 		goto fail;
917 	}
918 
919 	mpt = ddi_get_soft_state(mptsas_state, instance);
920 
921 	if (mpt == NULL) {
922 		mptsas_log(NULL, CE_WARN,
923 		    "mptsas%d: cannot get soft state", instance);
924 		goto fail;
925 	}
926 
927 	/* Allocate a transport structure */
928 	hba_tran = mpt->m_tran = scsi_hba_tran_alloc(dip, SCSI_HBA_CANSLEEP);
929 	ASSERT(mpt->m_tran != NULL);
930 
931 	/* Indicate that we are 'sizeof (scsi_*(9S))' clean. */
932 	scsi_size_clean(dip);
933 
934 	mpt->m_dip = dip;
935 	mpt->m_instance = instance;
936 
937 	/* Make a per-instance copy of the structures */
938 	mpt->m_io_dma_attr = mptsas_dma_attrs64;
939 	mpt->m_msg_dma_attr = mptsas_dma_attrs;
940 	mpt->m_dev_acc_attr = mptsas_dev_attr;
941 
942 	/*
943 	 * Initialize FMA
944 	 */
945 	mpt->m_fm_capabilities = ddi_getprop(DDI_DEV_T_ANY, mpt->m_dip,
946 	    DDI_PROP_CANSLEEP | DDI_PROP_DONTPASS, "fm-capable",
947 	    DDI_FM_EREPORT_CAPABLE | DDI_FM_ACCCHK_CAPABLE |
948 	    DDI_FM_DMACHK_CAPABLE | DDI_FM_ERRCB_CAPABLE);
949 
950 	mptsas_fm_init(mpt);
951 
952 	if (pci_config_setup(mpt->m_dip,
953 	    &mpt->m_config_handle) != DDI_SUCCESS) {
954 		mptsas_log(mpt, CE_WARN, "cannot map configuration space.");
955 		goto fail;
956 	}
957 	config_setup++;
958 
959 	if (mptsas_alloc_handshake_msg(mpt,
960 	    sizeof (Mpi2SCSITaskManagementRequest_t)) == DDI_FAILURE) {
961 		mptsas_log(mpt, CE_WARN, "cannot initialize handshake msg.");
962 		goto fail;
963 	}
964 
965 	/*
966 	 * This is a workaround for a XMITS ASIC bug which does not
967 	 * drive the CBE upper bits.
968 	 */
969 	if (pci_config_get16(mpt->m_config_handle, PCI_CONF_STAT) &
970 	    PCI_STAT_PERROR) {
971 		pci_config_put16(mpt->m_config_handle, PCI_CONF_STAT,
972 		    PCI_STAT_PERROR);
973 	}
974 
975 	/*
976 	 * Setup configuration space
977 	 */
978 	if (mptsas_config_space_init(mpt) == FALSE) {
979 		mptsas_log(mpt, CE_WARN, "mptsas_config_space_init failed");
980 		goto fail;
981 	}
982 
983 	if (ddi_regs_map_setup(dip, mem_bar, (caddr_t *)&mpt->m_reg,
984 	    0, 0, &mpt->m_dev_acc_attr, &mpt->m_datap) != DDI_SUCCESS) {
985 		mptsas_log(mpt, CE_WARN, "map setup failed");
986 		goto fail;
987 	}
988 	map_setup++;
989 
990 	/*
991 	 * A taskq is created for dealing with the event handler
992 	 */
993 	if ((mpt->m_event_taskq = ddi_taskq_create(dip, "mptsas_event_taskq",
994 	    1, TASKQ_DEFAULTPRI, 0)) == NULL) {
995 		mptsas_log(mpt, CE_NOTE, "ddi_taskq_create failed");
996 		goto fail;
997 	}
998 	event_taskq_create++;
999 
1000 	/*
1001 	 * A taskq is created for dealing with dr events
1002 	 */
1003 	if ((mpt->m_dr_taskq = ddi_taskq_create(dip,
1004 	    "mptsas_dr_taskq",
1005 	    1, TASKQ_DEFAULTPRI, 0)) == NULL) {
1006 		mptsas_log(mpt, CE_NOTE, "ddi_taskq_create for discovery "
1007 		    "failed");
1008 		goto fail;
1009 	}
1010 	dr_taskq_create++;
1011 
1012 	mpt->m_doneq_thread_threshold = ddi_prop_get_int(DDI_DEV_T_ANY, dip,
1013 	    0, "mptsas_doneq_thread_threshold_prop", 10);
1014 	mpt->m_doneq_length_threshold = ddi_prop_get_int(DDI_DEV_T_ANY, dip,
1015 	    0, "mptsas_doneq_length_threshold_prop", 8);
1016 	mpt->m_doneq_thread_n = ddi_prop_get_int(DDI_DEV_T_ANY, dip,
1017 	    0, "mptsas_doneq_thread_n_prop", 8);
1018 
1019 	if (mpt->m_doneq_thread_n) {
1020 		cv_init(&mpt->m_doneq_thread_cv, NULL, CV_DRIVER, NULL);
1021 		mutex_init(&mpt->m_doneq_mutex, NULL, MUTEX_DRIVER, NULL);
1022 
1023 		mutex_enter(&mpt->m_doneq_mutex);
1024 		mpt->m_doneq_thread_id =
1025 		    kmem_zalloc(sizeof (mptsas_doneq_thread_list_t)
1026 		    * mpt->m_doneq_thread_n, KM_SLEEP);
1027 
1028 		for (j = 0; j < mpt->m_doneq_thread_n; j++) {
1029 			cv_init(&mpt->m_doneq_thread_id[j].cv, NULL,
1030 			    CV_DRIVER, NULL);
1031 			mutex_init(&mpt->m_doneq_thread_id[j].mutex, NULL,
1032 			    MUTEX_DRIVER, NULL);
1033 			mutex_enter(&mpt->m_doneq_thread_id[j].mutex);
1034 			mpt->m_doneq_thread_id[j].flag |=
1035 			    MPTSAS_DONEQ_THREAD_ACTIVE;
1036 			mpt->m_doneq_thread_id[j].arg.mpt = mpt;
1037 			mpt->m_doneq_thread_id[j].arg.t = j;
1038 			mpt->m_doneq_thread_id[j].threadp =
1039 			    thread_create(NULL, 0, mptsas_doneq_thread,
1040 			    &mpt->m_doneq_thread_id[j].arg,
1041 			    0, &p0, TS_RUN, minclsyspri);
1042 			mpt->m_doneq_thread_id[j].donetail =
1043 			    &mpt->m_doneq_thread_id[j].doneq;
1044 			mutex_exit(&mpt->m_doneq_thread_id[j].mutex);
1045 		}
1046 		mutex_exit(&mpt->m_doneq_mutex);
1047 		doneq_thread_create++;
1048 	}
1049 
1050 	/* Get supported interrupt types */
1051 	if (ddi_intr_get_supported_types(dip, &intr_types) != DDI_SUCCESS) {
1052 		mptsas_log(mpt, CE_WARN, "ddi_intr_get_supported_types "
1053 		    "failed\n");
1054 		goto fail;
1055 	}
1056 
1057 	NDBG6(("ddi_intr_get_supported_types() returned: 0x%x", intr_types));
1058 
1059 	if (mptsas_enable_msi && (intr_types & DDI_INTR_TYPE_MSI)) {
1060 		/*
1061 		 * Try MSI, but fall back to FIXED
1062 		 */
1063 		if (mptsas_add_intrs(mpt, DDI_INTR_TYPE_MSI) == DDI_SUCCESS) {
1064 			NDBG0(("Using MSI interrupt type"));
1065 			mpt->m_intr_type = DDI_INTR_TYPE_MSI;
1066 			goto intr_done;
1067 		}
1068 	}
1069 
1070 	if (intr_types & DDI_INTR_TYPE_FIXED) {
1071 
1072 		if (mptsas_add_intrs(mpt, DDI_INTR_TYPE_FIXED) == DDI_SUCCESS) {
1073 			NDBG0(("Using FIXED interrupt type"));
1074 			mpt->m_intr_type = DDI_INTR_TYPE_FIXED;
1075 
1076 			goto intr_done;
1077 		}
1078 
1079 		NDBG0(("FIXED interrupt registration failed"));
1080 	}
1081 
1082 	goto fail;
1083 
1084 intr_done:
1085 	intr_added++;
1086 
1087 	/* Initialize mutex used in interrupt handler */
1088 	mutex_init(&mpt->m_mutex, NULL, MUTEX_DRIVER,
1089 	    DDI_INTR_PRI(mpt->m_intr_pri));
1090 	mutex_init(&mpt->m_tx_waitq_mutex, NULL, MUTEX_DRIVER,
1091 	    DDI_INTR_PRI(mpt->m_intr_pri));
1092 	cv_init(&mpt->m_cv, NULL, CV_DRIVER, NULL);
1093 	cv_init(&mpt->m_passthru_cv, NULL, CV_DRIVER, NULL);
1094 	cv_init(&mpt->m_fw_cv, NULL, CV_DRIVER, NULL);
1095 	cv_init(&mpt->m_config_cv, NULL, CV_DRIVER, NULL);
1096 	mutex_init_done++;
1097 
1098 	/*
1099 	 * Disable hardware interrupt since we're not ready to
1100 	 * handle it yet.
1101 	 */
1102 	MPTSAS_DISABLE_INTR(mpt);
1103 
1104 	/*
1105 	 * Enable interrupts
1106 	 */
1107 	if (mpt->m_intr_cap & DDI_INTR_FLAG_BLOCK) {
1108 		/* Call ddi_intr_block_enable() for MSI interrupts */
1109 		(void) ddi_intr_block_enable(mpt->m_htable, mpt->m_intr_cnt);
1110 	} else {
1111 		/* Call ddi_intr_enable for MSI or FIXED interrupts */
1112 		for (i = 0; i < mpt->m_intr_cnt; i++) {
1113 			(void) ddi_intr_enable(mpt->m_htable[i]);
1114 		}
1115 	}
1116 
1117 	mutex_enter(&mpt->m_mutex);
1118 	/*
1119 	 * Initialize power management component
1120 	 */
1121 	if (mpt->m_options & MPTSAS_OPT_PM) {
1122 		if (mptsas_init_pm(mpt)) {
1123 			mutex_exit(&mpt->m_mutex);
1124 			mptsas_log(mpt, CE_WARN, "mptsas pm initialization "
1125 			    "failed");
1126 			goto fail;
1127 		}
1128 	}
1129 
1130 	/*
1131 	 * Initialize chip
1132 	 */
1133 	if (mptsas_init_chip(mpt, TRUE) == DDI_FAILURE) {
1134 		mutex_exit(&mpt->m_mutex);
1135 		mptsas_log(mpt, CE_WARN, "mptsas chip initialization failed");
1136 		goto fail;
1137 	}
1138 	mutex_exit(&mpt->m_mutex);
1139 
1140 	/*
1141 	 * initialize SCSI HBA transport structure
1142 	 */
1143 	hba_tran->tran_hba_private	= mpt;
1144 	hba_tran->tran_tgt_private	= NULL;
1145 
1146 	hba_tran->tran_tgt_init		= mptsas_scsi_tgt_init;
1147 	hba_tran->tran_tgt_free		= mptsas_scsi_tgt_free;
1148 
1149 	hba_tran->tran_start		= mptsas_scsi_start;
1150 	hba_tran->tran_reset		= mptsas_scsi_reset;
1151 	hba_tran->tran_abort		= mptsas_scsi_abort;
1152 	hba_tran->tran_getcap		= mptsas_scsi_getcap;
1153 	hba_tran->tran_setcap		= mptsas_scsi_setcap;
1154 	hba_tran->tran_init_pkt		= mptsas_scsi_init_pkt;
1155 	hba_tran->tran_destroy_pkt	= mptsas_scsi_destroy_pkt;
1156 
1157 	hba_tran->tran_dmafree		= mptsas_scsi_dmafree;
1158 	hba_tran->tran_sync_pkt		= mptsas_scsi_sync_pkt;
1159 	hba_tran->tran_reset_notify	= mptsas_scsi_reset_notify;
1160 
1161 	hba_tran->tran_get_bus_addr	= mptsas_get_bus_addr;
1162 	hba_tran->tran_get_name		= mptsas_get_name;
1163 
1164 	hba_tran->tran_quiesce		= mptsas_scsi_quiesce;
1165 	hba_tran->tran_unquiesce	= mptsas_scsi_unquiesce;
1166 	hba_tran->tran_bus_reset	= NULL;
1167 
1168 	hba_tran->tran_add_eventcall	= NULL;
1169 	hba_tran->tran_get_eventcookie	= NULL;
1170 	hba_tran->tran_post_event	= NULL;
1171 	hba_tran->tran_remove_eventcall	= NULL;
1172 
1173 	hba_tran->tran_bus_config	= mptsas_bus_config;
1174 
1175 	hba_tran->tran_interconnect_type = INTERCONNECT_SAS;
1176 
1177 	if (mptsas_alloc_active_slots(mpt, KM_SLEEP)) {
1178 		goto fail;
1179 	}
1180 
1181 	/*
1182 	 * Register the iport for multiple port HBA
1183 	 */
1184 	/*
1185 	 * initial value of mask is 0
1186 	 */
1187 	mutex_enter(&mpt->m_mutex);
1188 	for (i = 0; i < mpt->m_num_phys; i++) {
1189 		uint8_t	phy_mask = 0x00;
1190 		char phy_mask_name[8];
1191 		uint8_t current_port;
1192 
1193 		if (mpt->m_phy_info[i].attached_devhdl == 0)
1194 			continue;
1195 
1196 		bzero(phy_mask_name, sizeof (phy_mask_name));
1197 
1198 		current_port = mpt->m_phy_info[i].port_num;
1199 
1200 		if ((mask & (1 << i)) != 0)
1201 			continue;
1202 
1203 		for (j = 0; j < mpt->m_num_phys; j++) {
1204 			if (mpt->m_phy_info[j].attached_devhdl &&
1205 			    (mpt->m_phy_info[j].port_num == current_port)) {
1206 				phy_mask |= (1 << j);
1207 			}
1208 		}
1209 		mask = mask | phy_mask;
1210 
1211 		for (j = 0; j < mpt->m_num_phys; j++) {
1212 			if ((phy_mask >> j) & 0x01) {
1213 				mpt->m_phy_info[j].phy_mask = phy_mask;
1214 			}
1215 		}
1216 
1217 		(void) sprintf(phy_mask_name, "%x", phy_mask);
1218 
1219 		mutex_exit(&mpt->m_mutex);
1220 		/*
1221 		 * register a iport
1222 		 */
1223 		(void) scsi_hba_iport_register(dip, phy_mask_name);
1224 		mutex_enter(&mpt->m_mutex);
1225 	}
1226 	mutex_exit(&mpt->m_mutex);
1227 	/*
1228 	 * register a virtual port for RAID volume always
1229 	 */
1230 	(void) scsi_hba_iport_register(dip, "v0");
1231 	/*
1232 	 * All children of the HBA are iports. We need tran was cloned.
1233 	 * So we pass the flags to SCSA. SCSI_HBA_TRAN_CLONE will be
1234 	 * inherited to iport's tran vector.
1235 	 */
1236 	tran_flags = (SCSI_HBA_HBA | SCSI_HBA_TRAN_CLONE);
1237 
1238 	if (scsi_hba_attach_setup(dip, &mpt->m_msg_dma_attr,
1239 	    hba_tran, tran_flags) != DDI_SUCCESS) {
1240 		mptsas_log(mpt, CE_WARN, "hba attach setup failed");
1241 		goto fail;
1242 	}
1243 	hba_attach_setup++;
1244 
1245 	mpt->m_smptran = sas_hba_tran_alloc(dip);
1246 	ASSERT(mpt->m_smptran != NULL);
1247 	mpt->m_smptran->tran_hba_private = mpt;
1248 	mpt->m_smptran->tran_smp_start = mptsas_smp_start;
1249 	mpt->m_smptran->tran_sas_getcap = mptsas_getcap;
1250 	if (sas_hba_attach_setup(dip, mpt->m_smptran) != DDI_SUCCESS) {
1251 		mptsas_log(mpt, CE_WARN, "smp attach setup failed");
1252 		goto fail;
1253 	}
1254 	sas_attach_setup++;
1255 	/*
1256 	 * Initialize smp hash table
1257 	 */
1258 	mptsas_hash_init(&mpt->m_active->m_smptbl);
1259 	mpt->m_smp_devhdl = 0xFFFF;
1260 
1261 	/*
1262 	 * create kmem cache for packets
1263 	 */
1264 	(void) sprintf(buf, "mptsas%d_cache", instance);
1265 	mpt->m_kmem_cache = kmem_cache_create(buf,
1266 	    sizeof (struct mptsas_cmd) + scsi_pkt_size(), 8,
1267 	    mptsas_kmem_cache_constructor, mptsas_kmem_cache_destructor,
1268 	    NULL, (void *)mpt, NULL, 0);
1269 
1270 	if (mpt->m_kmem_cache == NULL) {
1271 		mptsas_log(mpt, CE_WARN, "creating kmem cache failed");
1272 		goto fail;
1273 	}
1274 
1275 	/*
1276 	 * create kmem cache for extra SGL frames if SGL cannot
1277 	 * be accomodated into main request frame.
1278 	 */
1279 	(void) sprintf(buf, "mptsas%d_cache_frames", instance);
1280 	mpt->m_cache_frames = kmem_cache_create(buf,
1281 	    sizeof (mptsas_cache_frames_t), 8,
1282 	    mptsas_cache_frames_constructor, mptsas_cache_frames_destructor,
1283 	    NULL, (void *)mpt, NULL, 0);
1284 
1285 	if (mpt->m_cache_frames == NULL) {
1286 		mptsas_log(mpt, CE_WARN, "creating cache for frames failed");
1287 		goto fail;
1288 	}
1289 
1290 	mpt->m_scsi_reset_delay	= ddi_prop_get_int(DDI_DEV_T_ANY,
1291 	    dip, 0, "scsi-reset-delay",	SCSI_DEFAULT_RESET_DELAY);
1292 	if (mpt->m_scsi_reset_delay == 0) {
1293 		mptsas_log(mpt, CE_NOTE,
1294 		    "scsi_reset_delay of 0 is not recommended,"
1295 		    " resetting to SCSI_DEFAULT_RESET_DELAY\n");
1296 		mpt->m_scsi_reset_delay = SCSI_DEFAULT_RESET_DELAY;
1297 	}
1298 
1299 	/*
1300 	 * Initialize the wait and done FIFO queue
1301 	 */
1302 	mpt->m_donetail = &mpt->m_doneq;
1303 	mpt->m_waitqtail = &mpt->m_waitq;
1304 
1305 	mpt->m_tx_waitqtail = &mpt->m_tx_waitq;
1306 	mpt->m_tx_draining = 0;
1307 
1308 	/*
1309 	 * ioc cmd queue initialize
1310 	 */
1311 	mpt->m_ioc_event_cmdtail = &mpt->m_ioc_event_cmdq;
1312 
1313 	mpt->m_dev_handle = 0xFFFF;
1314 
1315 	MPTSAS_ENABLE_INTR(mpt);
1316 
1317 	/*
1318 	 * enable event notification
1319 	 */
1320 	mutex_enter(&mpt->m_mutex);
1321 	if (mptsas_ioc_enable_event_notification(mpt)) {
1322 		mutex_exit(&mpt->m_mutex);
1323 		goto fail;
1324 	}
1325 	mutex_exit(&mpt->m_mutex);
1326 
1327 
1328 	/* Check all dma handles allocated in attach */
1329 	if ((mptsas_check_dma_handle(mpt->m_dma_req_frame_hdl)
1330 	    != DDI_SUCCESS) ||
1331 	    (mptsas_check_dma_handle(mpt->m_dma_reply_frame_hdl)
1332 	    != DDI_SUCCESS) ||
1333 	    (mptsas_check_dma_handle(mpt->m_dma_free_queue_hdl)
1334 	    != DDI_SUCCESS) ||
1335 	    (mptsas_check_dma_handle(mpt->m_dma_post_queue_hdl)
1336 	    != DDI_SUCCESS) ||
1337 	    (mptsas_check_dma_handle(mpt->m_hshk_dma_hdl)
1338 	    != DDI_SUCCESS)) {
1339 		goto fail;
1340 	}
1341 
1342 	/* Check all acc handles allocated in attach */
1343 	if ((mptsas_check_acc_handle(mpt->m_datap) != DDI_SUCCESS) ||
1344 	    (mptsas_check_acc_handle(mpt->m_acc_req_frame_hdl)
1345 	    != DDI_SUCCESS) ||
1346 	    (mptsas_check_acc_handle(mpt->m_acc_reply_frame_hdl)
1347 	    != DDI_SUCCESS) ||
1348 	    (mptsas_check_acc_handle(mpt->m_acc_free_queue_hdl)
1349 	    != DDI_SUCCESS) ||
1350 	    (mptsas_check_acc_handle(mpt->m_acc_post_queue_hdl)
1351 	    != DDI_SUCCESS) ||
1352 	    (mptsas_check_acc_handle(mpt->m_hshk_acc_hdl)
1353 	    != DDI_SUCCESS) ||
1354 	    (mptsas_check_acc_handle(mpt->m_config_handle)
1355 	    != DDI_SUCCESS)) {
1356 		goto fail;
1357 	}
1358 
1359 	/*
1360 	 * After this point, we are not going to fail the attach.
1361 	 */
1362 	/*
1363 	 * used for mptsas_watch
1364 	 */
1365 	rw_enter(&mptsas_global_rwlock, RW_WRITER);
1366 	if (mptsas_head == NULL) {
1367 		mptsas_head = mpt;
1368 	} else {
1369 		mptsas_tail->m_next = mpt;
1370 	}
1371 	mptsas_tail = mpt;
1372 	rw_exit(&mptsas_global_rwlock);
1373 
1374 	mutex_enter(&mptsas_global_mutex);
1375 	if (mptsas_timeouts_enabled == 0) {
1376 		mptsas_scsi_watchdog_tick = ddi_prop_get_int(DDI_DEV_T_ANY,
1377 		    dip, 0, "scsi-watchdog-tick", DEFAULT_WD_TICK);
1378 
1379 		mptsas_tick = mptsas_scsi_watchdog_tick *
1380 		    drv_usectohz((clock_t)1000000);
1381 
1382 		mptsas_timeout_id = timeout(mptsas_watch, NULL, mptsas_tick);
1383 		mptsas_timeouts_enabled = 1;
1384 	}
1385 	mutex_exit(&mptsas_global_mutex);
1386 
1387 	/* Print message of HBA present */
1388 	ddi_report_dev(dip);
1389 
1390 	/* report idle status to pm framework */
1391 	if (mpt->m_options & MPTSAS_OPT_PM) {
1392 		(void) pm_idle_component(dip, 0);
1393 	}
1394 
1395 	return (DDI_SUCCESS);
1396 
1397 fail:
1398 	mptsas_log(mpt, CE_WARN, "attach failed");
1399 	mptsas_fm_ereport(mpt, DDI_FM_DEVICE_NO_RESPONSE);
1400 	ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_LOST);
1401 	if (mpt) {
1402 		mutex_enter(&mptsas_global_mutex);
1403 
1404 		if (mptsas_timeout_id && (mptsas_head == NULL)) {
1405 			timeout_id_t tid = mptsas_timeout_id;
1406 			mptsas_timeouts_enabled = 0;
1407 			mptsas_timeout_id = 0;
1408 			mutex_exit(&mptsas_global_mutex);
1409 			(void) untimeout(tid);
1410 			mutex_enter(&mptsas_global_mutex);
1411 		}
1412 		mutex_exit(&mptsas_global_mutex);
1413 		/* deallocate in reverse order */
1414 		if (mpt->m_cache_frames) {
1415 			kmem_cache_destroy(mpt->m_cache_frames);
1416 		}
1417 		if (mpt->m_kmem_cache) {
1418 			kmem_cache_destroy(mpt->m_kmem_cache);
1419 		}
1420 		if (hba_attach_setup) {
1421 			(void) scsi_hba_detach(dip);
1422 		}
1423 		if (sas_attach_setup) {
1424 			(void) sas_hba_detach(dip);
1425 		}
1426 		if (intr_added) {
1427 			mptsas_rem_intrs(mpt);
1428 		}
1429 		if (doneq_thread_create) {
1430 			mutex_enter(&mpt->m_doneq_mutex);
1431 			doneq_thread_num = mpt->m_doneq_thread_n;
1432 			for (j = 0; j < mpt->m_doneq_thread_n; j++) {
1433 				mutex_enter(&mpt->m_doneq_thread_id[j].mutex);
1434 				mpt->m_doneq_thread_id[j].flag &=
1435 				    (~MPTSAS_DONEQ_THREAD_ACTIVE);
1436 				cv_signal(&mpt->m_doneq_thread_id[j].cv);
1437 				mutex_exit(&mpt->m_doneq_thread_id[j].mutex);
1438 			}
1439 			while (mpt->m_doneq_thread_n) {
1440 				cv_wait(&mpt->m_doneq_thread_cv,
1441 				    &mpt->m_doneq_mutex);
1442 			}
1443 			for (j = 0; j < doneq_thread_num; j++) {
1444 				cv_destroy(&mpt->m_doneq_thread_id[j].cv);
1445 				mutex_destroy(&mpt->m_doneq_thread_id[j].mutex);
1446 			}
1447 			kmem_free(mpt->m_doneq_thread_id,
1448 			    sizeof (mptsas_doneq_thread_list_t)
1449 			    * doneq_thread_num);
1450 			mutex_exit(&mpt->m_doneq_mutex);
1451 			cv_destroy(&mpt->m_doneq_thread_cv);
1452 			mutex_destroy(&mpt->m_doneq_mutex);
1453 		}
1454 		if (event_taskq_create) {
1455 			ddi_taskq_destroy(mpt->m_event_taskq);
1456 		}
1457 		if (dr_taskq_create) {
1458 			ddi_taskq_destroy(mpt->m_dr_taskq);
1459 		}
1460 		if (mutex_init_done) {
1461 			mutex_destroy(&mpt->m_tx_waitq_mutex);
1462 			mutex_destroy(&mpt->m_mutex);
1463 			cv_destroy(&mpt->m_cv);
1464 			cv_destroy(&mpt->m_passthru_cv);
1465 			cv_destroy(&mpt->m_fw_cv);
1466 			cv_destroy(&mpt->m_config_cv);
1467 		}
1468 		mptsas_free_handshake_msg(mpt);
1469 		mptsas_hba_fini(mpt);
1470 		if (map_setup) {
1471 			mptsas_cfg_fini(mpt);
1472 		}
1473 		if (config_setup) {
1474 			pci_config_teardown(&mpt->m_config_handle);
1475 		}
1476 		if (mpt->m_tran) {
1477 			scsi_hba_tran_free(mpt->m_tran);
1478 			mpt->m_tran = NULL;
1479 		}
1480 		if (mpt->m_smptran) {
1481 			sas_hba_tran_free(mpt->m_smptran);
1482 			mpt->m_smptran = NULL;
1483 		}
1484 		mptsas_fm_fini(mpt);
1485 		ddi_soft_state_free(mptsas_state, instance);
1486 		ddi_prop_remove_all(dip);
1487 	}
1488 	return (DDI_FAILURE);
1489 }
1490 
1491 static int
1492 mptsas_suspend(dev_info_t *devi)
1493 {
1494 	mptsas_t	*mpt, *g;
1495 	scsi_hba_tran_t	*tran;
1496 
1497 	if (scsi_hba_iport_unit_address(devi)) {
1498 		return (DDI_SUCCESS);
1499 	}
1500 
1501 	if ((tran = ddi_get_driver_private(devi)) == NULL)
1502 		return (DDI_SUCCESS);
1503 
1504 	mpt = TRAN2MPT(tran);
1505 	if (!mpt) {
1506 		return (DDI_SUCCESS);
1507 	}
1508 
1509 	mutex_enter(&mpt->m_mutex);
1510 
1511 	if (mpt->m_suspended++) {
1512 		mutex_exit(&mpt->m_mutex);
1513 		return (DDI_SUCCESS);
1514 	}
1515 
1516 	/*
1517 	 * Cancel timeout threads for this mpt
1518 	 */
1519 	if (mpt->m_quiesce_timeid) {
1520 		timeout_id_t tid = mpt->m_quiesce_timeid;
1521 		mpt->m_quiesce_timeid = 0;
1522 		mutex_exit(&mpt->m_mutex);
1523 		(void) untimeout(tid);
1524 		mutex_enter(&mpt->m_mutex);
1525 	}
1526 
1527 	if (mpt->m_restart_cmd_timeid) {
1528 		timeout_id_t tid = mpt->m_restart_cmd_timeid;
1529 		mpt->m_restart_cmd_timeid = 0;
1530 		mutex_exit(&mpt->m_mutex);
1531 		(void) untimeout(tid);
1532 		mutex_enter(&mpt->m_mutex);
1533 	}
1534 
1535 	if (mpt->m_pm_timeid != 0) {
1536 		timeout_id_t tid = mpt->m_pm_timeid;
1537 		mpt->m_pm_timeid = 0;
1538 		mutex_exit(&mpt->m_mutex);
1539 		(void) untimeout(tid);
1540 		/*
1541 		 * Report idle status for last ioctl since
1542 		 * calls to pm_busy_component(9F) are stacked.
1543 		 */
1544 		(void) pm_idle_component(mpt->m_dip, 0);
1545 		mutex_enter(&mpt->m_mutex);
1546 	}
1547 	mutex_exit(&mpt->m_mutex);
1548 
1549 	/*
1550 	 * Cancel watch threads if all mpts suspended
1551 	 */
1552 	rw_enter(&mptsas_global_rwlock, RW_WRITER);
1553 	for (g = mptsas_head; g != NULL; g = g->m_next) {
1554 		if (!g->m_suspended)
1555 			break;
1556 	}
1557 	rw_exit(&mptsas_global_rwlock);
1558 
1559 	mutex_enter(&mptsas_global_mutex);
1560 	if (g == NULL) {
1561 		timeout_id_t tid;
1562 
1563 		mptsas_timeouts_enabled = 0;
1564 		if (mptsas_timeout_id) {
1565 			tid = mptsas_timeout_id;
1566 			mptsas_timeout_id = 0;
1567 			mutex_exit(&mptsas_global_mutex);
1568 			(void) untimeout(tid);
1569 			mutex_enter(&mptsas_global_mutex);
1570 		}
1571 		if (mptsas_reset_watch) {
1572 			tid = mptsas_reset_watch;
1573 			mptsas_reset_watch = 0;
1574 			mutex_exit(&mptsas_global_mutex);
1575 			(void) untimeout(tid);
1576 			mutex_enter(&mptsas_global_mutex);
1577 		}
1578 	}
1579 	mutex_exit(&mptsas_global_mutex);
1580 
1581 	mutex_enter(&mpt->m_mutex);
1582 
1583 	/*
1584 	 * If this mpt is not in full power(PM_LEVEL_D0), just return.
1585 	 */
1586 	if ((mpt->m_options & MPTSAS_OPT_PM) &&
1587 	    (mpt->m_power_level != PM_LEVEL_D0)) {
1588 		mutex_exit(&mpt->m_mutex);
1589 		return (DDI_SUCCESS);
1590 	}
1591 
1592 	/* Disable HBA interrupts in hardware */
1593 	MPTSAS_DISABLE_INTR(mpt);
1594 
1595 	mutex_exit(&mpt->m_mutex);
1596 
1597 	/* drain the taskq */
1598 	ddi_taskq_wait(mpt->m_event_taskq);
1599 	ddi_taskq_wait(mpt->m_dr_taskq);
1600 
1601 	return (DDI_SUCCESS);
1602 }
1603 
1604 /*
1605  * quiesce(9E) entry point.
1606  *
1607  * This function is called when the system is single-threaded at high
1608  * PIL with preemption disabled. Therefore, this function must not be
1609  * blocked.
1610  *
1611  * This function returns DDI_SUCCESS on success, or DDI_FAILURE on failure.
1612  * DDI_FAILURE indicates an error condition and should almost never happen.
1613  */
1614 #ifndef	__sparc
1615 static int
1616 mptsas_quiesce(dev_info_t *devi)
1617 {
1618 	mptsas_t	*mpt;
1619 	scsi_hba_tran_t *tran;
1620 
1621 	if ((tran = ddi_get_driver_private(devi)) == NULL)
1622 		return (DDI_SUCCESS);
1623 
1624 	if ((mpt = TRAN2MPT(tran)) == NULL)
1625 		return (DDI_SUCCESS);
1626 
1627 	/* Disable HBA interrupts in hardware */
1628 	MPTSAS_DISABLE_INTR(mpt);
1629 
1630 	return (DDI_SUCCESS);
1631 }
1632 #endif	/* __sparc */
1633 
1634 /*
1635  * detach(9E).	Remove all device allocations and system resources;
1636  * disable device interrupts.
1637  * Return DDI_SUCCESS if done; DDI_FAILURE if there's a problem.
1638  */
1639 static int
1640 mptsas_detach(dev_info_t *devi, ddi_detach_cmd_t cmd)
1641 {
1642 	/* CONSTCOND */
1643 	ASSERT(NO_COMPETING_THREADS);
1644 	NDBG0(("mptsas_detach: dip=0x%p cmd=0x%p", (void *)devi, (void *)cmd));
1645 
1646 	switch (cmd) {
1647 	case DDI_DETACH:
1648 		return (mptsas_do_detach(devi));
1649 
1650 	case DDI_SUSPEND:
1651 		return (mptsas_suspend(devi));
1652 
1653 	default:
1654 		return (DDI_FAILURE);
1655 	}
1656 	/* NOTREACHED */
1657 }
1658 
1659 static int
1660 mptsas_do_detach(dev_info_t *dip)
1661 {
1662 	mptsas_t	*mpt, *m;
1663 	scsi_hba_tran_t	*tran;
1664 	mptsas_slots_t	*active;
1665 	int		circ = 0;
1666 	int		circ1 = 0;
1667 	mdi_pathinfo_t	*pip = NULL;
1668 	int		i;
1669 	int		doneq_thread_num = 0;
1670 
1671 	NDBG0(("mptsas_do_detach: dip=0x%p", (void *)dip));
1672 
1673 	if ((tran = ndi_flavorv_get(dip, SCSA_FLAVOR_SCSI_DEVICE)) == NULL)
1674 		return (DDI_FAILURE);
1675 
1676 	mpt = TRAN2MPT(tran);
1677 	if (!mpt) {
1678 		return (DDI_FAILURE);
1679 	}
1680 	/*
1681 	 * Still have pathinfo child, should not detach mpt driver
1682 	 */
1683 	if (scsi_hba_iport_unit_address(dip)) {
1684 		if (mpt->m_mpxio_enable) {
1685 			/*
1686 			 * MPxIO enabled for the iport
1687 			 */
1688 			ndi_devi_enter(scsi_vhci_dip, &circ1);
1689 			ndi_devi_enter(dip, &circ);
1690 			while (pip = mdi_get_next_client_path(dip, NULL)) {
1691 				if (mdi_pi_free(pip, 0) == MDI_SUCCESS) {
1692 					continue;
1693 				}
1694 				ndi_devi_exit(dip, circ);
1695 				ndi_devi_exit(scsi_vhci_dip, circ1);
1696 				NDBG12(("detach failed because of "
1697 				    "outstanding path info"));
1698 				return (DDI_FAILURE);
1699 			}
1700 			ndi_devi_exit(dip, circ);
1701 			ndi_devi_exit(scsi_vhci_dip, circ1);
1702 			(void) mdi_phci_unregister(dip, 0);
1703 		}
1704 
1705 		ddi_prop_remove_all(dip);
1706 
1707 		return (DDI_SUCCESS);
1708 	}
1709 
1710 	/* Make sure power level is D0 before accessing registers */
1711 	if (mpt->m_options & MPTSAS_OPT_PM) {
1712 		(void) pm_busy_component(dip, 0);
1713 		if (mpt->m_power_level != PM_LEVEL_D0) {
1714 			if (pm_raise_power(dip, 0, PM_LEVEL_D0) !=
1715 			    DDI_SUCCESS) {
1716 				mptsas_log(mpt, CE_WARN,
1717 				    "mptsas%d: Raise power request failed.",
1718 				    mpt->m_instance);
1719 				(void) pm_idle_component(dip, 0);
1720 				return (DDI_FAILURE);
1721 			}
1722 		}
1723 	}
1724 
1725 	mutex_enter(&mpt->m_mutex);
1726 	MPTSAS_DISABLE_INTR(mpt);
1727 	mutex_exit(&mpt->m_mutex);
1728 	mptsas_rem_intrs(mpt);
1729 	ddi_taskq_destroy(mpt->m_event_taskq);
1730 	ddi_taskq_destroy(mpt->m_dr_taskq);
1731 
1732 	if (mpt->m_doneq_thread_n) {
1733 		mutex_enter(&mpt->m_doneq_mutex);
1734 		doneq_thread_num = mpt->m_doneq_thread_n;
1735 		for (i = 0; i < mpt->m_doneq_thread_n; i++) {
1736 			mutex_enter(&mpt->m_doneq_thread_id[i].mutex);
1737 			mpt->m_doneq_thread_id[i].flag &=
1738 			    (~MPTSAS_DONEQ_THREAD_ACTIVE);
1739 			cv_signal(&mpt->m_doneq_thread_id[i].cv);
1740 			mutex_exit(&mpt->m_doneq_thread_id[i].mutex);
1741 		}
1742 		while (mpt->m_doneq_thread_n) {
1743 			cv_wait(&mpt->m_doneq_thread_cv,
1744 			    &mpt->m_doneq_mutex);
1745 		}
1746 		for (i = 0;  i < doneq_thread_num; i++) {
1747 			cv_destroy(&mpt->m_doneq_thread_id[i].cv);
1748 			mutex_destroy(&mpt->m_doneq_thread_id[i].mutex);
1749 		}
1750 		kmem_free(mpt->m_doneq_thread_id,
1751 		    sizeof (mptsas_doneq_thread_list_t)
1752 		    * doneq_thread_num);
1753 		mutex_exit(&mpt->m_doneq_mutex);
1754 		cv_destroy(&mpt->m_doneq_thread_cv);
1755 		mutex_destroy(&mpt->m_doneq_mutex);
1756 	}
1757 
1758 	scsi_hba_reset_notify_tear_down(mpt->m_reset_notify_listf);
1759 
1760 	/*
1761 	 * Remove device instance from the global linked list
1762 	 */
1763 	rw_enter(&mptsas_global_rwlock, RW_WRITER);
1764 	if (mptsas_head == mpt) {
1765 		m = mptsas_head = mpt->m_next;
1766 	} else {
1767 		for (m = mptsas_head; m != NULL; m = m->m_next) {
1768 			if (m->m_next == mpt) {
1769 				m->m_next = mpt->m_next;
1770 				break;
1771 			}
1772 		}
1773 		if (m == NULL) {
1774 			mptsas_log(mpt, CE_PANIC, "Not in softc list!");
1775 		}
1776 	}
1777 
1778 	if (mptsas_tail == mpt) {
1779 		mptsas_tail = m;
1780 	}
1781 	rw_exit(&mptsas_global_rwlock);
1782 
1783 	/*
1784 	 * Cancel timeout threads for this mpt
1785 	 */
1786 	mutex_enter(&mpt->m_mutex);
1787 	if (mpt->m_quiesce_timeid) {
1788 		timeout_id_t tid = mpt->m_quiesce_timeid;
1789 		mpt->m_quiesce_timeid = 0;
1790 		mutex_exit(&mpt->m_mutex);
1791 		(void) untimeout(tid);
1792 		mutex_enter(&mpt->m_mutex);
1793 	}
1794 
1795 	if (mpt->m_restart_cmd_timeid) {
1796 		timeout_id_t tid = mpt->m_restart_cmd_timeid;
1797 		mpt->m_restart_cmd_timeid = 0;
1798 		mutex_exit(&mpt->m_mutex);
1799 		(void) untimeout(tid);
1800 		mutex_enter(&mpt->m_mutex);
1801 	}
1802 
1803 	if (mpt->m_pm_timeid != 0) {
1804 		timeout_id_t tid = mpt->m_pm_timeid;
1805 		mpt->m_pm_timeid = 0;
1806 		mutex_exit(&mpt->m_mutex);
1807 		(void) untimeout(tid);
1808 		/*
1809 		 * Report idle status for last ioctl since
1810 		 * calls to pm_busy_component(9F) are stacked.
1811 		 */
1812 		(void) pm_idle_component(mpt->m_dip, 0);
1813 		mutex_enter(&mpt->m_mutex);
1814 	}
1815 	mutex_exit(&mpt->m_mutex);
1816 
1817 	/*
1818 	 * last mpt? ... if active, CANCEL watch threads.
1819 	 */
1820 	mutex_enter(&mptsas_global_mutex);
1821 	if (mptsas_head == NULL) {
1822 		timeout_id_t tid;
1823 		/*
1824 		 * Clear mptsas_timeouts_enable so that the watch thread
1825 		 * gets restarted on DDI_ATTACH
1826 		 */
1827 		mptsas_timeouts_enabled = 0;
1828 		if (mptsas_timeout_id) {
1829 			tid = mptsas_timeout_id;
1830 			mptsas_timeout_id = 0;
1831 			mutex_exit(&mptsas_global_mutex);
1832 			(void) untimeout(tid);
1833 			mutex_enter(&mptsas_global_mutex);
1834 		}
1835 		if (mptsas_reset_watch) {
1836 			tid = mptsas_reset_watch;
1837 			mptsas_reset_watch = 0;
1838 			mutex_exit(&mptsas_global_mutex);
1839 			(void) untimeout(tid);
1840 			mutex_enter(&mptsas_global_mutex);
1841 		}
1842 	}
1843 	mutex_exit(&mptsas_global_mutex);
1844 
1845 	/*
1846 	 * Delete nt_active.
1847 	 */
1848 	active = mpt->m_active;
1849 	mutex_enter(&mpt->m_mutex);
1850 	mptsas_hash_uninit(&active->m_smptbl, sizeof (mptsas_smp_t));
1851 	mutex_exit(&mpt->m_mutex);
1852 
1853 	if (active) {
1854 		kmem_free(active, active->m_size);
1855 		mpt->m_active = NULL;
1856 	}
1857 
1858 	/* deallocate everything that was allocated in mptsas_attach */
1859 	mptsas_fm_fini(mpt);
1860 	kmem_cache_destroy(mpt->m_cache_frames);
1861 	kmem_cache_destroy(mpt->m_kmem_cache);
1862 
1863 	(void) scsi_hba_detach(dip);
1864 	(void) sas_hba_detach(dip);
1865 	mptsas_free_handshake_msg(mpt);
1866 	mptsas_hba_fini(mpt);
1867 	mptsas_cfg_fini(mpt);
1868 
1869 	/* Lower the power informing PM Framework */
1870 	if (mpt->m_options & MPTSAS_OPT_PM) {
1871 		if (pm_lower_power(dip, 0, PM_LEVEL_D3) != DDI_SUCCESS)
1872 			mptsas_log(mpt, CE_WARN,
1873 			    "!mptsas%d: Lower power request failed "
1874 			    "during detach, ignoring.",
1875 			    mpt->m_instance);
1876 	}
1877 
1878 	mutex_destroy(&mpt->m_tx_waitq_mutex);
1879 	mutex_destroy(&mpt->m_mutex);
1880 	cv_destroy(&mpt->m_cv);
1881 	cv_destroy(&mpt->m_passthru_cv);
1882 	cv_destroy(&mpt->m_fw_cv);
1883 	cv_destroy(&mpt->m_config_cv);
1884 
1885 	pci_config_teardown(&mpt->m_config_handle);
1886 	if (mpt->m_tran) {
1887 		scsi_hba_tran_free(mpt->m_tran);
1888 		mpt->m_tran = NULL;
1889 	}
1890 
1891 	if (mpt->m_smptran) {
1892 		sas_hba_tran_free(mpt->m_smptran);
1893 		mpt->m_smptran = NULL;
1894 	}
1895 
1896 	ddi_soft_state_free(mptsas_state, ddi_get_instance(dip));
1897 	ddi_prop_remove_all(dip);
1898 
1899 	return (DDI_SUCCESS);
1900 }
1901 
1902 static int
1903 mptsas_alloc_handshake_msg(mptsas_t *mpt, size_t alloc_size)
1904 {
1905 	ddi_dma_attr_t		task_dma_attrs;
1906 	ddi_dma_cookie_t	tmp_dma_cookie;
1907 	size_t			alloc_len;
1908 	uint_t			ncookie;
1909 
1910 	/* allocate Task Management ddi_dma resources */
1911 	task_dma_attrs = mpt->m_msg_dma_attr;
1912 	task_dma_attrs.dma_attr_sgllen = 1;
1913 	task_dma_attrs.dma_attr_granular = (uint32_t)(alloc_size);
1914 
1915 	if (ddi_dma_alloc_handle(mpt->m_dip, &task_dma_attrs,
1916 	    DDI_DMA_SLEEP, NULL, &mpt->m_hshk_dma_hdl) != DDI_SUCCESS) {
1917 		mpt->m_hshk_dma_hdl = NULL;
1918 		return (DDI_FAILURE);
1919 	}
1920 
1921 	if (ddi_dma_mem_alloc(mpt->m_hshk_dma_hdl, alloc_size,
1922 	    &mpt->m_dev_acc_attr, DDI_DMA_CONSISTENT, DDI_DMA_SLEEP, NULL,
1923 	    &mpt->m_hshk_memp, &alloc_len, &mpt->m_hshk_acc_hdl)
1924 	    != DDI_SUCCESS) {
1925 		ddi_dma_free_handle(&mpt->m_hshk_dma_hdl);
1926 		mpt->m_hshk_dma_hdl = NULL;
1927 		return (DDI_FAILURE);
1928 	}
1929 
1930 	if (ddi_dma_addr_bind_handle(mpt->m_hshk_dma_hdl, NULL,
1931 	    mpt->m_hshk_memp, alloc_len, (DDI_DMA_RDWR | DDI_DMA_CONSISTENT),
1932 	    DDI_DMA_SLEEP, NULL, &tmp_dma_cookie, &ncookie)
1933 	    != DDI_DMA_MAPPED) {
1934 		(void) ddi_dma_mem_free(&mpt->m_hshk_acc_hdl);
1935 		ddi_dma_free_handle(&mpt->m_hshk_dma_hdl);
1936 		mpt->m_hshk_dma_hdl = NULL;
1937 		return (DDI_FAILURE);
1938 	}
1939 	mpt->m_hshk_dma_size = alloc_size;
1940 	return (DDI_SUCCESS);
1941 }
1942 
1943 static void
1944 mptsas_free_handshake_msg(mptsas_t *mpt)
1945 {
1946 	if (mpt->m_hshk_dma_hdl != NULL) {
1947 		(void) ddi_dma_unbind_handle(mpt->m_hshk_dma_hdl);
1948 		(void) ddi_dma_mem_free(&mpt->m_hshk_acc_hdl);
1949 		ddi_dma_free_handle(&mpt->m_hshk_dma_hdl);
1950 		mpt->m_hshk_dma_hdl = NULL;
1951 		mpt->m_hshk_dma_size = 0;
1952 	}
1953 }
1954 
1955 static int
1956 mptsas_power(dev_info_t *dip, int component, int level)
1957 {
1958 #ifndef __lock_lint
1959 	_NOTE(ARGUNUSED(component))
1960 #endif
1961 	mptsas_t	*mpt;
1962 	int		rval = DDI_SUCCESS;
1963 	int		polls = 0;
1964 	uint32_t	ioc_status;
1965 
1966 	if (scsi_hba_iport_unit_address(dip) != 0)
1967 		return (DDI_SUCCESS);
1968 
1969 	mpt = ddi_get_soft_state(mptsas_state, ddi_get_instance(dip));
1970 	if (mpt == NULL) {
1971 		return (DDI_FAILURE);
1972 	}
1973 
1974 	mutex_enter(&mpt->m_mutex);
1975 
1976 	/*
1977 	 * If the device is busy, don't lower its power level
1978 	 */
1979 	if (mpt->m_busy && (mpt->m_power_level > level)) {
1980 		mutex_exit(&mpt->m_mutex);
1981 		return (DDI_FAILURE);
1982 	}
1983 
1984 	switch (level) {
1985 	case PM_LEVEL_D0:
1986 		NDBG11(("mptsas%d: turning power ON.", mpt->m_instance));
1987 		MPTSAS_POWER_ON(mpt);
1988 		/*
1989 		 * Wait up to 30 seconds for IOC to come out of reset.
1990 		 */
1991 		while (((ioc_status = ddi_get32(mpt->m_datap,
1992 		    &mpt->m_reg->Doorbell)) &
1993 		    MPI2_IOC_STATE_MASK) == MPI2_IOC_STATE_RESET) {
1994 			if (polls++ > 3000) {
1995 				break;
1996 			}
1997 			delay(drv_usectohz(10000));
1998 		}
1999 		/*
2000 		 * If IOC is not in operational state, try to hard reset it.
2001 		 */
2002 		if ((ioc_status & MPI2_IOC_STATE_MASK) !=
2003 		    MPI2_IOC_STATE_OPERATIONAL) {
2004 			if (mptsas_restart_ioc(mpt) == DDI_FAILURE) {
2005 				mptsas_log(mpt, CE_WARN,
2006 				    "mptsas_power: hard reset failed");
2007 				mutex_exit(&mpt->m_mutex);
2008 				return (DDI_FAILURE);
2009 			}
2010 		}
2011 		mpt->m_power_level = PM_LEVEL_D0;
2012 		break;
2013 	case PM_LEVEL_D3:
2014 		NDBG11(("mptsas%d: turning power OFF.", mpt->m_instance));
2015 		MPTSAS_POWER_OFF(mpt);
2016 		break;
2017 	default:
2018 		mptsas_log(mpt, CE_WARN, "mptsas%d: unknown power level <%x>.",
2019 		    mpt->m_instance, level);
2020 		rval = DDI_FAILURE;
2021 		break;
2022 	}
2023 	mutex_exit(&mpt->m_mutex);
2024 	return (rval);
2025 }
2026 
2027 /*
2028  * Initialize configuration space and figure out which
2029  * chip and revison of the chip the mpt driver is using.
2030  */
2031 int
2032 mptsas_config_space_init(mptsas_t *mpt)
2033 {
2034 	ushort_t	caps_ptr, cap, cap_count;
2035 
2036 	NDBG0(("mptsas_config_space_init"));
2037 
2038 	mptsas_setup_cmd_reg(mpt);
2039 
2040 	/*
2041 	 * Get the chip device id:
2042 	 */
2043 	mpt->m_devid = pci_config_get16(mpt->m_config_handle, PCI_CONF_DEVID);
2044 
2045 	/*
2046 	 * Save the revision.
2047 	 */
2048 	mpt->m_revid = pci_config_get8(mpt->m_config_handle, PCI_CONF_REVID);
2049 
2050 	/*
2051 	 * Save the SubSystem Vendor and Device IDs
2052 	 */
2053 	mpt->m_svid = pci_config_get16(mpt->m_config_handle, PCI_CONF_SUBVENID);
2054 	mpt->m_ssid = pci_config_get16(mpt->m_config_handle, PCI_CONF_SUBSYSID);
2055 
2056 	/*
2057 	 * Set the latency timer to 0x40 as specified by the upa -> pci
2058 	 * bridge chip design team.  This may be done by the sparc pci
2059 	 * bus nexus driver, but the driver should make sure the latency
2060 	 * timer is correct for performance reasons.
2061 	 */
2062 	pci_config_put8(mpt->m_config_handle, PCI_CONF_LATENCY_TIMER,
2063 	    MPTSAS_LATENCY_TIMER);
2064 
2065 	/*
2066 	 * Check if capabilities list is supported and if so,
2067 	 * get initial capabilities pointer and clear bits 0,1.
2068 	 */
2069 	if (pci_config_get16(mpt->m_config_handle, PCI_CONF_STAT)
2070 	    & PCI_STAT_CAP) {
2071 		caps_ptr = P2ALIGN(pci_config_get8(mpt->m_config_handle,
2072 		    PCI_CONF_CAP_PTR), 4);
2073 	} else {
2074 		caps_ptr = PCI_CAP_NEXT_PTR_NULL;
2075 	}
2076 
2077 	/*
2078 	 * Walk capabilities if supported.
2079 	 */
2080 	for (cap_count = 0; caps_ptr != PCI_CAP_NEXT_PTR_NULL; ) {
2081 
2082 		/*
2083 		 * Check that we haven't exceeded the maximum number of
2084 		 * capabilities and that the pointer is in a valid range.
2085 		 */
2086 		if (++cap_count > 48) {
2087 			mptsas_log(mpt, CE_WARN,
2088 			    "too many device capabilities.\n");
2089 			return (FALSE);
2090 		}
2091 		if (caps_ptr < 64) {
2092 			mptsas_log(mpt, CE_WARN,
2093 			    "capabilities pointer 0x%x out of range.\n",
2094 			    caps_ptr);
2095 			return (FALSE);
2096 		}
2097 
2098 		/*
2099 		 * Get next capability and check that it is valid.
2100 		 * For now, we only support power management.
2101 		 */
2102 		cap = pci_config_get8(mpt->m_config_handle, caps_ptr);
2103 		switch (cap) {
2104 			case PCI_CAP_ID_PM:
2105 				mptsas_log(mpt, CE_NOTE,
2106 				    "?mptsas%d supports power management.\n",
2107 				    mpt->m_instance);
2108 				mpt->m_options |= MPTSAS_OPT_PM;
2109 
2110 				/* Save PMCSR offset */
2111 				mpt->m_pmcsr_offset = caps_ptr + PCI_PMCSR;
2112 				break;
2113 
2114 			/*
2115 			 * 0x5 is Message signaled interrupts and 0x7
2116 			 * is pci-x capable.  Both are unsupported for now
2117 			 * but supported by the 1030 chip so we don't
2118 			 * need to keep printing out the notice.
2119 			 * 0x10 is PCI-E support (1064E/1068E)
2120 			 * 0x11 is MSIX supported by the 1064/1068
2121 			 */
2122 			case 0x5:
2123 			case 0x7:
2124 			case 0x10:
2125 			case 0x11:
2126 				break;
2127 			default:
2128 				mptsas_log(mpt, CE_NOTE,
2129 				    "?mptsas%d unrecognized capability "
2130 				    "0x%x.\n", mpt->m_instance, cap);
2131 			break;
2132 		}
2133 
2134 		/*
2135 		 * Get next capabilities pointer and clear bits 0,1.
2136 		 */
2137 		caps_ptr = P2ALIGN(pci_config_get8(mpt->m_config_handle,
2138 		    (caps_ptr + PCI_CAP_NEXT_PTR)), 4);
2139 	}
2140 
2141 	return (TRUE);
2142 }
2143 
2144 static void
2145 mptsas_setup_cmd_reg(mptsas_t *mpt)
2146 {
2147 	ushort_t	cmdreg;
2148 
2149 	/*
2150 	 * Set the command register to the needed values.
2151 	 */
2152 	cmdreg = pci_config_get16(mpt->m_config_handle, PCI_CONF_COMM);
2153 	cmdreg |= (PCI_COMM_ME | PCI_COMM_SERR_ENABLE |
2154 	    PCI_COMM_PARITY_DETECT | PCI_COMM_MAE);
2155 	cmdreg &= ~PCI_COMM_IO;
2156 	pci_config_put16(mpt->m_config_handle, PCI_CONF_COMM, cmdreg);
2157 }
2158 
2159 static void
2160 mptsas_disable_bus_master(mptsas_t *mpt)
2161 {
2162 	ushort_t	cmdreg;
2163 
2164 	/*
2165 	 * Clear the master enable bit in the PCI command register.
2166 	 * This prevents any bus mastering activity like DMA.
2167 	 */
2168 	cmdreg = pci_config_get16(mpt->m_config_handle, PCI_CONF_COMM);
2169 	cmdreg &= ~PCI_COMM_ME;
2170 	pci_config_put16(mpt->m_config_handle, PCI_CONF_COMM, cmdreg);
2171 }
2172 
2173 int
2174 mptsas_passthru_dma_alloc(mptsas_t *mpt, mptsas_dma_alloc_state_t *dma_statep)
2175 {
2176 	ddi_dma_attr_t	attrs;
2177 	uint_t		ncookie;
2178 	size_t		alloc_len;
2179 
2180 	attrs = mpt->m_msg_dma_attr;
2181 	attrs.dma_attr_sgllen = 1;
2182 
2183 	ASSERT(dma_statep != NULL);
2184 
2185 	if (ddi_dma_alloc_handle(mpt->m_dip, &attrs,
2186 	    DDI_DMA_SLEEP, NULL, &dma_statep->handle) != DDI_SUCCESS) {
2187 		mptsas_log(mpt, CE_WARN,
2188 		    "unable to allocate dma handle.");
2189 		return (DDI_FAILURE);
2190 	}
2191 
2192 	if (ddi_dma_mem_alloc(dma_statep->handle, dma_statep->size,
2193 	    &mpt->m_dev_acc_attr, DDI_DMA_CONSISTENT, DDI_DMA_SLEEP, NULL,
2194 	    &dma_statep->memp, &alloc_len, &dma_statep->accessp) !=
2195 	    DDI_SUCCESS) {
2196 		ddi_dma_free_handle(&dma_statep->handle);
2197 		dma_statep->handle = NULL;
2198 		mptsas_log(mpt, CE_WARN,
2199 		    "unable to allocate memory for dma xfer.");
2200 		return (DDI_FAILURE);
2201 	}
2202 
2203 	if (ddi_dma_addr_bind_handle(dma_statep->handle, NULL, dma_statep->memp,
2204 	    alloc_len, DDI_DMA_RDWR | DDI_DMA_CONSISTENT, DDI_DMA_SLEEP,
2205 	    NULL, &dma_statep->cookie, &ncookie) != DDI_DMA_MAPPED) {
2206 		ddi_dma_mem_free(&dma_statep->accessp);
2207 		dma_statep->accessp = NULL;
2208 		ddi_dma_free_handle(&dma_statep->handle);
2209 		dma_statep->handle = NULL;
2210 		mptsas_log(mpt, CE_WARN, "unable to bind DMA resources.");
2211 		return (DDI_FAILURE);
2212 	}
2213 	return (DDI_SUCCESS);
2214 }
2215 
2216 void
2217 mptsas_passthru_dma_free(mptsas_dma_alloc_state_t *dma_statep)
2218 {
2219 	ASSERT(dma_statep != NULL);
2220 	if (dma_statep->handle != NULL) {
2221 		(void) ddi_dma_unbind_handle(dma_statep->handle);
2222 		(void) ddi_dma_mem_free(&dma_statep->accessp);
2223 		ddi_dma_free_handle(&dma_statep->handle);
2224 	}
2225 }
2226 
2227 int
2228 mptsas_do_dma(mptsas_t *mpt, uint32_t size, int var, int (*callback)())
2229 {
2230 	ddi_dma_attr_t		attrs;
2231 	ddi_dma_handle_t	dma_handle;
2232 	caddr_t			memp;
2233 	uint_t			ncookie;
2234 	ddi_dma_cookie_t	cookie;
2235 	ddi_acc_handle_t	accessp;
2236 	size_t			alloc_len;
2237 	int			rval;
2238 
2239 	ASSERT(mutex_owned(&mpt->m_mutex));
2240 
2241 	attrs = mpt->m_msg_dma_attr;
2242 	attrs.dma_attr_sgllen = 1;
2243 	attrs.dma_attr_granular = size;
2244 
2245 	if (ddi_dma_alloc_handle(mpt->m_dip, &attrs,
2246 	    DDI_DMA_SLEEP, NULL, &dma_handle) != DDI_SUCCESS) {
2247 		mptsas_log(mpt, CE_WARN,
2248 		    "unable to allocate dma handle.");
2249 		return (DDI_FAILURE);
2250 	}
2251 
2252 	if (ddi_dma_mem_alloc(dma_handle, size,
2253 	    &mpt->m_dev_acc_attr, DDI_DMA_CONSISTENT, DDI_DMA_SLEEP, NULL,
2254 	    &memp, &alloc_len, &accessp) != DDI_SUCCESS) {
2255 		ddi_dma_free_handle(&dma_handle);
2256 		mptsas_log(mpt, CE_WARN,
2257 		    "unable to allocate request structure.");
2258 		return (DDI_FAILURE);
2259 	}
2260 
2261 	if (ddi_dma_addr_bind_handle(dma_handle, NULL, memp,
2262 	    alloc_len, DDI_DMA_RDWR | DDI_DMA_CONSISTENT, DDI_DMA_SLEEP,
2263 	    NULL, &cookie, &ncookie) != DDI_DMA_MAPPED) {
2264 		(void) ddi_dma_mem_free(&accessp);
2265 		ddi_dma_free_handle(&dma_handle);
2266 		mptsas_log(mpt, CE_WARN, "unable to bind DMA resources.");
2267 		return (DDI_FAILURE);
2268 	}
2269 
2270 	rval = (*callback) (mpt, memp, var, accessp);
2271 
2272 	if ((mptsas_check_dma_handle(dma_handle) != DDI_SUCCESS) ||
2273 	    (mptsas_check_acc_handle(accessp) != DDI_SUCCESS)) {
2274 		ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_UNAFFECTED);
2275 		rval = DDI_FAILURE;
2276 	}
2277 
2278 	if (dma_handle != NULL) {
2279 		(void) ddi_dma_unbind_handle(dma_handle);
2280 		(void) ddi_dma_mem_free(&accessp);
2281 		ddi_dma_free_handle(&dma_handle);
2282 	}
2283 
2284 	return (rval);
2285 
2286 }
2287 
2288 static int
2289 mptsas_alloc_request_frames(mptsas_t *mpt)
2290 {
2291 	ddi_dma_attr_t		frame_dma_attrs;
2292 	caddr_t			memp;
2293 	uint_t			ncookie;
2294 	ddi_dma_cookie_t	cookie;
2295 	size_t			alloc_len;
2296 	size_t			mem_size;
2297 
2298 	/*
2299 	 * The size of the request frame pool is:
2300 	 *   Number of Request Frames * Request Frame Size
2301 	 */
2302 	mem_size = mpt->m_max_requests * mpt->m_req_frame_size;
2303 
2304 	/*
2305 	 * set the DMA attributes.  System Request Message Frames must be
2306 	 * aligned on a 16-byte boundry.
2307 	 */
2308 	frame_dma_attrs = mpt->m_msg_dma_attr;
2309 	frame_dma_attrs.dma_attr_align = 16;
2310 	frame_dma_attrs.dma_attr_sgllen = 1;
2311 
2312 	/*
2313 	 * allocate the request frame pool.
2314 	 */
2315 	if (ddi_dma_alloc_handle(mpt->m_dip, &frame_dma_attrs,
2316 	    DDI_DMA_SLEEP, NULL, &mpt->m_dma_req_frame_hdl) != DDI_SUCCESS) {
2317 		mptsas_log(mpt, CE_WARN,
2318 		    "Unable to allocate dma handle.");
2319 		return (DDI_FAILURE);
2320 	}
2321 
2322 	if (ddi_dma_mem_alloc(mpt->m_dma_req_frame_hdl,
2323 	    mem_size, &mpt->m_dev_acc_attr, DDI_DMA_CONSISTENT, DDI_DMA_SLEEP,
2324 	    NULL, (caddr_t *)&memp, &alloc_len, &mpt->m_acc_req_frame_hdl)
2325 	    != DDI_SUCCESS) {
2326 		ddi_dma_free_handle(&mpt->m_dma_req_frame_hdl);
2327 		mpt->m_dma_req_frame_hdl = NULL;
2328 		mptsas_log(mpt, CE_WARN,
2329 		    "Unable to allocate request frames.");
2330 		return (DDI_FAILURE);
2331 	}
2332 
2333 	if (ddi_dma_addr_bind_handle(mpt->m_dma_req_frame_hdl, NULL,
2334 	    memp, alloc_len, DDI_DMA_RDWR | DDI_DMA_CONSISTENT,
2335 	    DDI_DMA_SLEEP, NULL, &cookie, &ncookie) != DDI_DMA_MAPPED) {
2336 		(void) ddi_dma_mem_free(&mpt->m_acc_req_frame_hdl);
2337 		ddi_dma_free_handle(&mpt->m_dma_req_frame_hdl);
2338 		mpt->m_dma_req_frame_hdl = NULL;
2339 		mptsas_log(mpt, CE_WARN, "Unable to bind DMA resources.");
2340 		return (DDI_FAILURE);
2341 	}
2342 
2343 	/*
2344 	 * Store the request frame memory address.  This chip uses this
2345 	 * address to dma to and from the driver's frame.  The second
2346 	 * address is the address mpt uses to fill in the frame.
2347 	 */
2348 	mpt->m_req_frame_dma_addr = cookie.dmac_laddress;
2349 	mpt->m_req_frame = memp;
2350 
2351 	/*
2352 	 * Clear the request frame pool.
2353 	 */
2354 	bzero(mpt->m_req_frame, alloc_len);
2355 
2356 	return (DDI_SUCCESS);
2357 }
2358 
2359 static int
2360 mptsas_alloc_reply_frames(mptsas_t *mpt)
2361 {
2362 	ddi_dma_attr_t		frame_dma_attrs;
2363 	caddr_t			memp;
2364 	uint_t			ncookie;
2365 	ddi_dma_cookie_t	cookie;
2366 	size_t			alloc_len;
2367 	size_t			mem_size;
2368 
2369 	/*
2370 	 * The size of the reply frame pool is:
2371 	 *   Number of Reply Frames * Reply Frame Size
2372 	 */
2373 	mem_size = mpt->m_max_replies * mpt->m_reply_frame_size;
2374 
2375 	/*
2376 	 * set the DMA attributes.   System Reply Message Frames must be
2377 	 * aligned on a 4-byte boundry.  This is the default.
2378 	 */
2379 	frame_dma_attrs = mpt->m_msg_dma_attr;
2380 	frame_dma_attrs.dma_attr_sgllen = 1;
2381 
2382 	/*
2383 	 * allocate the reply frame pool
2384 	 */
2385 	if (ddi_dma_alloc_handle(mpt->m_dip, &frame_dma_attrs,
2386 	    DDI_DMA_SLEEP, NULL, &mpt->m_dma_reply_frame_hdl) != DDI_SUCCESS) {
2387 		mptsas_log(mpt, CE_WARN,
2388 		    "Unable to allocate dma handle.");
2389 		return (DDI_FAILURE);
2390 	}
2391 
2392 	if (ddi_dma_mem_alloc(mpt->m_dma_reply_frame_hdl,
2393 	    mem_size, &mpt->m_dev_acc_attr, DDI_DMA_CONSISTENT, DDI_DMA_SLEEP,
2394 	    NULL, (caddr_t *)&memp, &alloc_len, &mpt->m_acc_reply_frame_hdl)
2395 	    != DDI_SUCCESS) {
2396 		ddi_dma_free_handle(&mpt->m_dma_reply_frame_hdl);
2397 		mpt->m_dma_reply_frame_hdl = NULL;
2398 		mptsas_log(mpt, CE_WARN,
2399 		    "Unable to allocate reply frames.");
2400 		return (DDI_FAILURE);
2401 	}
2402 
2403 	if (ddi_dma_addr_bind_handle(mpt->m_dma_reply_frame_hdl, NULL,
2404 	    memp, alloc_len, DDI_DMA_RDWR | DDI_DMA_CONSISTENT,
2405 	    DDI_DMA_SLEEP, NULL, &cookie, &ncookie) != DDI_DMA_MAPPED) {
2406 		(void) ddi_dma_mem_free(&mpt->m_acc_reply_frame_hdl);
2407 		ddi_dma_free_handle(&mpt->m_dma_reply_frame_hdl);
2408 		mpt->m_dma_reply_frame_hdl = NULL;
2409 		mptsas_log(mpt, CE_WARN, "Unable to bind DMA resources.");
2410 		return (DDI_FAILURE);
2411 	}
2412 
2413 	/*
2414 	 * Store the reply frame memory address.  This chip uses this
2415 	 * address to dma to and from the driver's frame.  The second
2416 	 * address is the address mpt uses to process the frame.
2417 	 */
2418 	mpt->m_reply_frame_dma_addr = cookie.dmac_laddress;
2419 	mpt->m_reply_frame = memp;
2420 
2421 	/*
2422 	 * Clear the reply frame pool.
2423 	 */
2424 	bzero(mpt->m_reply_frame, alloc_len);
2425 
2426 	return (DDI_SUCCESS);
2427 }
2428 
2429 static int
2430 mptsas_alloc_free_queue(mptsas_t *mpt)
2431 {
2432 	ddi_dma_attr_t		frame_dma_attrs;
2433 	caddr_t			memp;
2434 	uint_t			ncookie;
2435 	ddi_dma_cookie_t	cookie;
2436 	size_t			alloc_len;
2437 	size_t			mem_size;
2438 
2439 	/*
2440 	 * The reply free queue size is:
2441 	 *   Reply Free Queue Depth * 4
2442 	 * The "4" is the size of one 32 bit address (low part of 64-bit
2443 	 *   address)
2444 	 */
2445 	mem_size = mpt->m_free_queue_depth * 4;
2446 
2447 	/*
2448 	 * set the DMA attributes  The Reply Free Queue must be aligned on a
2449 	 * 16-byte boundry.
2450 	 */
2451 	frame_dma_attrs = mpt->m_msg_dma_attr;
2452 	frame_dma_attrs.dma_attr_align = 16;
2453 	frame_dma_attrs.dma_attr_sgllen = 1;
2454 
2455 	/*
2456 	 * allocate the reply free queue
2457 	 */
2458 	if (ddi_dma_alloc_handle(mpt->m_dip, &frame_dma_attrs,
2459 	    DDI_DMA_SLEEP, NULL, &mpt->m_dma_free_queue_hdl) != DDI_SUCCESS) {
2460 		mptsas_log(mpt, CE_WARN,
2461 		    "Unable to allocate dma handle.");
2462 		return (DDI_FAILURE);
2463 	}
2464 
2465 	if (ddi_dma_mem_alloc(mpt->m_dma_free_queue_hdl,
2466 	    mem_size, &mpt->m_dev_acc_attr, DDI_DMA_CONSISTENT, DDI_DMA_SLEEP,
2467 	    NULL, (caddr_t *)&memp, &alloc_len, &mpt->m_acc_free_queue_hdl)
2468 	    != DDI_SUCCESS) {
2469 		ddi_dma_free_handle(&mpt->m_dma_free_queue_hdl);
2470 		mpt->m_dma_free_queue_hdl = NULL;
2471 		mptsas_log(mpt, CE_WARN,
2472 		    "Unable to allocate free queue.");
2473 		return (DDI_FAILURE);
2474 	}
2475 
2476 	if (ddi_dma_addr_bind_handle(mpt->m_dma_free_queue_hdl, NULL,
2477 	    memp, alloc_len, DDI_DMA_RDWR | DDI_DMA_CONSISTENT,
2478 	    DDI_DMA_SLEEP, NULL, &cookie, &ncookie) != DDI_DMA_MAPPED) {
2479 		(void) ddi_dma_mem_free(&mpt->m_acc_free_queue_hdl);
2480 		ddi_dma_free_handle(&mpt->m_dma_free_queue_hdl);
2481 		mpt->m_dma_free_queue_hdl = NULL;
2482 		mptsas_log(mpt, CE_WARN, "Unable to bind DMA resources.");
2483 		return (DDI_FAILURE);
2484 	}
2485 
2486 	/*
2487 	 * Store the reply free queue memory address.  This chip uses this
2488 	 * address to read from the reply free queue.  The second address
2489 	 * is the address mpt uses to manage the queue.
2490 	 */
2491 	mpt->m_free_queue_dma_addr = cookie.dmac_laddress;
2492 	mpt->m_free_queue = memp;
2493 
2494 	/*
2495 	 * Clear the reply free queue memory.
2496 	 */
2497 	bzero(mpt->m_free_queue, alloc_len);
2498 
2499 	return (DDI_SUCCESS);
2500 }
2501 
2502 static int
2503 mptsas_alloc_post_queue(mptsas_t *mpt)
2504 {
2505 	ddi_dma_attr_t		frame_dma_attrs;
2506 	caddr_t			memp;
2507 	uint_t			ncookie;
2508 	ddi_dma_cookie_t	cookie;
2509 	size_t			alloc_len;
2510 	size_t			mem_size;
2511 
2512 	/*
2513 	 * The reply descriptor post queue size is:
2514 	 *   Reply Descriptor Post Queue Depth * 8
2515 	 * The "8" is the size of each descriptor (8 bytes or 64 bits).
2516 	 */
2517 	mem_size = mpt->m_post_queue_depth * 8;
2518 
2519 	/*
2520 	 * set the DMA attributes.  The Reply Descriptor Post Queue must be
2521 	 * aligned on a 16-byte boundry.
2522 	 */
2523 	frame_dma_attrs = mpt->m_msg_dma_attr;
2524 	frame_dma_attrs.dma_attr_align = 16;
2525 	frame_dma_attrs.dma_attr_sgllen = 1;
2526 
2527 	/*
2528 	 * allocate the reply post queue
2529 	 */
2530 	if (ddi_dma_alloc_handle(mpt->m_dip, &frame_dma_attrs,
2531 	    DDI_DMA_SLEEP, NULL, &mpt->m_dma_post_queue_hdl) != DDI_SUCCESS) {
2532 		mptsas_log(mpt, CE_WARN,
2533 		    "Unable to allocate dma handle.");
2534 		return (DDI_FAILURE);
2535 	}
2536 
2537 	if (ddi_dma_mem_alloc(mpt->m_dma_post_queue_hdl,
2538 	    mem_size, &mpt->m_dev_acc_attr, DDI_DMA_CONSISTENT, DDI_DMA_SLEEP,
2539 	    NULL, (caddr_t *)&memp, &alloc_len, &mpt->m_acc_post_queue_hdl)
2540 	    != DDI_SUCCESS) {
2541 		ddi_dma_free_handle(&mpt->m_dma_post_queue_hdl);
2542 		mpt->m_dma_post_queue_hdl = NULL;
2543 		mptsas_log(mpt, CE_WARN,
2544 		    "Unable to allocate post queue.");
2545 		return (DDI_FAILURE);
2546 	}
2547 
2548 	if (ddi_dma_addr_bind_handle(mpt->m_dma_post_queue_hdl, NULL,
2549 	    memp, alloc_len, DDI_DMA_RDWR | DDI_DMA_CONSISTENT,
2550 	    DDI_DMA_SLEEP, NULL, &cookie, &ncookie) != DDI_DMA_MAPPED) {
2551 		(void) ddi_dma_mem_free(&mpt->m_acc_post_queue_hdl);
2552 		ddi_dma_free_handle(&mpt->m_dma_post_queue_hdl);
2553 		mpt->m_dma_post_queue_hdl = NULL;
2554 		mptsas_log(mpt, CE_WARN, "Unable to bind DMA resources.");
2555 		return (DDI_FAILURE);
2556 	}
2557 
2558 	/*
2559 	 * Store the reply descriptor post queue memory address.  This chip
2560 	 * uses this address to write to the reply descriptor post queue.  The
2561 	 * second address is the address mpt uses to manage the queue.
2562 	 */
2563 	mpt->m_post_queue_dma_addr = cookie.dmac_laddress;
2564 	mpt->m_post_queue = memp;
2565 
2566 	/*
2567 	 * Clear the reply post queue memory.
2568 	 */
2569 	bzero(mpt->m_post_queue, alloc_len);
2570 
2571 	return (DDI_SUCCESS);
2572 }
2573 
2574 static int
2575 mptsas_alloc_extra_sgl_frame(mptsas_t *mpt, mptsas_cmd_t *cmd)
2576 {
2577 	mptsas_cache_frames_t	*frames = NULL;
2578 	if (cmd->cmd_extra_frames == NULL) {
2579 		frames = kmem_cache_alloc(mpt->m_cache_frames, KM_NOSLEEP);
2580 		if (frames == NULL) {
2581 			return (DDI_FAILURE);
2582 		}
2583 		cmd->cmd_extra_frames = frames;
2584 	}
2585 	return (DDI_SUCCESS);
2586 }
2587 
2588 static void
2589 mptsas_free_extra_sgl_frame(mptsas_t *mpt, mptsas_cmd_t *cmd)
2590 {
2591 	if (cmd->cmd_extra_frames) {
2592 		kmem_cache_free(mpt->m_cache_frames,
2593 		    (void *)cmd->cmd_extra_frames);
2594 		cmd->cmd_extra_frames = NULL;
2595 	}
2596 }
2597 
2598 static void
2599 mptsas_cfg_fini(mptsas_t *mpt)
2600 {
2601 	NDBG0(("mptsas_cfg_fini"));
2602 	ddi_regs_map_free(&mpt->m_datap);
2603 }
2604 
2605 static void
2606 mptsas_hba_fini(mptsas_t *mpt)
2607 {
2608 	NDBG0(("mptsas_hba_fini"));
2609 
2610 	/*
2611 	 * Disable any bus mastering ability (i.e: DMA) prior to freeing any
2612 	 * allocated DMA resources.
2613 	 */
2614 	if (mpt->m_config_handle != NULL)
2615 		mptsas_disable_bus_master(mpt);
2616 
2617 	/*
2618 	 * Free up any allocated memory
2619 	 */
2620 	if (mpt->m_dma_req_frame_hdl != NULL) {
2621 		(void) ddi_dma_unbind_handle(mpt->m_dma_req_frame_hdl);
2622 		ddi_dma_mem_free(&mpt->m_acc_req_frame_hdl);
2623 		ddi_dma_free_handle(&mpt->m_dma_req_frame_hdl);
2624 		mpt->m_dma_req_frame_hdl = NULL;
2625 	}
2626 
2627 	if (mpt->m_dma_reply_frame_hdl != NULL) {
2628 		(void) ddi_dma_unbind_handle(mpt->m_dma_reply_frame_hdl);
2629 		ddi_dma_mem_free(&mpt->m_acc_reply_frame_hdl);
2630 		ddi_dma_free_handle(&mpt->m_dma_reply_frame_hdl);
2631 		mpt->m_dma_reply_frame_hdl = NULL;
2632 	}
2633 
2634 	if (mpt->m_dma_free_queue_hdl != NULL) {
2635 		(void) ddi_dma_unbind_handle(mpt->m_dma_free_queue_hdl);
2636 		ddi_dma_mem_free(&mpt->m_acc_free_queue_hdl);
2637 		ddi_dma_free_handle(&mpt->m_dma_free_queue_hdl);
2638 		mpt->m_dma_free_queue_hdl = NULL;
2639 	}
2640 
2641 	if (mpt->m_dma_post_queue_hdl != NULL) {
2642 		(void) ddi_dma_unbind_handle(mpt->m_dma_post_queue_hdl);
2643 		ddi_dma_mem_free(&mpt->m_acc_post_queue_hdl);
2644 		ddi_dma_free_handle(&mpt->m_dma_post_queue_hdl);
2645 		mpt->m_dma_post_queue_hdl = NULL;
2646 	}
2647 
2648 	if (mpt->m_replyh_args != NULL) {
2649 		kmem_free(mpt->m_replyh_args, sizeof (m_replyh_arg_t)
2650 		    * mpt->m_max_replies);
2651 	}
2652 }
2653 
2654 static int
2655 mptsas_name_child(dev_info_t *lun_dip, char *name, int len)
2656 {
2657 	int		lun = 0;
2658 	char		*sas_wwn = NULL;
2659 	int		phynum = -1;
2660 	int		reallen = 0;
2661 
2662 	/* Get the target num */
2663 	lun = ddi_prop_get_int(DDI_DEV_T_ANY, lun_dip, DDI_PROP_DONTPASS,
2664 	    LUN_PROP, 0);
2665 
2666 	if (ddi_prop_lookup_string(DDI_DEV_T_ANY, lun_dip, DDI_PROP_DONTPASS,
2667 	    SCSI_ADDR_PROP_TARGET_PORT, &sas_wwn) == DDI_PROP_SUCCESS) {
2668 		/*
2669 		 * Stick in the address of the form "wWWN,LUN"
2670 		 */
2671 		reallen = snprintf(name, len, "w%s,%x", sas_wwn, lun);
2672 		ddi_prop_free(sas_wwn);
2673 	} else if ((phynum = ddi_prop_get_int(DDI_DEV_T_ANY, lun_dip,
2674 	    DDI_PROP_DONTPASS, "sata-phy", -1)) != -1) {
2675 		/*
2676 		 * Stick in the address of form "pPHY,LUN"
2677 		 */
2678 		reallen = snprintf(name, len, "p%x,%x", phynum, lun);
2679 	} else {
2680 		return (DDI_FAILURE);
2681 	}
2682 
2683 	ASSERT(reallen < len);
2684 	if (reallen >= len) {
2685 		mptsas_log(0, CE_WARN, "!mptsas_get_name: name parameter "
2686 		    "length too small, it needs to be %d bytes", reallen + 1);
2687 	}
2688 	return (DDI_SUCCESS);
2689 }
2690 
2691 /*
2692  * tran_tgt_init(9E) - target device instance initialization
2693  */
2694 static int
2695 mptsas_scsi_tgt_init(dev_info_t *hba_dip, dev_info_t *tgt_dip,
2696     scsi_hba_tran_t *hba_tran, struct scsi_device *sd)
2697 {
2698 #ifndef __lock_lint
2699 	_NOTE(ARGUNUSED(hba_tran))
2700 #endif
2701 
2702 	/*
2703 	 * At this point, the scsi_device structure already exists
2704 	 * and has been initialized.
2705 	 *
2706 	 * Use this function to allocate target-private data structures,
2707 	 * if needed by this HBA.  Add revised flow-control and queue
2708 	 * properties for child here, if desired and if you can tell they
2709 	 * support tagged queueing by now.
2710 	 */
2711 	mptsas_t		*mpt;
2712 	int			lun = sd->sd_address.a_lun;
2713 	mdi_pathinfo_t		*pip = NULL;
2714 	mptsas_tgt_private_t	*tgt_private = NULL;
2715 	mptsas_target_t		*ptgt = NULL;
2716 	char			*psas_wwn = NULL;
2717 	int			phymask = 0;
2718 	uint64_t		sas_wwn = 0;
2719 	mpt = SDEV2MPT(sd);
2720 
2721 	ASSERT(scsi_hba_iport_unit_address(hba_dip) != 0);
2722 
2723 	NDBG0(("mptsas_scsi_tgt_init: hbadip=0x%p tgtdip=0x%p lun=%d",
2724 	    (void *)hba_dip, (void *)tgt_dip, lun));
2725 
2726 	if (ndi_dev_is_persistent_node(tgt_dip) == 0) {
2727 		(void) ndi_merge_node(tgt_dip, mptsas_name_child);
2728 		ddi_set_name_addr(tgt_dip, NULL);
2729 		return (DDI_FAILURE);
2730 	}
2731 	/*
2732 	 * phymask is 0 means the virtual port for RAID
2733 	 */
2734 	phymask = ddi_prop_get_int(DDI_DEV_T_ANY, hba_dip, 0,
2735 	    "phymask", 0);
2736 	if (mdi_component_is_client(tgt_dip, NULL) == MDI_SUCCESS) {
2737 		if ((pip = (void *)(sd->sd_private)) == NULL) {
2738 			/*
2739 			 * Very bad news if this occurs. Somehow scsi_vhci has
2740 			 * lost the pathinfo node for this target.
2741 			 */
2742 			return (DDI_NOT_WELL_FORMED);
2743 		}
2744 
2745 		if (mdi_prop_lookup_int(pip, LUN_PROP, &lun) !=
2746 		    DDI_PROP_SUCCESS) {
2747 			mptsas_log(mpt, CE_WARN, "Get lun property failed\n");
2748 			return (DDI_FAILURE);
2749 		}
2750 
2751 		if (mdi_prop_lookup_string(pip, SCSI_ADDR_PROP_TARGET_PORT,
2752 		    &psas_wwn) == MDI_SUCCESS) {
2753 			if (scsi_wwnstr_to_wwn(psas_wwn, &sas_wwn)) {
2754 				sas_wwn = 0;
2755 			}
2756 			(void) mdi_prop_free(psas_wwn);
2757 		}
2758 	} else {
2759 		lun = ddi_prop_get_int(DDI_DEV_T_ANY, tgt_dip,
2760 		    DDI_PROP_DONTPASS, LUN_PROP, 0);
2761 		if (ddi_prop_lookup_string(DDI_DEV_T_ANY, tgt_dip,
2762 		    DDI_PROP_DONTPASS, SCSI_ADDR_PROP_TARGET_PORT, &psas_wwn) ==
2763 		    DDI_PROP_SUCCESS) {
2764 			if (scsi_wwnstr_to_wwn(psas_wwn, &sas_wwn)) {
2765 				sas_wwn = 0;
2766 			}
2767 			ddi_prop_free(psas_wwn);
2768 		} else {
2769 			sas_wwn = 0;
2770 		}
2771 	}
2772 	ASSERT((sas_wwn != 0) || (phymask != 0));
2773 	mutex_enter(&mpt->m_mutex);
2774 	ptgt = mptsas_hash_search(&mpt->m_active->m_tgttbl, sas_wwn, phymask);
2775 	mutex_exit(&mpt->m_mutex);
2776 	if (ptgt == NULL) {
2777 		mptsas_log(mpt, CE_WARN, "!tgt_init: target doesn't exist or "
2778 		    "gone already! phymask:%x, saswwn %"PRIx64, phymask,
2779 		    sas_wwn);
2780 		return (DDI_FAILURE);
2781 	}
2782 	if (hba_tran->tran_tgt_private == NULL) {
2783 		tgt_private = kmem_zalloc(sizeof (mptsas_tgt_private_t),
2784 		    KM_SLEEP);
2785 		tgt_private->t_lun = lun;
2786 		tgt_private->t_private = ptgt;
2787 		hba_tran->tran_tgt_private = tgt_private;
2788 	}
2789 
2790 	if (mdi_component_is_client(tgt_dip, NULL) == MDI_SUCCESS) {
2791 		return (DDI_SUCCESS);
2792 	}
2793 	mutex_enter(&mpt->m_mutex);
2794 
2795 	if (ptgt->m_deviceinfo &
2796 	    (MPI2_SAS_DEVICE_INFO_SATA_DEVICE |
2797 	    MPI2_SAS_DEVICE_INFO_ATAPI_DEVICE)) {
2798 		uchar_t *inq89 = NULL;
2799 		int inq89_len = 0x238;
2800 		int reallen = 0;
2801 		int rval = 0;
2802 		struct sata_id *sid = NULL;
2803 		char model[SATA_ID_MODEL_LEN + 1];
2804 		char fw[SATA_ID_FW_LEN + 1];
2805 		char *vid, *pid;
2806 		int i;
2807 
2808 		mutex_exit(&mpt->m_mutex);
2809 		/*
2810 		 * According SCSI/ATA Translation -2 (SAT-2) revision 01a
2811 		 * chapter 12.4.2 VPD page 89h includes 512 bytes ATA IDENTIFY
2812 		 * DEVICE data or ATA IDENTIFY PACKET DEVICE data.
2813 		 */
2814 		inq89 = kmem_zalloc(inq89_len, KM_SLEEP);
2815 		rval = mptsas_inquiry(mpt, ptgt, 0, 0x89,
2816 		    inq89, inq89_len, &reallen, 1);
2817 
2818 		if (rval != 0) {
2819 			if (inq89 != NULL) {
2820 				kmem_free(inq89, inq89_len);
2821 			}
2822 
2823 			mptsas_log(mpt, CE_WARN, "!mptsas request inquiry page "
2824 			    "0x89 for SATA target:%x failed!", ptgt->m_devhdl);
2825 			return (DDI_SUCCESS);
2826 		}
2827 		sid = (void *)(&inq89[60]);
2828 
2829 		swab(sid->ai_model, model, SATA_ID_MODEL_LEN);
2830 		swab(sid->ai_fw, fw, SATA_ID_FW_LEN);
2831 
2832 		model[SATA_ID_MODEL_LEN] = 0;
2833 		fw[SATA_ID_FW_LEN] = 0;
2834 
2835 		/*
2836 		 * split model into into vid/pid
2837 		 */
2838 		for (i = 0, pid = model; i < SATA_ID_MODEL_LEN; i++, pid++)
2839 			if ((*pid == ' ') || (*pid == '\t'))
2840 				break;
2841 		if (i < SATA_ID_MODEL_LEN) {
2842 			vid = model;
2843 			/*
2844 			 * terminate vid, establish pid
2845 			 */
2846 			*pid++ = 0;
2847 		} else {
2848 			/*
2849 			 * vid will stay "ATA     ", the rule is same
2850 			 * as sata framework implementation.
2851 			 */
2852 			vid = NULL;
2853 			/*
2854 			 * model is all pid
2855 			 */
2856 			pid = model;
2857 		}
2858 
2859 		/*
2860 		 * override SCSA "inquiry-*" properties
2861 		 */
2862 		if (vid)
2863 			(void) scsi_device_prop_update_inqstring(sd,
2864 			    INQUIRY_VENDOR_ID, vid, strlen(vid));
2865 		if (pid)
2866 			(void) scsi_device_prop_update_inqstring(sd,
2867 			    INQUIRY_PRODUCT_ID, pid, strlen(pid));
2868 		(void) scsi_device_prop_update_inqstring(sd,
2869 		    INQUIRY_REVISION_ID, fw, strlen(fw));
2870 
2871 		if (inq89 != NULL) {
2872 			kmem_free(inq89, inq89_len);
2873 		}
2874 	} else {
2875 		mutex_exit(&mpt->m_mutex);
2876 	}
2877 
2878 	return (DDI_SUCCESS);
2879 }
2880 /*
2881  * tran_tgt_free(9E) - target device instance deallocation
2882  */
2883 static void
2884 mptsas_scsi_tgt_free(dev_info_t *hba_dip, dev_info_t *tgt_dip,
2885     scsi_hba_tran_t *hba_tran, struct scsi_device *sd)
2886 {
2887 #ifndef __lock_lint
2888 	_NOTE(ARGUNUSED(hba_dip, tgt_dip, hba_tran, sd))
2889 #endif
2890 
2891 	mptsas_tgt_private_t	*tgt_private = hba_tran->tran_tgt_private;
2892 
2893 	if (tgt_private != NULL) {
2894 		kmem_free(tgt_private, sizeof (mptsas_tgt_private_t));
2895 		hba_tran->tran_tgt_private = NULL;
2896 	}
2897 }
2898 
2899 /*
2900  * scsi_pkt handling
2901  *
2902  * Visible to the external world via the transport structure.
2903  */
2904 
2905 /*
2906  * Notes:
2907  *	- transport the command to the addressed SCSI target/lun device
2908  *	- normal operation is to schedule the command to be transported,
2909  *	  and return TRAN_ACCEPT if this is successful.
2910  *	- if NO_INTR, tran_start must poll device for command completion
2911  */
2912 static int
2913 mptsas_scsi_start(struct scsi_address *ap, struct scsi_pkt *pkt)
2914 {
2915 #ifndef __lock_lint
2916 	_NOTE(ARGUNUSED(ap))
2917 #endif
2918 	mptsas_t	*mpt = PKT2MPT(pkt);
2919 	mptsas_cmd_t	*cmd = PKT2CMD(pkt);
2920 	int		rval;
2921 	mptsas_target_t	*ptgt = cmd->cmd_tgt_addr;
2922 
2923 	NDBG1(("mptsas_scsi_start: pkt=0x%p", (void *)pkt));
2924 	ASSERT(ptgt);
2925 	if (ptgt == NULL)
2926 		return (TRAN_FATAL_ERROR);
2927 
2928 	/*
2929 	 * prepare the pkt before taking mutex.
2930 	 */
2931 	rval = mptsas_prepare_pkt(cmd);
2932 	if (rval != TRAN_ACCEPT) {
2933 		return (rval);
2934 	}
2935 
2936 	/*
2937 	 * Send the command to target/lun, however your HBA requires it.
2938 	 * If busy, return TRAN_BUSY; if there's some other formatting error
2939 	 * in the packet, return TRAN_BADPKT; otherwise, fall through to the
2940 	 * return of TRAN_ACCEPT.
2941 	 *
2942 	 * Remember that access to shared resources, including the mptsas_t
2943 	 * data structure and the HBA hardware registers, must be protected
2944 	 * with mutexes, here and everywhere.
2945 	 *
2946 	 * Also remember that at interrupt time, you'll get an argument
2947 	 * to the interrupt handler which is a pointer to your mptsas_t
2948 	 * structure; you'll have to remember which commands are outstanding
2949 	 * and which scsi_pkt is the currently-running command so the
2950 	 * interrupt handler can refer to the pkt to set completion
2951 	 * status, call the target driver back through pkt_comp, etc.
2952 	 *
2953 	 * If the instance lock is held by other thread, don't spin to wait
2954 	 * for it. Instead, queue the cmd and next time when the instance lock
2955 	 * is not held, accept all the queued cmd. A extra tx_waitq is
2956 	 * introduced to protect the queue.
2957 	 *
2958 	 * The polled cmd will not be queud and accepted as usual.
2959 	 *
2960 	 * Under the tx_waitq mutex, record whether a thread is draining
2961 	 * the tx_waitq.  An IO requesting thread that finds the instance
2962 	 * mutex contended appends to the tx_waitq and while holding the
2963 	 * tx_wait mutex, if the draining flag is not set, sets it and then
2964 	 * proceeds to spin for the instance mutex. This scheme ensures that
2965 	 * the last cmd in a burst be processed.
2966 	 *
2967 	 * we enable this feature only when the helper threads are enabled,
2968 	 * at which we think the loads are heavy.
2969 	 *
2970 	 * per instance mutex m_tx_waitq_mutex is introduced to protect the
2971 	 * m_tx_waitqtail, m_tx_waitq, m_tx_draining.
2972 	 */
2973 
2974 	if (mpt->m_doneq_thread_n) {
2975 		if (mutex_tryenter(&mpt->m_mutex) != 0) {
2976 			rval = mptsas_accept_txwq_and_pkt(mpt, cmd);
2977 			mutex_exit(&mpt->m_mutex);
2978 		} else if (cmd->cmd_pkt_flags & FLAG_NOINTR) {
2979 			mutex_enter(&mpt->m_mutex);
2980 			rval = mptsas_accept_txwq_and_pkt(mpt, cmd);
2981 			mutex_exit(&mpt->m_mutex);
2982 		} else {
2983 			mutex_enter(&mpt->m_tx_waitq_mutex);
2984 			/*
2985 			 * ptgt->m_dr_flag is protected by m_mutex or
2986 			 * m_tx_waitq_mutex. In this case, m_tx_waitq_mutex
2987 			 * is acquired.
2988 			 */
2989 			if (ptgt->m_dr_flag == MPTSAS_DR_INTRANSITION) {
2990 				if (cmd->cmd_pkt_flags & FLAG_NOQUEUE) {
2991 					/*
2992 					 * The command should be allowed to
2993 					 * retry by returning TRAN_BUSY to
2994 					 * to stall the I/O's which come from
2995 					 * scsi_vhci since the device/path is
2996 					 * in unstable state now.
2997 					 */
2998 					mutex_exit(&mpt->m_tx_waitq_mutex);
2999 					return (TRAN_BUSY);
3000 				} else {
3001 					/*
3002 					 * The device is offline, just fail the
3003 					 * command by returning
3004 					 * TRAN_FATAL_ERROR.
3005 					 */
3006 					mutex_exit(&mpt->m_tx_waitq_mutex);
3007 					return (TRAN_FATAL_ERROR);
3008 				}
3009 			}
3010 			if (mpt->m_tx_draining) {
3011 				cmd->cmd_flags |= CFLAG_TXQ;
3012 				*mpt->m_tx_waitqtail = cmd;
3013 				mpt->m_tx_waitqtail = &cmd->cmd_linkp;
3014 				mutex_exit(&mpt->m_tx_waitq_mutex);
3015 			} else { /* drain the queue */
3016 				mpt->m_tx_draining = 1;
3017 				mutex_exit(&mpt->m_tx_waitq_mutex);
3018 				mutex_enter(&mpt->m_mutex);
3019 				rval = mptsas_accept_txwq_and_pkt(mpt, cmd);
3020 				mutex_exit(&mpt->m_mutex);
3021 			}
3022 		}
3023 	} else {
3024 		mutex_enter(&mpt->m_mutex);
3025 		/*
3026 		 * ptgt->m_dr_flag is protected by m_mutex or m_tx_waitq_mutex
3027 		 * in this case, m_mutex is acquired.
3028 		 */
3029 		if (ptgt->m_dr_flag == MPTSAS_DR_INTRANSITION) {
3030 			if (cmd->cmd_pkt_flags & FLAG_NOQUEUE) {
3031 				/*
3032 				 * commands should be allowed to retry by
3033 				 * returning TRAN_BUSY to stall the I/O's
3034 				 * which come from scsi_vhci since the device/
3035 				 * path is in unstable state now.
3036 				 */
3037 				mutex_exit(&mpt->m_mutex);
3038 				return (TRAN_BUSY);
3039 			} else {
3040 				/*
3041 				 * The device is offline, just fail the
3042 				 * command by returning TRAN_FATAL_ERROR.
3043 				 */
3044 				mutex_exit(&mpt->m_mutex);
3045 				return (TRAN_FATAL_ERROR);
3046 			}
3047 		}
3048 		rval = mptsas_accept_pkt(mpt, cmd);
3049 		mutex_exit(&mpt->m_mutex);
3050 	}
3051 
3052 	return (rval);
3053 }
3054 
3055 /*
3056  * Accept all the queued cmds(if any) before accept the current one.
3057  */
3058 static int
3059 mptsas_accept_txwq_and_pkt(mptsas_t *mpt, mptsas_cmd_t *cmd)
3060 {
3061 	int rval;
3062 	mptsas_target_t	*ptgt = cmd->cmd_tgt_addr;
3063 
3064 	ASSERT(mutex_owned(&mpt->m_mutex));
3065 	/*
3066 	 * The call to mptsas_accept_tx_waitq() must always be performed
3067 	 * because that is where mpt->m_tx_draining is cleared.
3068 	 */
3069 	mutex_enter(&mpt->m_tx_waitq_mutex);
3070 	mptsas_accept_tx_waitq(mpt);
3071 	mutex_exit(&mpt->m_tx_waitq_mutex);
3072 	/*
3073 	 * ptgt->m_dr_flag is protected by m_mutex or m_tx_waitq_mutex
3074 	 * in this case, m_mutex is acquired.
3075 	 */
3076 	if (ptgt->m_dr_flag == MPTSAS_DR_INTRANSITION) {
3077 		if (cmd->cmd_pkt_flags & FLAG_NOQUEUE) {
3078 			/*
3079 			 * The command should be allowed to retry by returning
3080 			 * TRAN_BUSY to stall the I/O's which come from
3081 			 * scsi_vhci since the device/path is in unstable state
3082 			 * now.
3083 			 */
3084 			return (TRAN_BUSY);
3085 		} else {
3086 			/*
3087 			 * The device is offline, just fail the command by
3088 			 * return TRAN_FATAL_ERROR.
3089 			 */
3090 			return (TRAN_FATAL_ERROR);
3091 		}
3092 	}
3093 	rval = mptsas_accept_pkt(mpt, cmd);
3094 
3095 	return (rval);
3096 }
3097 
3098 static int
3099 mptsas_accept_pkt(mptsas_t *mpt, mptsas_cmd_t *cmd)
3100 {
3101 	int		rval = TRAN_ACCEPT;
3102 	mptsas_target_t	*ptgt = cmd->cmd_tgt_addr;
3103 
3104 	NDBG1(("mptsas_accept_pkt: cmd=0x%p", (void *)cmd));
3105 
3106 	ASSERT(mutex_owned(&mpt->m_mutex));
3107 
3108 	if ((cmd->cmd_flags & CFLAG_PREPARED) == 0) {
3109 		rval = mptsas_prepare_pkt(cmd);
3110 		if (rval != TRAN_ACCEPT) {
3111 			cmd->cmd_flags &= ~CFLAG_TRANFLAG;
3112 			return (rval);
3113 		}
3114 	}
3115 
3116 	/*
3117 	 * reset the throttle if we were draining
3118 	 */
3119 	if ((ptgt->m_t_ncmds == 0) &&
3120 	    (ptgt->m_t_throttle == DRAIN_THROTTLE)) {
3121 		NDBG23(("reset throttle"));
3122 		ASSERT(ptgt->m_reset_delay == 0);
3123 		mptsas_set_throttle(mpt, ptgt, MAX_THROTTLE);
3124 	}
3125 
3126 	/*
3127 	 * If device handle has already been invalidated, just
3128 	 * fail the command. In theory, command from scsi_vhci
3129 	 * client is impossible send down command with invalid
3130 	 * devhdl since devhdl is set after path offline, target
3131 	 * driver is not suppose to select a offlined path.
3132 	 */
3133 	if (ptgt->m_devhdl == MPTSAS_INVALID_DEVHDL) {
3134 		NDBG20(("rejecting command, it might because invalid devhdl "
3135 		    "request."));
3136 		mptsas_set_pkt_reason(mpt, cmd, CMD_DEV_GONE, STAT_TERMINATED);
3137 		if (cmd->cmd_flags & CFLAG_TXQ) {
3138 			mptsas_doneq_add(mpt, cmd);
3139 			mptsas_doneq_empty(mpt);
3140 			return (rval);
3141 		} else {
3142 			return (TRAN_FATAL_ERROR);
3143 		}
3144 	}
3145 	/*
3146 	 * The first case is the normal case.  mpt gets a command from the
3147 	 * target driver and starts it.
3148 	 * Since SMID 0 is reserved and the TM slot is reserved, the actual max
3149 	 * commands is m_max_requests - 2.
3150 	 */
3151 	if ((mpt->m_ncmds <= (mpt->m_max_requests - 2)) &&
3152 	    (ptgt->m_t_throttle > HOLD_THROTTLE) &&
3153 	    (ptgt->m_t_ncmds < ptgt->m_t_throttle) &&
3154 	    (ptgt->m_reset_delay == 0) &&
3155 	    (ptgt->m_t_nwait == 0) &&
3156 	    ((cmd->cmd_pkt_flags & FLAG_NOINTR) == 0)) {
3157 		if (mptsas_save_cmd(mpt, cmd) == TRUE) {
3158 			(void) mptsas_start_cmd(mpt, cmd);
3159 		} else {
3160 			mptsas_waitq_add(mpt, cmd);
3161 		}
3162 	} else {
3163 		/*
3164 		 * Add this pkt to the work queue
3165 		 */
3166 		mptsas_waitq_add(mpt, cmd);
3167 
3168 		if (cmd->cmd_pkt_flags & FLAG_NOINTR) {
3169 			(void) mptsas_poll(mpt, cmd, MPTSAS_POLL_TIME);
3170 
3171 			/*
3172 			 * Only flush the doneq if this is not a TM
3173 			 * cmd.  For TM cmds the flushing of the
3174 			 * doneq will be done in those routines.
3175 			 */
3176 			if ((cmd->cmd_flags & CFLAG_TM_CMD) == 0) {
3177 				mptsas_doneq_empty(mpt);
3178 			}
3179 		}
3180 	}
3181 	return (rval);
3182 }
3183 
3184 int
3185 mptsas_save_cmd(mptsas_t *mpt, mptsas_cmd_t *cmd)
3186 {
3187 	mptsas_slots_t	*slots;
3188 	int		slot;
3189 	mptsas_target_t	*ptgt = cmd->cmd_tgt_addr;
3190 
3191 	ASSERT(mutex_owned(&mpt->m_mutex));
3192 	slots = mpt->m_active;
3193 
3194 	/*
3195 	 * Account for reserved TM request slot and reserved SMID of 0.
3196 	 */
3197 	ASSERT(slots->m_n_slots == (mpt->m_max_requests - 2));
3198 
3199 	/*
3200 	 * m_tags is equivalent to the SMID when sending requests.  Since the
3201 	 * SMID cannot be 0, start out at one if rolling over past the size
3202 	 * of the request queue depth.  Also, don't use the last SMID, which is
3203 	 * reserved for TM requests.
3204 	 */
3205 	slot = (slots->m_tags)++;
3206 	if (slots->m_tags > slots->m_n_slots) {
3207 		slots->m_tags = 1;
3208 	}
3209 
3210 alloc_tag:
3211 	/* Validate tag, should never fail. */
3212 	if (slots->m_slot[slot] == NULL) {
3213 		/*
3214 		 * Make sure SMID is not using reserved value of 0
3215 		 * and the TM request slot.
3216 		 */
3217 		ASSERT((slot > 0) && (slot <= slots->m_n_slots));
3218 		cmd->cmd_slot = slot;
3219 		slots->m_slot[slot] = cmd;
3220 		mpt->m_ncmds++;
3221 
3222 		/*
3223 		 * only increment per target ncmds if this is not a
3224 		 * command that has no target associated with it (i.e. a
3225 		 * event acknoledgment)
3226 		 */
3227 		if ((cmd->cmd_flags & CFLAG_CMDIOC) == 0) {
3228 			ptgt->m_t_ncmds++;
3229 		}
3230 		cmd->cmd_active_timeout = cmd->cmd_pkt->pkt_time;
3231 
3232 		/*
3233 		 * If initial timout is less than or equal to one tick, bump
3234 		 * the timeout by a tick so that command doesn't timeout before
3235 		 * its allotted time.
3236 		 */
3237 		if (cmd->cmd_active_timeout <= mptsas_scsi_watchdog_tick) {
3238 			cmd->cmd_active_timeout += mptsas_scsi_watchdog_tick;
3239 		}
3240 		return (TRUE);
3241 	} else {
3242 		int i;
3243 
3244 		/*
3245 		 * If slot in use, scan until a free one is found. Don't use 0
3246 		 * or final slot, which is reserved for TM requests.
3247 		 */
3248 		for (i = 0; i < slots->m_n_slots; i++) {
3249 			slot = slots->m_tags;
3250 			if (++(slots->m_tags) > slots->m_n_slots) {
3251 				slots->m_tags = 1;
3252 			}
3253 			if (slots->m_slot[slot] == NULL) {
3254 				NDBG22(("found free slot %d", slot));
3255 				goto alloc_tag;
3256 			}
3257 		}
3258 	}
3259 	return (FALSE);
3260 }
3261 
3262 /*
3263  * prepare the pkt:
3264  * the pkt may have been resubmitted or just reused so
3265  * initialize some fields and do some checks.
3266  */
3267 static int
3268 mptsas_prepare_pkt(mptsas_cmd_t *cmd)
3269 {
3270 	struct scsi_pkt	*pkt = CMD2PKT(cmd);
3271 
3272 	NDBG1(("mptsas_prepare_pkt: cmd=0x%p", (void *)cmd));
3273 
3274 	/*
3275 	 * Reinitialize some fields that need it; the packet may
3276 	 * have been resubmitted
3277 	 */
3278 	pkt->pkt_reason = CMD_CMPLT;
3279 	pkt->pkt_state = 0;
3280 	pkt->pkt_statistics = 0;
3281 	pkt->pkt_resid = 0;
3282 	cmd->cmd_age = 0;
3283 	cmd->cmd_pkt_flags = pkt->pkt_flags;
3284 
3285 	/*
3286 	 * zero status byte.
3287 	 */
3288 	*(pkt->pkt_scbp) = 0;
3289 
3290 	if (cmd->cmd_flags & CFLAG_DMAVALID) {
3291 		pkt->pkt_resid = cmd->cmd_dmacount;
3292 
3293 		/*
3294 		 * consistent packets need to be sync'ed first
3295 		 * (only for data going out)
3296 		 */
3297 		if ((cmd->cmd_flags & CFLAG_CMDIOPB) &&
3298 		    (cmd->cmd_flags & CFLAG_DMASEND)) {
3299 			(void) ddi_dma_sync(cmd->cmd_dmahandle, 0, 0,
3300 			    DDI_DMA_SYNC_FORDEV);
3301 		}
3302 	}
3303 
3304 	cmd->cmd_flags =
3305 	    (cmd->cmd_flags & ~(CFLAG_TRANFLAG)) |
3306 	    CFLAG_PREPARED | CFLAG_IN_TRANSPORT;
3307 
3308 	return (TRAN_ACCEPT);
3309 }
3310 
3311 /*
3312  * tran_init_pkt(9E) - allocate scsi_pkt(9S) for command
3313  *
3314  * One of three possibilities:
3315  *	- allocate scsi_pkt
3316  *	- allocate scsi_pkt and DMA resources
3317  *	- allocate DMA resources to an already-allocated pkt
3318  */
3319 static struct scsi_pkt *
3320 mptsas_scsi_init_pkt(struct scsi_address *ap, struct scsi_pkt *pkt,
3321     struct buf *bp, int cmdlen, int statuslen, int tgtlen, int flags,
3322     int (*callback)(), caddr_t arg)
3323 {
3324 	mptsas_cmd_t		*cmd, *new_cmd;
3325 	mptsas_t		*mpt = ADDR2MPT(ap);
3326 	int			failure = 1;
3327 	uint_t			oldcookiec;
3328 	mptsas_target_t		*ptgt = NULL;
3329 	int			rval;
3330 	mptsas_tgt_private_t	*tgt_private;
3331 	int			kf;
3332 
3333 	kf = (callback == SLEEP_FUNC)? KM_SLEEP: KM_NOSLEEP;
3334 
3335 	tgt_private = (mptsas_tgt_private_t *)ap->a_hba_tran->
3336 	    tran_tgt_private;
3337 	ASSERT(tgt_private != NULL);
3338 	if (tgt_private == NULL) {
3339 		return (NULL);
3340 	}
3341 	ptgt = tgt_private->t_private;
3342 	ASSERT(ptgt != NULL);
3343 	if (ptgt == NULL)
3344 		return (NULL);
3345 	ap->a_target = ptgt->m_devhdl;
3346 	ap->a_lun = tgt_private->t_lun;
3347 
3348 	ASSERT(callback == NULL_FUNC || callback == SLEEP_FUNC);
3349 #ifdef MPTSAS_TEST_EXTRN_ALLOC
3350 	statuslen *= 100; tgtlen *= 4;
3351 #endif
3352 	NDBG3(("mptsas_scsi_init_pkt:\n"
3353 	    "\ttgt=%d in=0x%p bp=0x%p clen=%d slen=%d tlen=%d flags=%x",
3354 	    ap->a_target, (void *)pkt, (void *)bp,
3355 	    cmdlen, statuslen, tgtlen, flags));
3356 
3357 	/*
3358 	 * Allocate the new packet.
3359 	 */
3360 	if (pkt == NULL) {
3361 		ddi_dma_handle_t	save_dma_handle;
3362 		ddi_dma_handle_t	save_arq_dma_handle;
3363 		struct buf		*save_arq_bp;
3364 		ddi_dma_cookie_t	save_arqcookie;
3365 
3366 		cmd = kmem_cache_alloc(mpt->m_kmem_cache, kf);
3367 
3368 		if (cmd) {
3369 			save_dma_handle = cmd->cmd_dmahandle;
3370 			save_arq_dma_handle = cmd->cmd_arqhandle;
3371 			save_arq_bp = cmd->cmd_arq_buf;
3372 			save_arqcookie = cmd->cmd_arqcookie;
3373 			bzero(cmd, sizeof (*cmd) + scsi_pkt_size());
3374 			cmd->cmd_dmahandle = save_dma_handle;
3375 			cmd->cmd_arqhandle = save_arq_dma_handle;
3376 			cmd->cmd_arq_buf = save_arq_bp;
3377 			cmd->cmd_arqcookie = save_arqcookie;
3378 
3379 			pkt = (void *)((uchar_t *)cmd +
3380 			    sizeof (struct mptsas_cmd));
3381 			pkt->pkt_ha_private = (opaque_t)cmd;
3382 			pkt->pkt_address = *ap;
3383 			pkt->pkt_private = (opaque_t)cmd->cmd_pkt_private;
3384 			pkt->pkt_scbp = (opaque_t)&cmd->cmd_scb;
3385 			pkt->pkt_cdbp = (opaque_t)&cmd->cmd_cdb;
3386 			cmd->cmd_pkt = (struct scsi_pkt *)pkt;
3387 			cmd->cmd_cdblen = (uchar_t)cmdlen;
3388 			cmd->cmd_scblen = statuslen;
3389 			cmd->cmd_rqslen = SENSE_LENGTH;
3390 			cmd->cmd_tgt_addr = ptgt;
3391 			failure = 0;
3392 		}
3393 
3394 		if (failure || (cmdlen > sizeof (cmd->cmd_cdb)) ||
3395 		    (tgtlen > PKT_PRIV_LEN) ||
3396 		    (statuslen > EXTCMDS_STATUS_SIZE)) {
3397 			if (failure == 0) {
3398 				/*
3399 				 * if extern alloc fails, all will be
3400 				 * deallocated, including cmd
3401 				 */
3402 				failure = mptsas_pkt_alloc_extern(mpt, cmd,
3403 				    cmdlen, tgtlen, statuslen, kf);
3404 			}
3405 			if (failure) {
3406 				/*
3407 				 * if extern allocation fails, it will
3408 				 * deallocate the new pkt as well
3409 				 */
3410 				return (NULL);
3411 			}
3412 		}
3413 		new_cmd = cmd;
3414 
3415 	} else {
3416 		cmd = PKT2CMD(pkt);
3417 		new_cmd = NULL;
3418 	}
3419 
3420 
3421 	/* grab cmd->cmd_cookiec here as oldcookiec */
3422 
3423 	oldcookiec = cmd->cmd_cookiec;
3424 
3425 	/*
3426 	 * If the dma was broken up into PARTIAL transfers cmd_nwin will be
3427 	 * greater than 0 and we'll need to grab the next dma window
3428 	 */
3429 	/*
3430 	 * SLM-not doing extra command frame right now; may add later
3431 	 */
3432 
3433 	if (cmd->cmd_nwin > 0) {
3434 
3435 		/*
3436 		 * Make sure we havn't gone past the the total number
3437 		 * of windows
3438 		 */
3439 		if (++cmd->cmd_winindex >= cmd->cmd_nwin) {
3440 			return (NULL);
3441 		}
3442 		if (ddi_dma_getwin(cmd->cmd_dmahandle, cmd->cmd_winindex,
3443 		    &cmd->cmd_dma_offset, &cmd->cmd_dma_len,
3444 		    &cmd->cmd_cookie, &cmd->cmd_cookiec) == DDI_FAILURE) {
3445 			return (NULL);
3446 		}
3447 		goto get_dma_cookies;
3448 	}
3449 
3450 
3451 	if (flags & PKT_XARQ) {
3452 		cmd->cmd_flags |= CFLAG_XARQ;
3453 	}
3454 
3455 	/*
3456 	 * DMA resource allocation.  This version assumes your
3457 	 * HBA has some sort of bus-mastering or onboard DMA capability, with a
3458 	 * scatter-gather list of length MPTSAS_MAX_DMA_SEGS, as given in the
3459 	 * ddi_dma_attr_t structure and passed to scsi_impl_dmaget.
3460 	 */
3461 	if (bp && (bp->b_bcount != 0) &&
3462 	    (cmd->cmd_flags & CFLAG_DMAVALID) == 0) {
3463 
3464 		int	cnt, dma_flags;
3465 		mptti_t	*dmap;		/* ptr to the S/G list */
3466 
3467 		/*
3468 		 * Set up DMA memory and position to the next DMA segment.
3469 		 */
3470 		ASSERT(cmd->cmd_dmahandle != NULL);
3471 
3472 		if (bp->b_flags & B_READ) {
3473 			dma_flags = DDI_DMA_READ;
3474 			cmd->cmd_flags &= ~CFLAG_DMASEND;
3475 		} else {
3476 			dma_flags = DDI_DMA_WRITE;
3477 			cmd->cmd_flags |= CFLAG_DMASEND;
3478 		}
3479 		if (flags & PKT_CONSISTENT) {
3480 			cmd->cmd_flags |= CFLAG_CMDIOPB;
3481 			dma_flags |= DDI_DMA_CONSISTENT;
3482 		}
3483 
3484 		if (flags & PKT_DMA_PARTIAL) {
3485 			dma_flags |= DDI_DMA_PARTIAL;
3486 		}
3487 
3488 		/*
3489 		 * workaround for byte hole issue on psycho and
3490 		 * schizo pre 2.1
3491 		 */
3492 		if ((bp->b_flags & B_READ) && ((bp->b_flags &
3493 		    (B_PAGEIO|B_REMAPPED)) != B_PAGEIO) &&
3494 		    ((uintptr_t)bp->b_un.b_addr & 0x7)) {
3495 			dma_flags |= DDI_DMA_CONSISTENT;
3496 		}
3497 
3498 		rval = ddi_dma_buf_bind_handle(cmd->cmd_dmahandle, bp,
3499 		    dma_flags, callback, arg,
3500 		    &cmd->cmd_cookie, &cmd->cmd_cookiec);
3501 		if (rval == DDI_DMA_PARTIAL_MAP) {
3502 			(void) ddi_dma_numwin(cmd->cmd_dmahandle,
3503 			    &cmd->cmd_nwin);
3504 			cmd->cmd_winindex = 0;
3505 			(void) ddi_dma_getwin(cmd->cmd_dmahandle,
3506 			    cmd->cmd_winindex, &cmd->cmd_dma_offset,
3507 			    &cmd->cmd_dma_len, &cmd->cmd_cookie,
3508 			    &cmd->cmd_cookiec);
3509 		} else if (rval && (rval != DDI_DMA_MAPPED)) {
3510 			switch (rval) {
3511 			case DDI_DMA_NORESOURCES:
3512 				bioerror(bp, 0);
3513 				break;
3514 			case DDI_DMA_BADATTR:
3515 			case DDI_DMA_NOMAPPING:
3516 				bioerror(bp, EFAULT);
3517 				break;
3518 			case DDI_DMA_TOOBIG:
3519 			default:
3520 				bioerror(bp, EINVAL);
3521 				break;
3522 			}
3523 			cmd->cmd_flags &= ~CFLAG_DMAVALID;
3524 			if (new_cmd) {
3525 				mptsas_scsi_destroy_pkt(ap, pkt);
3526 			}
3527 			return ((struct scsi_pkt *)NULL);
3528 		}
3529 
3530 get_dma_cookies:
3531 		cmd->cmd_flags |= CFLAG_DMAVALID;
3532 		ASSERT(cmd->cmd_cookiec > 0);
3533 
3534 		if (cmd->cmd_cookiec > MPTSAS_MAX_CMD_SEGS) {
3535 			mptsas_log(mpt, CE_NOTE, "large cookiec received %d\n",
3536 			    cmd->cmd_cookiec);
3537 			bioerror(bp, EINVAL);
3538 			if (new_cmd) {
3539 				mptsas_scsi_destroy_pkt(ap, pkt);
3540 			}
3541 			return ((struct scsi_pkt *)NULL);
3542 		}
3543 
3544 		/*
3545 		 * Allocate extra SGL buffer if needed.
3546 		 */
3547 		if ((cmd->cmd_cookiec > MPTSAS_MAX_FRAME_SGES64(mpt)) &&
3548 		    (cmd->cmd_extra_frames == NULL)) {
3549 			if (mptsas_alloc_extra_sgl_frame(mpt, cmd) ==
3550 			    DDI_FAILURE) {
3551 				mptsas_log(mpt, CE_WARN, "MPT SGL mem alloc "
3552 				    "failed");
3553 				bioerror(bp, ENOMEM);
3554 				if (new_cmd) {
3555 					mptsas_scsi_destroy_pkt(ap, pkt);
3556 				}
3557 				return ((struct scsi_pkt *)NULL);
3558 			}
3559 		}
3560 
3561 		/*
3562 		 * Always use scatter-gather transfer
3563 		 * Use the loop below to store physical addresses of
3564 		 * DMA segments, from the DMA cookies, into your HBA's
3565 		 * scatter-gather list.
3566 		 * We need to ensure we have enough kmem alloc'd
3567 		 * for the sg entries since we are no longer using an
3568 		 * array inside mptsas_cmd_t.
3569 		 *
3570 		 * We check cmd->cmd_cookiec against oldcookiec so
3571 		 * the scatter-gather list is correctly allocated
3572 		 */
3573 
3574 		if (oldcookiec != cmd->cmd_cookiec) {
3575 			if (cmd->cmd_sg != (mptti_t *)NULL) {
3576 				kmem_free(cmd->cmd_sg, sizeof (mptti_t) *
3577 				    oldcookiec);
3578 				cmd->cmd_sg = NULL;
3579 			}
3580 		}
3581 
3582 		if (cmd->cmd_sg == (mptti_t *)NULL) {
3583 			cmd->cmd_sg = kmem_alloc((size_t)(sizeof (mptti_t)*
3584 			    cmd->cmd_cookiec), kf);
3585 
3586 			if (cmd->cmd_sg == (mptti_t *)NULL) {
3587 				mptsas_log(mpt, CE_WARN,
3588 				    "unable to kmem_alloc enough memory "
3589 				    "for scatter/gather list");
3590 		/*
3591 		 * if we have an ENOMEM condition we need to behave
3592 		 * the same way as the rest of this routine
3593 		 */
3594 
3595 				bioerror(bp, ENOMEM);
3596 				if (new_cmd) {
3597 					mptsas_scsi_destroy_pkt(ap, pkt);
3598 				}
3599 				return ((struct scsi_pkt *)NULL);
3600 			}
3601 		}
3602 
3603 		dmap = cmd->cmd_sg;
3604 
3605 		ASSERT(cmd->cmd_cookie.dmac_size != 0);
3606 
3607 		/*
3608 		 * store the first segment into the S/G list
3609 		 */
3610 		dmap->count = cmd->cmd_cookie.dmac_size;
3611 		dmap->addr.address64.Low = (uint32_t)
3612 		    (cmd->cmd_cookie.dmac_laddress & 0xffffffffull);
3613 		dmap->addr.address64.High = (uint32_t)
3614 		    (cmd->cmd_cookie.dmac_laddress >> 32);
3615 
3616 		/*
3617 		 * dmacount counts the size of the dma for this window
3618 		 * (if partial dma is being used).  totaldmacount
3619 		 * keeps track of the total amount of dma we have
3620 		 * transferred for all the windows (needed to calculate
3621 		 * the resid value below).
3622 		 */
3623 		cmd->cmd_dmacount = cmd->cmd_cookie.dmac_size;
3624 		cmd->cmd_totaldmacount += cmd->cmd_cookie.dmac_size;
3625 
3626 		/*
3627 		 * We already stored the first DMA scatter gather segment,
3628 		 * start at 1 if we need to store more.
3629 		 */
3630 		for (cnt = 1; cnt < cmd->cmd_cookiec; cnt++) {
3631 			/*
3632 			 * Get next DMA cookie
3633 			 */
3634 			ddi_dma_nextcookie(cmd->cmd_dmahandle,
3635 			    &cmd->cmd_cookie);
3636 			dmap++;
3637 
3638 			cmd->cmd_dmacount += cmd->cmd_cookie.dmac_size;
3639 			cmd->cmd_totaldmacount += cmd->cmd_cookie.dmac_size;
3640 
3641 			/*
3642 			 * store the segment parms into the S/G list
3643 			 */
3644 			dmap->count = cmd->cmd_cookie.dmac_size;
3645 			dmap->addr.address64.Low = (uint32_t)
3646 			    (cmd->cmd_cookie.dmac_laddress & 0xffffffffull);
3647 			dmap->addr.address64.High = (uint32_t)
3648 			    (cmd->cmd_cookie.dmac_laddress >> 32);
3649 		}
3650 
3651 		/*
3652 		 * If this was partially allocated we set the resid
3653 		 * the amount of data NOT transferred in this window
3654 		 * If there is only one window, the resid will be 0
3655 		 */
3656 		pkt->pkt_resid = (bp->b_bcount - cmd->cmd_totaldmacount);
3657 		NDBG16(("mptsas_dmaget: cmd_dmacount=%d.", cmd->cmd_dmacount));
3658 	}
3659 	return (pkt);
3660 }
3661 
3662 /*
3663  * tran_destroy_pkt(9E) - scsi_pkt(9s) deallocation
3664  *
3665  * Notes:
3666  *	- also frees DMA resources if allocated
3667  *	- implicit DMA synchonization
3668  */
3669 static void
3670 mptsas_scsi_destroy_pkt(struct scsi_address *ap, struct scsi_pkt *pkt)
3671 {
3672 	mptsas_cmd_t	*cmd = PKT2CMD(pkt);
3673 	mptsas_t	*mpt = ADDR2MPT(ap);
3674 
3675 	NDBG3(("mptsas_scsi_destroy_pkt: target=%d pkt=0x%p",
3676 	    ap->a_target, (void *)pkt));
3677 
3678 	if (cmd->cmd_flags & CFLAG_DMAVALID) {
3679 		(void) ddi_dma_unbind_handle(cmd->cmd_dmahandle);
3680 		cmd->cmd_flags &= ~CFLAG_DMAVALID;
3681 	}
3682 
3683 	if (cmd->cmd_sg) {
3684 		kmem_free(cmd->cmd_sg, sizeof (mptti_t) * cmd->cmd_cookiec);
3685 		cmd->cmd_sg = NULL;
3686 	}
3687 
3688 	mptsas_free_extra_sgl_frame(mpt, cmd);
3689 
3690 	if ((cmd->cmd_flags &
3691 	    (CFLAG_FREE | CFLAG_CDBEXTERN | CFLAG_PRIVEXTERN |
3692 	    CFLAG_SCBEXTERN)) == 0) {
3693 		cmd->cmd_flags = CFLAG_FREE;
3694 		kmem_cache_free(mpt->m_kmem_cache, (void *)cmd);
3695 	} else {
3696 		mptsas_pkt_destroy_extern(mpt, cmd);
3697 	}
3698 }
3699 
3700 /*
3701  * kmem cache constructor and destructor:
3702  * When constructing, we bzero the cmd and allocate the dma handle
3703  * When destructing, just free the dma handle
3704  */
3705 static int
3706 mptsas_kmem_cache_constructor(void *buf, void *cdrarg, int kmflags)
3707 {
3708 	mptsas_cmd_t		*cmd = buf;
3709 	mptsas_t		*mpt  = cdrarg;
3710 	struct scsi_address	ap;
3711 	uint_t			cookiec;
3712 	ddi_dma_attr_t		arq_dma_attr;
3713 	int			(*callback)(caddr_t);
3714 
3715 	callback = (kmflags == KM_SLEEP)? DDI_DMA_SLEEP: DDI_DMA_DONTWAIT;
3716 
3717 	NDBG4(("mptsas_kmem_cache_constructor"));
3718 
3719 	ap.a_hba_tran = mpt->m_tran;
3720 	ap.a_target = 0;
3721 	ap.a_lun = 0;
3722 
3723 	/*
3724 	 * allocate a dma handle
3725 	 */
3726 	if ((ddi_dma_alloc_handle(mpt->m_dip, &mpt->m_io_dma_attr, callback,
3727 	    NULL, &cmd->cmd_dmahandle)) != DDI_SUCCESS) {
3728 		cmd->cmd_dmahandle = NULL;
3729 		return (-1);
3730 	}
3731 
3732 	cmd->cmd_arq_buf = scsi_alloc_consistent_buf(&ap, (struct buf *)NULL,
3733 	    SENSE_LENGTH, B_READ, callback, NULL);
3734 	if (cmd->cmd_arq_buf == NULL) {
3735 		ddi_dma_free_handle(&cmd->cmd_dmahandle);
3736 		cmd->cmd_dmahandle = NULL;
3737 		return (-1);
3738 	}
3739 
3740 	/*
3741 	 * allocate a arq handle
3742 	 */
3743 	arq_dma_attr = mpt->m_msg_dma_attr;
3744 	arq_dma_attr.dma_attr_sgllen = 1;
3745 	if ((ddi_dma_alloc_handle(mpt->m_dip, &arq_dma_attr, callback,
3746 	    NULL, &cmd->cmd_arqhandle)) != DDI_SUCCESS) {
3747 		ddi_dma_free_handle(&cmd->cmd_dmahandle);
3748 		scsi_free_consistent_buf(cmd->cmd_arq_buf);
3749 		cmd->cmd_dmahandle = NULL;
3750 		cmd->cmd_arqhandle = NULL;
3751 		return (-1);
3752 	}
3753 
3754 	if (ddi_dma_buf_bind_handle(cmd->cmd_arqhandle,
3755 	    cmd->cmd_arq_buf, (DDI_DMA_READ | DDI_DMA_CONSISTENT),
3756 	    callback, NULL, &cmd->cmd_arqcookie, &cookiec) != DDI_SUCCESS) {
3757 		ddi_dma_free_handle(&cmd->cmd_dmahandle);
3758 		ddi_dma_free_handle(&cmd->cmd_arqhandle);
3759 		scsi_free_consistent_buf(cmd->cmd_arq_buf);
3760 		cmd->cmd_dmahandle = NULL;
3761 		cmd->cmd_arqhandle = NULL;
3762 		cmd->cmd_arq_buf = NULL;
3763 		return (-1);
3764 	}
3765 
3766 	return (0);
3767 }
3768 
3769 static void
3770 mptsas_kmem_cache_destructor(void *buf, void *cdrarg)
3771 {
3772 #ifndef __lock_lint
3773 	_NOTE(ARGUNUSED(cdrarg))
3774 #endif
3775 	mptsas_cmd_t	*cmd = buf;
3776 
3777 	NDBG4(("mptsas_kmem_cache_destructor"));
3778 
3779 	if (cmd->cmd_arqhandle) {
3780 		(void) ddi_dma_unbind_handle(cmd->cmd_arqhandle);
3781 		ddi_dma_free_handle(&cmd->cmd_arqhandle);
3782 		cmd->cmd_arqhandle = NULL;
3783 	}
3784 	if (cmd->cmd_arq_buf) {
3785 		scsi_free_consistent_buf(cmd->cmd_arq_buf);
3786 		cmd->cmd_arq_buf = NULL;
3787 	}
3788 	if (cmd->cmd_dmahandle) {
3789 		ddi_dma_free_handle(&cmd->cmd_dmahandle);
3790 		cmd->cmd_dmahandle = NULL;
3791 	}
3792 }
3793 
3794 static int
3795 mptsas_cache_frames_constructor(void *buf, void *cdrarg, int kmflags)
3796 {
3797 	mptsas_cache_frames_t	*p = buf;
3798 	mptsas_t		*mpt = cdrarg;
3799 	ddi_dma_attr_t		frame_dma_attr;
3800 	size_t			mem_size, alloc_len;
3801 	ddi_dma_cookie_t	cookie;
3802 	uint_t			ncookie;
3803 	int (*callback)(caddr_t) = (kmflags == KM_SLEEP)
3804 	    ? DDI_DMA_SLEEP: DDI_DMA_DONTWAIT;
3805 
3806 	frame_dma_attr = mpt->m_msg_dma_attr;
3807 	frame_dma_attr.dma_attr_align = 0x10;
3808 	frame_dma_attr.dma_attr_sgllen = 1;
3809 
3810 	if (ddi_dma_alloc_handle(mpt->m_dip, &frame_dma_attr, callback, NULL,
3811 	    &p->m_dma_hdl) != DDI_SUCCESS) {
3812 		mptsas_log(mpt, CE_WARN, "Unable to allocate dma handle for"
3813 		    " extra SGL.");
3814 		return (DDI_FAILURE);
3815 	}
3816 
3817 	mem_size = (mpt->m_max_request_frames - 1) * mpt->m_req_frame_size;
3818 
3819 	if (ddi_dma_mem_alloc(p->m_dma_hdl, mem_size, &mpt->m_dev_acc_attr,
3820 	    DDI_DMA_CONSISTENT, callback, NULL, (caddr_t *)&p->m_frames_addr,
3821 	    &alloc_len, &p->m_acc_hdl) != DDI_SUCCESS) {
3822 		ddi_dma_free_handle(&p->m_dma_hdl);
3823 		p->m_dma_hdl = NULL;
3824 		mptsas_log(mpt, CE_WARN, "Unable to allocate dma memory for"
3825 		    " extra SGL.");
3826 		return (DDI_FAILURE);
3827 	}
3828 
3829 	if (ddi_dma_addr_bind_handle(p->m_dma_hdl, NULL, p->m_frames_addr,
3830 	    alloc_len, DDI_DMA_RDWR | DDI_DMA_CONSISTENT, callback, NULL,
3831 	    &cookie, &ncookie) != DDI_DMA_MAPPED) {
3832 		(void) ddi_dma_mem_free(&p->m_acc_hdl);
3833 		ddi_dma_free_handle(&p->m_dma_hdl);
3834 		p->m_dma_hdl = NULL;
3835 		mptsas_log(mpt, CE_WARN, "Unable to bind DMA resources for"
3836 		    " extra SGL");
3837 		return (DDI_FAILURE);
3838 	}
3839 
3840 	/*
3841 	 * Store the SGL memory address.  This chip uses this
3842 	 * address to dma to and from the driver.  The second
3843 	 * address is the address mpt uses to fill in the SGL.
3844 	 */
3845 	p->m_phys_addr = cookie.dmac_address;
3846 
3847 	return (DDI_SUCCESS);
3848 }
3849 
3850 static void
3851 mptsas_cache_frames_destructor(void *buf, void *cdrarg)
3852 {
3853 #ifndef __lock_lint
3854 	_NOTE(ARGUNUSED(cdrarg))
3855 #endif
3856 	mptsas_cache_frames_t	*p = buf;
3857 	if (p->m_dma_hdl != NULL) {
3858 		(void) ddi_dma_unbind_handle(p->m_dma_hdl);
3859 		(void) ddi_dma_mem_free(&p->m_acc_hdl);
3860 		ddi_dma_free_handle(&p->m_dma_hdl);
3861 		p->m_phys_addr = NULL;
3862 		p->m_frames_addr = NULL;
3863 		p->m_dma_hdl = NULL;
3864 		p->m_acc_hdl = NULL;
3865 	}
3866 
3867 }
3868 
3869 /*
3870  * allocate and deallocate external pkt space (ie. not part of mptsas_cmd)
3871  * for non-standard length cdb, pkt_private, status areas
3872  * if allocation fails, then deallocate all external space and the pkt
3873  */
3874 /* ARGSUSED */
3875 static int
3876 mptsas_pkt_alloc_extern(mptsas_t *mpt, mptsas_cmd_t *cmd,
3877     int cmdlen, int tgtlen, int statuslen, int kf)
3878 {
3879 	caddr_t			cdbp, scbp, tgt;
3880 	int			(*callback)(caddr_t) = (kf == KM_SLEEP) ?
3881 	    DDI_DMA_SLEEP : DDI_DMA_DONTWAIT;
3882 	struct scsi_address	ap;
3883 	size_t			senselength;
3884 	ddi_dma_attr_t		ext_arq_dma_attr;
3885 	uint_t			cookiec;
3886 
3887 	NDBG3(("mptsas_pkt_alloc_extern: "
3888 	    "cmd=0x%p cmdlen=%d tgtlen=%d statuslen=%d kf=%x",
3889 	    (void *)cmd, cmdlen, tgtlen, statuslen, kf));
3890 
3891 	tgt = cdbp = scbp = NULL;
3892 	cmd->cmd_scblen		= statuslen;
3893 	cmd->cmd_privlen	= (uchar_t)tgtlen;
3894 
3895 	if (cmdlen > sizeof (cmd->cmd_cdb)) {
3896 		if ((cdbp = kmem_zalloc((size_t)cmdlen, kf)) == NULL) {
3897 			goto fail;
3898 		}
3899 		cmd->cmd_pkt->pkt_cdbp = (opaque_t)cdbp;
3900 		cmd->cmd_flags |= CFLAG_CDBEXTERN;
3901 	}
3902 	if (tgtlen > PKT_PRIV_LEN) {
3903 		if ((tgt = kmem_zalloc((size_t)tgtlen, kf)) == NULL) {
3904 			goto fail;
3905 		}
3906 		cmd->cmd_flags |= CFLAG_PRIVEXTERN;
3907 		cmd->cmd_pkt->pkt_private = tgt;
3908 	}
3909 	if (statuslen > EXTCMDS_STATUS_SIZE) {
3910 		if ((scbp = kmem_zalloc((size_t)statuslen, kf)) == NULL) {
3911 			goto fail;
3912 		}
3913 		cmd->cmd_flags |= CFLAG_SCBEXTERN;
3914 		cmd->cmd_pkt->pkt_scbp = (opaque_t)scbp;
3915 
3916 		/* allocate sense data buf for DMA */
3917 
3918 		senselength = statuslen - MPTSAS_GET_ITEM_OFF(
3919 		    struct scsi_arq_status, sts_sensedata);
3920 		cmd->cmd_rqslen = (uchar_t)senselength;
3921 
3922 		ap.a_hba_tran = mpt->m_tran;
3923 		ap.a_target = 0;
3924 		ap.a_lun = 0;
3925 
3926 		cmd->cmd_ext_arq_buf = scsi_alloc_consistent_buf(&ap,
3927 		    (struct buf *)NULL, senselength, B_READ,
3928 		    callback, NULL);
3929 
3930 		if (cmd->cmd_ext_arq_buf == NULL) {
3931 			goto fail;
3932 		}
3933 		/*
3934 		 * allocate a extern arq handle and bind the buf
3935 		 */
3936 		ext_arq_dma_attr = mpt->m_msg_dma_attr;
3937 		ext_arq_dma_attr.dma_attr_sgllen = 1;
3938 		if ((ddi_dma_alloc_handle(mpt->m_dip,
3939 		    &ext_arq_dma_attr, callback,
3940 		    NULL, &cmd->cmd_ext_arqhandle)) != DDI_SUCCESS) {
3941 			goto fail;
3942 		}
3943 
3944 		if (ddi_dma_buf_bind_handle(cmd->cmd_ext_arqhandle,
3945 		    cmd->cmd_ext_arq_buf, (DDI_DMA_READ | DDI_DMA_CONSISTENT),
3946 		    callback, NULL, &cmd->cmd_ext_arqcookie,
3947 		    &cookiec)
3948 		    != DDI_SUCCESS) {
3949 			goto fail;
3950 		}
3951 		cmd->cmd_flags |= CFLAG_EXTARQBUFVALID;
3952 	}
3953 	return (0);
3954 fail:
3955 	mptsas_pkt_destroy_extern(mpt, cmd);
3956 	return (1);
3957 }
3958 
3959 /*
3960  * deallocate external pkt space and deallocate the pkt
3961  */
3962 static void
3963 mptsas_pkt_destroy_extern(mptsas_t *mpt, mptsas_cmd_t *cmd)
3964 {
3965 	NDBG3(("mptsas_pkt_destroy_extern: cmd=0x%p", (void *)cmd));
3966 
3967 	if (cmd->cmd_flags & CFLAG_FREE) {
3968 		mptsas_log(mpt, CE_PANIC,
3969 		    "mptsas_pkt_destroy_extern: freeing free packet");
3970 		_NOTE(NOT_REACHED)
3971 		/* NOTREACHED */
3972 	}
3973 	if (cmd->cmd_flags & CFLAG_CDBEXTERN) {
3974 		kmem_free(cmd->cmd_pkt->pkt_cdbp, (size_t)cmd->cmd_cdblen);
3975 	}
3976 	if (cmd->cmd_flags & CFLAG_SCBEXTERN) {
3977 		kmem_free(cmd->cmd_pkt->pkt_scbp, (size_t)cmd->cmd_scblen);
3978 		if (cmd->cmd_flags & CFLAG_EXTARQBUFVALID) {
3979 			(void) ddi_dma_unbind_handle(cmd->cmd_ext_arqhandle);
3980 		}
3981 		if (cmd->cmd_ext_arqhandle) {
3982 			ddi_dma_free_handle(&cmd->cmd_ext_arqhandle);
3983 			cmd->cmd_ext_arqhandle = NULL;
3984 		}
3985 		if (cmd->cmd_ext_arq_buf)
3986 			scsi_free_consistent_buf(cmd->cmd_ext_arq_buf);
3987 	}
3988 	if (cmd->cmd_flags & CFLAG_PRIVEXTERN) {
3989 		kmem_free(cmd->cmd_pkt->pkt_private, (size_t)cmd->cmd_privlen);
3990 	}
3991 	cmd->cmd_flags = CFLAG_FREE;
3992 	kmem_cache_free(mpt->m_kmem_cache, (void *)cmd);
3993 }
3994 
3995 /*
3996  * tran_sync_pkt(9E) - explicit DMA synchronization
3997  */
3998 /*ARGSUSED*/
3999 static void
4000 mptsas_scsi_sync_pkt(struct scsi_address *ap, struct scsi_pkt *pkt)
4001 {
4002 	mptsas_cmd_t	*cmd = PKT2CMD(pkt);
4003 
4004 	NDBG3(("mptsas_scsi_sync_pkt: target=%d, pkt=0x%p",
4005 	    ap->a_target, (void *)pkt));
4006 
4007 	if (cmd->cmd_dmahandle) {
4008 		(void) ddi_dma_sync(cmd->cmd_dmahandle, 0, 0,
4009 		    (cmd->cmd_flags & CFLAG_DMASEND) ?
4010 		    DDI_DMA_SYNC_FORDEV : DDI_DMA_SYNC_FORCPU);
4011 	}
4012 }
4013 
4014 /*
4015  * tran_dmafree(9E) - deallocate DMA resources allocated for command
4016  */
4017 /*ARGSUSED*/
4018 static void
4019 mptsas_scsi_dmafree(struct scsi_address *ap, struct scsi_pkt *pkt)
4020 {
4021 	mptsas_cmd_t	*cmd = PKT2CMD(pkt);
4022 	mptsas_t	*mpt = ADDR2MPT(ap);
4023 
4024 	NDBG3(("mptsas_scsi_dmafree: target=%d pkt=0x%p",
4025 	    ap->a_target, (void *)pkt));
4026 
4027 	if (cmd->cmd_flags & CFLAG_DMAVALID) {
4028 		(void) ddi_dma_unbind_handle(cmd->cmd_dmahandle);
4029 		cmd->cmd_flags &= ~CFLAG_DMAVALID;
4030 	}
4031 
4032 	if (cmd->cmd_flags & CFLAG_EXTARQBUFVALID) {
4033 		(void) ddi_dma_unbind_handle(cmd->cmd_ext_arqhandle);
4034 		cmd->cmd_flags &= ~CFLAG_EXTARQBUFVALID;
4035 	}
4036 
4037 	mptsas_free_extra_sgl_frame(mpt, cmd);
4038 }
4039 
4040 static void
4041 mptsas_pkt_comp(struct scsi_pkt *pkt, mptsas_cmd_t *cmd)
4042 {
4043 	if ((cmd->cmd_flags & CFLAG_CMDIOPB) &&
4044 	    (!(cmd->cmd_flags & CFLAG_DMASEND))) {
4045 		(void) ddi_dma_sync(cmd->cmd_dmahandle, 0, 0,
4046 		    DDI_DMA_SYNC_FORCPU);
4047 	}
4048 	(*pkt->pkt_comp)(pkt);
4049 }
4050 
4051 static void
4052 mptsas_sge_setup(mptsas_t *mpt, mptsas_cmd_t *cmd, uint32_t *control,
4053 	pMpi2SCSIIORequest_t frame, ddi_acc_handle_t acc_hdl)
4054 {
4055 	uint_t			cookiec;
4056 	mptti_t			*dmap;
4057 	uint32_t		flags;
4058 	pMpi2SGESimple64_t	sge;
4059 	pMpi2SGEChain64_t	sgechain;
4060 	ASSERT(cmd->cmd_flags & CFLAG_DMAVALID);
4061 
4062 	/*
4063 	 * Save the number of entries in the DMA
4064 	 * Scatter/Gather list
4065 	 */
4066 	cookiec = cmd->cmd_cookiec;
4067 
4068 	NDBG1(("mptsas_sge_setup: cookiec=%d", cookiec));
4069 
4070 	/*
4071 	 * Set read/write bit in control.
4072 	 */
4073 	if (cmd->cmd_flags & CFLAG_DMASEND) {
4074 		*control |= MPI2_SCSIIO_CONTROL_WRITE;
4075 	} else {
4076 		*control |= MPI2_SCSIIO_CONTROL_READ;
4077 	}
4078 
4079 	ddi_put32(acc_hdl, &frame->DataLength, cmd->cmd_dmacount);
4080 
4081 	/*
4082 	 * We have 2 cases here.  First where we can fit all the
4083 	 * SG elements into the main frame, and the case
4084 	 * where we can't.
4085 	 * If we have more cookies than we can attach to a frame
4086 	 * we will need to use a chain element to point
4087 	 * a location of memory where the rest of the S/G
4088 	 * elements reside.
4089 	 */
4090 	if (cookiec <= MPTSAS_MAX_FRAME_SGES64(mpt)) {
4091 		dmap = cmd->cmd_sg;
4092 		sge = (pMpi2SGESimple64_t)(&frame->SGL);
4093 		while (cookiec--) {
4094 			ddi_put32(acc_hdl,
4095 			    &sge->Address.Low, dmap->addr.address64.Low);
4096 			ddi_put32(acc_hdl,
4097 			    &sge->Address.High, dmap->addr.address64.High);
4098 			ddi_put32(acc_hdl, &sge->FlagsLength,
4099 			    dmap->count);
4100 			flags = ddi_get32(acc_hdl, &sge->FlagsLength);
4101 			flags |= ((uint32_t)
4102 			    (MPI2_SGE_FLAGS_SIMPLE_ELEMENT |
4103 			    MPI2_SGE_FLAGS_SYSTEM_ADDRESS |
4104 			    MPI2_SGE_FLAGS_64_BIT_ADDRESSING) <<
4105 			    MPI2_SGE_FLAGS_SHIFT);
4106 
4107 			/*
4108 			 * If this is the last cookie, we set the flags
4109 			 * to indicate so
4110 			 */
4111 			if (cookiec == 0) {
4112 				flags |=
4113 				    ((uint32_t)(MPI2_SGE_FLAGS_LAST_ELEMENT
4114 				    | MPI2_SGE_FLAGS_END_OF_BUFFER
4115 				    | MPI2_SGE_FLAGS_END_OF_LIST) <<
4116 				    MPI2_SGE_FLAGS_SHIFT);
4117 			}
4118 			if (cmd->cmd_flags & CFLAG_DMASEND) {
4119 				flags |= (MPI2_SGE_FLAGS_HOST_TO_IOC <<
4120 				    MPI2_SGE_FLAGS_SHIFT);
4121 			} else {
4122 				flags |= (MPI2_SGE_FLAGS_IOC_TO_HOST <<
4123 				    MPI2_SGE_FLAGS_SHIFT);
4124 			}
4125 			ddi_put32(acc_hdl, &sge->FlagsLength, flags);
4126 			dmap++;
4127 			sge++;
4128 		}
4129 	} else {
4130 		/*
4131 		 * Hereby we start to deal with multiple frames.
4132 		 * The process is as follows:
4133 		 * 1. Determine how many frames are needed for SGL element
4134 		 *    storage; Note that all frames are stored in contiguous
4135 		 *    memory space and in 64-bit DMA mode each element is
4136 		 *    3 double-words (12 bytes) long.
4137 		 * 2. Fill up the main frame. We need to do this separately
4138 		 *    since it contains the SCSI IO request header and needs
4139 		 *    dedicated processing. Note that the last 4 double-words
4140 		 *    of the SCSI IO header is for SGL element storage
4141 		 *    (MPI2_SGE_IO_UNION).
4142 		 * 3. Fill the chain element in the main frame, so the DMA
4143 		 *    engine can use the following frames.
4144 		 * 4. Enter a loop to fill the remaining frames. Note that the
4145 		 *    last frame contains no chain element.  The remaining
4146 		 *    frames go into the mpt SGL buffer allocated on the fly,
4147 		 *    not immediately following the main message frame, as in
4148 		 *    Gen1.
4149 		 * Some restrictions:
4150 		 * 1. For 64-bit DMA, the simple element and chain element
4151 		 *    are both of 3 double-words (12 bytes) in size, even
4152 		 *    though all frames are stored in the first 4G of mem
4153 		 *    range and the higher 32-bits of the address are always 0.
4154 		 * 2. On some controllers (like the 1064/1068), a frame can
4155 		 *    hold SGL elements with the last 1 or 2 double-words
4156 		 *    (4 or 8 bytes) un-used. On these controllers, we should
4157 		 *    recognize that there's not enough room for another SGL
4158 		 *    element and move the sge pointer to the next frame.
4159 		 */
4160 		int		i, j, k, l, frames, sgemax;
4161 		int		temp;
4162 		uint8_t		chainflags;
4163 		uint16_t	chainlength;
4164 		mptsas_cache_frames_t *p;
4165 
4166 		/*
4167 		 * Sgemax is the number of SGE's that will fit
4168 		 * each extra frame and frames is total
4169 		 * number of frames we'll need.  1 sge entry per
4170 		 * frame is reseverd for the chain element thus the -1 below.
4171 		 */
4172 		sgemax = ((mpt->m_req_frame_size / sizeof (MPI2_SGE_SIMPLE64))
4173 		    - 1);
4174 		temp = (cookiec - (MPTSAS_MAX_FRAME_SGES64(mpt) - 1)) / sgemax;
4175 
4176 		/*
4177 		 * A little check to see if we need to round up the number
4178 		 * of frames we need
4179 		 */
4180 		if ((cookiec - (MPTSAS_MAX_FRAME_SGES64(mpt) - 1)) - (temp *
4181 		    sgemax) > 1) {
4182 			frames = (temp + 1);
4183 		} else {
4184 			frames = temp;
4185 		}
4186 		dmap = cmd->cmd_sg;
4187 		sge = (pMpi2SGESimple64_t)(&frame->SGL);
4188 
4189 		/*
4190 		 * First fill in the main frame
4191 		 */
4192 		for (j = 1; j < MPTSAS_MAX_FRAME_SGES64(mpt); j++) {
4193 			ddi_put32(acc_hdl, &sge->Address.Low,
4194 			    dmap->addr.address64.Low);
4195 			ddi_put32(acc_hdl, &sge->Address.High,
4196 			    dmap->addr.address64.High);
4197 			ddi_put32(acc_hdl, &sge->FlagsLength, dmap->count);
4198 			flags = ddi_get32(acc_hdl, &sge->FlagsLength);
4199 			flags |= ((uint32_t)(MPI2_SGE_FLAGS_SIMPLE_ELEMENT |
4200 			    MPI2_SGE_FLAGS_SYSTEM_ADDRESS |
4201 			    MPI2_SGE_FLAGS_64_BIT_ADDRESSING) <<
4202 			    MPI2_SGE_FLAGS_SHIFT);
4203 
4204 			/*
4205 			 * If this is the last SGE of this frame
4206 			 * we set the end of list flag
4207 			 */
4208 			if (j == (MPTSAS_MAX_FRAME_SGES64(mpt) - 1)) {
4209 				flags |= ((uint32_t)
4210 				    (MPI2_SGE_FLAGS_LAST_ELEMENT) <<
4211 				    MPI2_SGE_FLAGS_SHIFT);
4212 			}
4213 			if (cmd->cmd_flags & CFLAG_DMASEND) {
4214 				flags |=
4215 				    (MPI2_SGE_FLAGS_HOST_TO_IOC <<
4216 				    MPI2_SGE_FLAGS_SHIFT);
4217 			} else {
4218 				flags |=
4219 				    (MPI2_SGE_FLAGS_IOC_TO_HOST <<
4220 				    MPI2_SGE_FLAGS_SHIFT);
4221 			}
4222 			ddi_put32(acc_hdl, &sge->FlagsLength, flags);
4223 			dmap++;
4224 			sge++;
4225 		}
4226 
4227 		/*
4228 		 * Fill in the chain element in the main frame.
4229 		 * About calculation on ChainOffset:
4230 		 * 1. Struct msg_scsi_io_request has 4 double-words (16 bytes)
4231 		 *    in the end reserved for SGL element storage
4232 		 *    (MPI2_SGE_IO_UNION); we should count it in our
4233 		 *    calculation.  See its definition in the header file.
4234 		 * 2. Constant j is the counter of the current SGL element
4235 		 *    that will be processed, and (j - 1) is the number of
4236 		 *    SGL elements that have been processed (stored in the
4237 		 *    main frame).
4238 		 * 3. ChainOffset value should be in units of double-words (4
4239 		 *    bytes) so the last value should be divided by 4.
4240 		 */
4241 		ddi_put8(acc_hdl, &frame->ChainOffset,
4242 		    (sizeof (MPI2_SCSI_IO_REQUEST) -
4243 		    sizeof (MPI2_SGE_IO_UNION) +
4244 		    (j - 1) * sizeof (MPI2_SGE_SIMPLE64)) >> 2);
4245 		sgechain = (pMpi2SGEChain64_t)sge;
4246 		chainflags = (MPI2_SGE_FLAGS_CHAIN_ELEMENT |
4247 		    MPI2_SGE_FLAGS_SYSTEM_ADDRESS |
4248 		    MPI2_SGE_FLAGS_64_BIT_ADDRESSING);
4249 		ddi_put8(acc_hdl, &sgechain->Flags, chainflags);
4250 
4251 		/*
4252 		 * The size of the next frame is the accurate size of space
4253 		 * (in bytes) used to store the SGL elements. j is the counter
4254 		 * of SGL elements. (j - 1) is the number of SGL elements that
4255 		 * have been processed (stored in frames).
4256 		 */
4257 		if (frames >= 2) {
4258 			chainlength = mpt->m_req_frame_size /
4259 			    sizeof (MPI2_SGE_SIMPLE64) *
4260 			    sizeof (MPI2_SGE_SIMPLE64);
4261 		} else {
4262 			chainlength = ((cookiec - (j - 1)) *
4263 			    sizeof (MPI2_SGE_SIMPLE64));
4264 		}
4265 
4266 		p = cmd->cmd_extra_frames;
4267 
4268 		ddi_put16(acc_hdl, &sgechain->Length, chainlength);
4269 		ddi_put32(acc_hdl, &sgechain->Address.Low,
4270 		    p->m_phys_addr);
4271 		/* SGL is allocated in the first 4G mem range */
4272 		ddi_put32(acc_hdl, &sgechain->Address.High, 0);
4273 
4274 		/*
4275 		 * If there are more than 2 frames left we have to
4276 		 * fill in the next chain offset to the location of
4277 		 * the chain element in the next frame.
4278 		 * sgemax is the number of simple elements in an extra
4279 		 * frame. Note that the value NextChainOffset should be
4280 		 * in double-words (4 bytes).
4281 		 */
4282 		if (frames >= 2) {
4283 			ddi_put8(acc_hdl, &sgechain->NextChainOffset,
4284 			    (sgemax * sizeof (MPI2_SGE_SIMPLE64)) >> 2);
4285 		} else {
4286 			ddi_put8(acc_hdl, &sgechain->NextChainOffset, 0);
4287 		}
4288 
4289 		/*
4290 		 * Jump to next frame;
4291 		 * Starting here, chain buffers go into the per command SGL.
4292 		 * This buffer is allocated when chain buffers are needed.
4293 		 */
4294 		sge = (pMpi2SGESimple64_t)p->m_frames_addr;
4295 		i = cookiec;
4296 
4297 		/*
4298 		 * Start filling in frames with SGE's.  If we
4299 		 * reach the end of frame and still have SGE's
4300 		 * to fill we need to add a chain element and
4301 		 * use another frame.  j will be our counter
4302 		 * for what cookie we are at and i will be
4303 		 * the total cookiec. k is the current frame
4304 		 */
4305 		for (k = 1; k <= frames; k++) {
4306 			for (l = 1; (l <= (sgemax + 1)) && (j <= i); j++, l++) {
4307 
4308 				/*
4309 				 * If we have reached the end of frame
4310 				 * and we have more SGE's to fill in
4311 				 * we have to fill the final entry
4312 				 * with a chain element and then
4313 				 * continue to the next frame
4314 				 */
4315 				if ((l == (sgemax + 1)) && (k != frames)) {
4316 					sgechain = (pMpi2SGEChain64_t)sge;
4317 					j--;
4318 					chainflags = (
4319 					    MPI2_SGE_FLAGS_CHAIN_ELEMENT |
4320 					    MPI2_SGE_FLAGS_SYSTEM_ADDRESS |
4321 					    MPI2_SGE_FLAGS_64_BIT_ADDRESSING);
4322 					ddi_put8(p->m_acc_hdl,
4323 					    &sgechain->Flags, chainflags);
4324 					/*
4325 					 * k is the frame counter and (k + 1)
4326 					 * is the number of the next frame.
4327 					 * Note that frames are in contiguous
4328 					 * memory space.
4329 					 */
4330 					ddi_put32(p->m_acc_hdl,
4331 					    &sgechain->Address.Low,
4332 					    (p->m_phys_addr +
4333 					    (mpt->m_req_frame_size * k)));
4334 					ddi_put32(p->m_acc_hdl,
4335 					    &sgechain->Address.High, 0);
4336 
4337 					/*
4338 					 * If there are more than 2 frames left
4339 					 * we have to next chain offset to
4340 					 * the location of the chain element
4341 					 * in the next frame and fill in the
4342 					 * length of the next chain
4343 					 */
4344 					if ((frames - k) >= 2) {
4345 						ddi_put8(p->m_acc_hdl,
4346 						    &sgechain->NextChainOffset,
4347 						    (sgemax *
4348 						    sizeof (MPI2_SGE_SIMPLE64))
4349 						    >> 2);
4350 						ddi_put16(p->m_acc_hdl,
4351 						    &sgechain->Length,
4352 						    mpt->m_req_frame_size /
4353 						    sizeof (MPI2_SGE_SIMPLE64) *
4354 						    sizeof (MPI2_SGE_SIMPLE64));
4355 					} else {
4356 						/*
4357 						 * This is the last frame. Set
4358 						 * the NextChainOffset to 0 and
4359 						 * Length is the total size of
4360 						 * all remaining simple elements
4361 						 */
4362 						ddi_put8(p->m_acc_hdl,
4363 						    &sgechain->NextChainOffset,
4364 						    0);
4365 						ddi_put16(p->m_acc_hdl,
4366 						    &sgechain->Length,
4367 						    (cookiec - j) *
4368 						    sizeof (MPI2_SGE_SIMPLE64));
4369 					}
4370 
4371 					/* Jump to the next frame */
4372 					sge = (pMpi2SGESimple64_t)
4373 					    ((char *)p->m_frames_addr +
4374 					    (int)mpt->m_req_frame_size * k);
4375 
4376 					continue;
4377 				}
4378 
4379 				ddi_put32(p->m_acc_hdl,
4380 				    &sge->Address.Low,
4381 				    dmap->addr.address64.Low);
4382 				ddi_put32(p->m_acc_hdl,
4383 				    &sge->Address.High,
4384 				    dmap->addr.address64.High);
4385 				ddi_put32(p->m_acc_hdl,
4386 				    &sge->FlagsLength, dmap->count);
4387 				flags = ddi_get32(p->m_acc_hdl,
4388 				    &sge->FlagsLength);
4389 				flags |= ((uint32_t)(
4390 				    MPI2_SGE_FLAGS_SIMPLE_ELEMENT |
4391 				    MPI2_SGE_FLAGS_SYSTEM_ADDRESS |
4392 				    MPI2_SGE_FLAGS_64_BIT_ADDRESSING) <<
4393 				    MPI2_SGE_FLAGS_SHIFT);
4394 
4395 				/*
4396 				 * If we are at the end of the frame and
4397 				 * there is another frame to fill in
4398 				 * we set the last simple element as last
4399 				 * element
4400 				 */
4401 				if ((l == sgemax) && (k != frames)) {
4402 					flags |= ((uint32_t)
4403 					    (MPI2_SGE_FLAGS_LAST_ELEMENT) <<
4404 					    MPI2_SGE_FLAGS_SHIFT);
4405 				}
4406 
4407 				/*
4408 				 * If this is the final cookie we
4409 				 * indicate it by setting the flags
4410 				 */
4411 				if (j == i) {
4412 					flags |= ((uint32_t)
4413 					    (MPI2_SGE_FLAGS_LAST_ELEMENT |
4414 					    MPI2_SGE_FLAGS_END_OF_BUFFER |
4415 					    MPI2_SGE_FLAGS_END_OF_LIST) <<
4416 					    MPI2_SGE_FLAGS_SHIFT);
4417 				}
4418 				if (cmd->cmd_flags & CFLAG_DMASEND) {
4419 					flags |=
4420 					    (MPI2_SGE_FLAGS_HOST_TO_IOC <<
4421 					    MPI2_SGE_FLAGS_SHIFT);
4422 				} else {
4423 					flags |=
4424 					    (MPI2_SGE_FLAGS_IOC_TO_HOST <<
4425 					    MPI2_SGE_FLAGS_SHIFT);
4426 				}
4427 				ddi_put32(p->m_acc_hdl,
4428 				    &sge->FlagsLength, flags);
4429 				dmap++;
4430 				sge++;
4431 			}
4432 		}
4433 
4434 		/*
4435 		 * Sync DMA with the chain buffers that were just created
4436 		 */
4437 		(void) ddi_dma_sync(p->m_dma_hdl, 0, 0, DDI_DMA_SYNC_FORDEV);
4438 	}
4439 }
4440 
4441 /*
4442  * Interrupt handling
4443  * Utility routine.  Poll for status of a command sent to HBA
4444  * without interrupts (a FLAG_NOINTR command).
4445  */
4446 int
4447 mptsas_poll(mptsas_t *mpt, mptsas_cmd_t *poll_cmd, int polltime)
4448 {
4449 	int	rval = TRUE;
4450 
4451 	NDBG5(("mptsas_poll: cmd=0x%p", (void *)poll_cmd));
4452 
4453 	if ((poll_cmd->cmd_flags & CFLAG_TM_CMD) == 0) {
4454 		mptsas_restart_hba(mpt);
4455 	}
4456 
4457 	/*
4458 	 * Wait, using drv_usecwait(), long enough for the command to
4459 	 * reasonably return from the target if the target isn't
4460 	 * "dead".  A polled command may well be sent from scsi_poll, and
4461 	 * there are retries built in to scsi_poll if the transport
4462 	 * accepted the packet (TRAN_ACCEPT).  scsi_poll waits 1 second
4463 	 * and retries the transport up to scsi_poll_busycnt times
4464 	 * (currently 60) if
4465 	 * 1. pkt_reason is CMD_INCOMPLETE and pkt_state is 0, or
4466 	 * 2. pkt_reason is CMD_CMPLT and *pkt_scbp has STATUS_BUSY
4467 	 *
4468 	 * limit the waiting to avoid a hang in the event that the
4469 	 * cmd never gets started but we are still receiving interrupts
4470 	 */
4471 	while (!(poll_cmd->cmd_flags & CFLAG_FINISHED)) {
4472 		if (mptsas_wait_intr(mpt, polltime) == FALSE) {
4473 			NDBG5(("mptsas_poll: command incomplete"));
4474 			rval = FALSE;
4475 			break;
4476 		}
4477 	}
4478 
4479 	if (rval == FALSE) {
4480 
4481 		/*
4482 		 * this isn't supposed to happen, the hba must be wedged
4483 		 * Mark this cmd as a timeout.
4484 		 */
4485 		mptsas_set_pkt_reason(mpt, poll_cmd, CMD_TIMEOUT,
4486 		    (STAT_TIMEOUT|STAT_ABORTED));
4487 
4488 		if (poll_cmd->cmd_queued == FALSE) {
4489 
4490 			NDBG5(("mptsas_poll: not on waitq"));
4491 
4492 			poll_cmd->cmd_pkt->pkt_state |=
4493 			    (STATE_GOT_BUS|STATE_GOT_TARGET|STATE_SENT_CMD);
4494 		} else {
4495 
4496 			/* find and remove it from the waitq */
4497 			NDBG5(("mptsas_poll: delete from waitq"));
4498 			mptsas_waitq_delete(mpt, poll_cmd);
4499 		}
4500 
4501 	}
4502 	mptsas_fma_check(mpt, poll_cmd);
4503 	NDBG5(("mptsas_poll: done"));
4504 	return (rval);
4505 }
4506 
4507 /*
4508  * Used for polling cmds and TM function
4509  */
4510 static int
4511 mptsas_wait_intr(mptsas_t *mpt, int polltime)
4512 {
4513 	int				cnt;
4514 	pMpi2ReplyDescriptorsUnion_t	reply_desc_union;
4515 	uint32_t			int_mask;
4516 
4517 	NDBG5(("mptsas_wait_intr"));
4518 
4519 	mpt->m_polled_intr = 1;
4520 
4521 	/*
4522 	 * Get the current interrupt mask.  When re-enabling ints, set mask to
4523 	 * saved value.
4524 	 */
4525 	int_mask = ddi_get32(mpt->m_datap, &mpt->m_reg->HostInterruptMask);
4526 	MPTSAS_DISABLE_INTR(mpt);
4527 
4528 	/*
4529 	 * Keep polling for at least (polltime * 1000) seconds
4530 	 */
4531 	for (cnt = 0; cnt < polltime; cnt++) {
4532 		(void) ddi_dma_sync(mpt->m_dma_post_queue_hdl, 0, 0,
4533 		    DDI_DMA_SYNC_FORCPU);
4534 
4535 		reply_desc_union = (pMpi2ReplyDescriptorsUnion_t)
4536 		    MPTSAS_GET_NEXT_REPLY(mpt, mpt->m_post_index);
4537 
4538 		if (ddi_get32(mpt->m_acc_post_queue_hdl,
4539 		    &reply_desc_union->Words.Low) == 0xFFFFFFFF ||
4540 		    ddi_get32(mpt->m_acc_post_queue_hdl,
4541 		    &reply_desc_union->Words.High) == 0xFFFFFFFF) {
4542 			drv_usecwait(1000);
4543 			continue;
4544 		}
4545 		/*
4546 		 * The reply is valid, process it according to its
4547 		 * type.
4548 		 */
4549 		mptsas_process_intr(mpt, reply_desc_union);
4550 
4551 		if (++mpt->m_post_index == mpt->m_post_queue_depth) {
4552 			mpt->m_post_index = 0;
4553 		}
4554 
4555 		ddi_put32(mpt->m_datap,
4556 		    &mpt->m_reg->ReplyPostHostIndex, mpt->m_post_index);
4557 
4558 		mpt->m_polled_intr = 0;
4559 		/*
4560 		 * Re-enable interrupts and quit.
4561 		 */
4562 		ddi_put32(mpt->m_datap, &mpt->m_reg->HostInterruptMask,
4563 		    int_mask);
4564 		return (TRUE);
4565 
4566 	}
4567 
4568 	/*
4569 	 * Clear polling flag, re-enable interrupts and quit.
4570 	 */
4571 	mpt->m_polled_intr = 0;
4572 	ddi_put32(mpt->m_datap, &mpt->m_reg->HostInterruptMask, int_mask);
4573 	return (FALSE);
4574 }
4575 
4576 static void
4577 mptsas_handle_scsi_io_success(mptsas_t *mpt,
4578     pMpi2ReplyDescriptorsUnion_t reply_desc)
4579 {
4580 	pMpi2SCSIIOSuccessReplyDescriptor_t	scsi_io_success;
4581 	uint16_t				SMID;
4582 	mptsas_slots_t				*slots = mpt->m_active;
4583 	mptsas_cmd_t				*cmd = NULL;
4584 	struct scsi_pkt				*pkt;
4585 
4586 	ASSERT(mutex_owned(&mpt->m_mutex));
4587 
4588 	scsi_io_success = (pMpi2SCSIIOSuccessReplyDescriptor_t)reply_desc;
4589 	SMID = ddi_get16(mpt->m_acc_post_queue_hdl, &scsi_io_success->SMID);
4590 
4591 	/*
4592 	 * This is a success reply so just complete the IO.  First, do a sanity
4593 	 * check on the SMID.  The final slot is used for TM requests, which
4594 	 * would not come into this reply handler.
4595 	 */
4596 	if ((SMID == 0) || (SMID > slots->m_n_slots)) {
4597 		mptsas_log(mpt, CE_WARN, "?Received invalid SMID of %d\n",
4598 		    SMID);
4599 		ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_UNAFFECTED);
4600 		return;
4601 	}
4602 
4603 	cmd = slots->m_slot[SMID];
4604 
4605 	/*
4606 	 * print warning and return if the slot is empty
4607 	 */
4608 	if (cmd == NULL) {
4609 		mptsas_log(mpt, CE_WARN, "?NULL command for successful SCSI IO "
4610 		    "in slot %d", SMID);
4611 		return;
4612 	}
4613 
4614 	pkt = CMD2PKT(cmd);
4615 	pkt->pkt_state |= (STATE_GOT_BUS | STATE_GOT_TARGET | STATE_SENT_CMD |
4616 	    STATE_GOT_STATUS);
4617 	if (cmd->cmd_flags & CFLAG_DMAVALID) {
4618 		pkt->pkt_state |= STATE_XFERRED_DATA;
4619 	}
4620 	pkt->pkt_resid = 0;
4621 
4622 	if (cmd->cmd_flags & CFLAG_PASSTHRU) {
4623 		cmd->cmd_flags |= CFLAG_FINISHED;
4624 		cv_broadcast(&mpt->m_passthru_cv);
4625 		return;
4626 	} else {
4627 		mptsas_remove_cmd(mpt, cmd);
4628 	}
4629 
4630 	if (cmd->cmd_flags & CFLAG_RETRY) {
4631 		/*
4632 		 * The target returned QFULL or busy, do not add tihs
4633 		 * pkt to the doneq since the hba will retry
4634 		 * this cmd.
4635 		 *
4636 		 * The pkt has already been resubmitted in
4637 		 * mptsas_handle_qfull() or in mptsas_check_scsi_io_error().
4638 		 * Remove this cmd_flag here.
4639 		 */
4640 		cmd->cmd_flags &= ~CFLAG_RETRY;
4641 	} else {
4642 		mptsas_doneq_add(mpt, cmd);
4643 	}
4644 }
4645 
4646 static void
4647 mptsas_handle_address_reply(mptsas_t *mpt,
4648     pMpi2ReplyDescriptorsUnion_t reply_desc)
4649 {
4650 	pMpi2AddressReplyDescriptor_t	address_reply;
4651 	pMPI2DefaultReply_t		reply;
4652 	uint32_t			reply_addr;
4653 	uint16_t			SMID;
4654 	mptsas_slots_t			*slots = mpt->m_active;
4655 	mptsas_cmd_t			*cmd = NULL;
4656 	uint8_t				function;
4657 	m_replyh_arg_t			*args;
4658 	int				reply_frame_no;
4659 
4660 	ASSERT(mutex_owned(&mpt->m_mutex));
4661 
4662 	address_reply = (pMpi2AddressReplyDescriptor_t)reply_desc;
4663 	reply_addr = ddi_get32(mpt->m_acc_post_queue_hdl,
4664 	    &address_reply->ReplyFrameAddress);
4665 	SMID = ddi_get16(mpt->m_acc_post_queue_hdl, &address_reply->SMID);
4666 
4667 	/*
4668 	 * If reply frame is not in the proper range we should ignore this
4669 	 * message and exit the interrupt handler.
4670 	 */
4671 	if ((reply_addr < mpt->m_reply_frame_dma_addr) ||
4672 	    (reply_addr >= (mpt->m_reply_frame_dma_addr +
4673 	    (mpt->m_reply_frame_size * mpt->m_free_queue_depth))) ||
4674 	    ((reply_addr - mpt->m_reply_frame_dma_addr) %
4675 	    mpt->m_reply_frame_size != 0)) {
4676 		mptsas_log(mpt, CE_WARN, "?Received invalid reply frame "
4677 		    "address 0x%x\n", reply_addr);
4678 		ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_UNAFFECTED);
4679 		return;
4680 	}
4681 
4682 	(void) ddi_dma_sync(mpt->m_dma_reply_frame_hdl, 0, 0,
4683 	    DDI_DMA_SYNC_FORCPU);
4684 	reply = (pMPI2DefaultReply_t)(mpt->m_reply_frame + (reply_addr -
4685 	    mpt->m_reply_frame_dma_addr));
4686 	function = ddi_get8(mpt->m_acc_reply_frame_hdl, &reply->Function);
4687 
4688 	/*
4689 	 * don't get slot information and command for events since these values
4690 	 * don't exist
4691 	 */
4692 	if (function != MPI2_FUNCTION_EVENT_NOTIFICATION) {
4693 		/*
4694 		 * This could be a TM reply, which use the last allocated SMID,
4695 		 * so allow for that.
4696 		 */
4697 		if ((SMID == 0) || (SMID > (slots->m_n_slots + 1))) {
4698 			mptsas_log(mpt, CE_WARN, "?Received invalid SMID of "
4699 			    "%d\n", SMID);
4700 			ddi_fm_service_impact(mpt->m_dip,
4701 			    DDI_SERVICE_UNAFFECTED);
4702 			return;
4703 		}
4704 
4705 		cmd = slots->m_slot[SMID];
4706 
4707 		/*
4708 		 * print warning and return if the slot is empty
4709 		 */
4710 		if (cmd == NULL) {
4711 			mptsas_log(mpt, CE_WARN, "?NULL command for address "
4712 			    "reply in slot %d", SMID);
4713 			return;
4714 		}
4715 		if ((cmd->cmd_flags & CFLAG_PASSTHRU) ||
4716 		    (cmd->cmd_flags & CFLAG_CONFIG)) {
4717 			cmd->cmd_rfm = reply_addr;
4718 			cmd->cmd_flags |= CFLAG_FINISHED;
4719 			cv_broadcast(&mpt->m_passthru_cv);
4720 			cv_broadcast(&mpt->m_config_cv);
4721 			return;
4722 		} else if (!(cmd->cmd_flags & CFLAG_FW_CMD)) {
4723 			mptsas_remove_cmd(mpt, cmd);
4724 		}
4725 		NDBG31(("\t\tmptsas_process_intr: slot=%d", SMID));
4726 	}
4727 	/*
4728 	 * Depending on the function, we need to handle
4729 	 * the reply frame (and cmd) differently.
4730 	 */
4731 	switch (function) {
4732 	case MPI2_FUNCTION_SCSI_IO_REQUEST:
4733 		mptsas_check_scsi_io_error(mpt, (pMpi2SCSIIOReply_t)reply, cmd);
4734 		break;
4735 	case MPI2_FUNCTION_SCSI_TASK_MGMT:
4736 		mptsas_check_task_mgt(mpt, (pMpi2SCSIManagementReply_t)reply,
4737 		    cmd);
4738 		break;
4739 	case MPI2_FUNCTION_FW_DOWNLOAD:
4740 		cmd->cmd_flags |= CFLAG_FINISHED;
4741 		cv_signal(&mpt->m_fw_cv);
4742 		break;
4743 	case MPI2_FUNCTION_EVENT_NOTIFICATION:
4744 		reply_frame_no = (reply_addr - mpt->m_reply_frame_dma_addr) /
4745 		    mpt->m_reply_frame_size;
4746 		args = &mpt->m_replyh_args[reply_frame_no];
4747 		args->mpt = (void *)mpt;
4748 		args->rfm = reply_addr;
4749 
4750 		/*
4751 		 * Record the event if its type is enabled in
4752 		 * this mpt instance by ioctl.
4753 		 */
4754 		mptsas_record_event(args);
4755 
4756 		/*
4757 		 * Handle time critical events
4758 		 * NOT_RESPONDING/ADDED only now
4759 		 */
4760 		if (mptsas_handle_event_sync(args) == DDI_SUCCESS) {
4761 			/*
4762 			 * Would not return main process,
4763 			 * just let taskq resolve ack action
4764 			 * and ack would be sent in taskq thread
4765 			 */
4766 			NDBG20(("send mptsas_handle_event_sync success"));
4767 		}
4768 		if ((ddi_taskq_dispatch(mpt->m_event_taskq, mptsas_handle_event,
4769 		    (void *)args, DDI_NOSLEEP)) != DDI_SUCCESS) {
4770 			mptsas_log(mpt, CE_WARN, "No memory available"
4771 			"for dispatch taskq");
4772 			/*
4773 			 * Return the reply frame to the free queue.
4774 			 */
4775 			ddi_put32(mpt->m_acc_free_queue_hdl,
4776 			    &((uint32_t *)(void *)
4777 			    mpt->m_free_queue)[mpt->m_free_index], reply_addr);
4778 			(void) ddi_dma_sync(mpt->m_dma_free_queue_hdl, 0, 0,
4779 			    DDI_DMA_SYNC_FORDEV);
4780 			if (++mpt->m_free_index == mpt->m_free_queue_depth) {
4781 				mpt->m_free_index = 0;
4782 			}
4783 
4784 			ddi_put32(mpt->m_datap,
4785 			    &mpt->m_reg->ReplyFreeHostIndex, mpt->m_free_index);
4786 		}
4787 		return;
4788 	default:
4789 		mptsas_log(mpt, CE_WARN, "Unknown function 0x%x ", function);
4790 		break;
4791 	}
4792 
4793 	/*
4794 	 * Return the reply frame to the free queue.
4795 	 */
4796 	ddi_put32(mpt->m_acc_free_queue_hdl,
4797 	    &((uint32_t *)(void *)mpt->m_free_queue)[mpt->m_free_index],
4798 	    reply_addr);
4799 	(void) ddi_dma_sync(mpt->m_dma_free_queue_hdl, 0, 0,
4800 	    DDI_DMA_SYNC_FORDEV);
4801 	if (++mpt->m_free_index == mpt->m_free_queue_depth) {
4802 		mpt->m_free_index = 0;
4803 	}
4804 	ddi_put32(mpt->m_datap, &mpt->m_reg->ReplyFreeHostIndex,
4805 	    mpt->m_free_index);
4806 
4807 	if (cmd->cmd_flags & CFLAG_FW_CMD)
4808 		return;
4809 
4810 	if (cmd->cmd_flags & CFLAG_RETRY) {
4811 		/*
4812 		 * The target returned QFULL or busy, do not add tihs
4813 		 * pkt to the doneq since the hba will retry
4814 		 * this cmd.
4815 		 *
4816 		 * The pkt has already been resubmitted in
4817 		 * mptsas_handle_qfull() or in mptsas_check_scsi_io_error().
4818 		 * Remove this cmd_flag here.
4819 		 */
4820 		cmd->cmd_flags &= ~CFLAG_RETRY;
4821 	} else {
4822 		mptsas_doneq_add(mpt, cmd);
4823 	}
4824 }
4825 
4826 static void
4827 mptsas_check_scsi_io_error(mptsas_t *mpt, pMpi2SCSIIOReply_t reply,
4828     mptsas_cmd_t *cmd)
4829 {
4830 	uint8_t			scsi_status, scsi_state;
4831 	uint16_t		ioc_status;
4832 	uint32_t		xferred, sensecount, responsedata, loginfo = 0;
4833 	struct scsi_pkt		*pkt;
4834 	struct scsi_arq_status	*arqstat;
4835 	struct buf		*bp;
4836 	mptsas_target_t		*ptgt = cmd->cmd_tgt_addr;
4837 	uint8_t			*sensedata = NULL;
4838 
4839 	if ((cmd->cmd_flags & (CFLAG_SCBEXTERN | CFLAG_EXTARQBUFVALID)) ==
4840 	    (CFLAG_SCBEXTERN | CFLAG_EXTARQBUFVALID)) {
4841 		bp = cmd->cmd_ext_arq_buf;
4842 	} else {
4843 		bp = cmd->cmd_arq_buf;
4844 	}
4845 
4846 	scsi_status = ddi_get8(mpt->m_acc_reply_frame_hdl, &reply->SCSIStatus);
4847 	ioc_status = ddi_get16(mpt->m_acc_reply_frame_hdl, &reply->IOCStatus);
4848 	scsi_state = ddi_get8(mpt->m_acc_reply_frame_hdl, &reply->SCSIState);
4849 	xferred = ddi_get32(mpt->m_acc_reply_frame_hdl, &reply->TransferCount);
4850 	sensecount = ddi_get32(mpt->m_acc_reply_frame_hdl, &reply->SenseCount);
4851 	responsedata = ddi_get32(mpt->m_acc_reply_frame_hdl,
4852 	    &reply->ResponseInfo);
4853 
4854 	if (ioc_status & MPI2_IOCSTATUS_FLAG_LOG_INFO_AVAILABLE) {
4855 		loginfo = ddi_get32(mpt->m_acc_reply_frame_hdl,
4856 		    &reply->IOCLogInfo);
4857 		mptsas_log(mpt, CE_NOTE,
4858 		    "?Log info 0x%x received for target %d.\n"
4859 		    "\tscsi_status=0x%x, ioc_status=0x%x, scsi_state=0x%x",
4860 		    loginfo, Tgt(cmd), scsi_status, ioc_status,
4861 		    scsi_state);
4862 	}
4863 
4864 	NDBG31(("\t\tscsi_status=0x%x, ioc_status=0x%x, scsi_state=0x%x",
4865 	    scsi_status, ioc_status, scsi_state));
4866 
4867 	pkt = CMD2PKT(cmd);
4868 	*(pkt->pkt_scbp) = scsi_status;
4869 
4870 	if (loginfo == 0x31170000) {
4871 		/*
4872 		 * if loginfo PL_LOGINFO_CODE_IO_DEVICE_MISSING_DELAY_RETRY
4873 		 * 0x31170000 comes, that means the device missing delay
4874 		 * is in progressing, the command need retry later.
4875 		 */
4876 		*(pkt->pkt_scbp) = STATUS_BUSY;
4877 		return;
4878 	}
4879 
4880 	if ((scsi_state & MPI2_SCSI_STATE_NO_SCSI_STATUS) &&
4881 	    ((ioc_status & MPI2_IOCSTATUS_MASK) ==
4882 	    MPI2_IOCSTATUS_SCSI_DEVICE_NOT_THERE)) {
4883 		pkt->pkt_reason = CMD_INCOMPLETE;
4884 		pkt->pkt_state |= STATE_GOT_BUS;
4885 		if (ptgt->m_reset_delay == 0) {
4886 			mptsas_set_throttle(mpt, ptgt,
4887 			    DRAIN_THROTTLE);
4888 		}
4889 		return;
4890 	}
4891 
4892 	if (scsi_state & MPI2_SCSI_STATE_RESPONSE_INFO_VALID) {
4893 		responsedata &= 0x000000FF;
4894 		if (responsedata & MPTSAS_SCSI_RESPONSE_CODE_TLR_OFF) {
4895 			mptsas_log(mpt, CE_NOTE, "Do not support the TLR\n");
4896 			pkt->pkt_reason = CMD_TLR_OFF;
4897 			return;
4898 		}
4899 	}
4900 
4901 
4902 	switch (scsi_status) {
4903 	case MPI2_SCSI_STATUS_CHECK_CONDITION:
4904 		pkt->pkt_resid = (cmd->cmd_dmacount - xferred);
4905 		arqstat = (void*)(pkt->pkt_scbp);
4906 		arqstat->sts_rqpkt_status = *((struct scsi_status *)
4907 		    (pkt->pkt_scbp));
4908 		pkt->pkt_state |= (STATE_GOT_BUS | STATE_GOT_TARGET |
4909 		    STATE_SENT_CMD | STATE_GOT_STATUS | STATE_ARQ_DONE);
4910 		if (cmd->cmd_flags & CFLAG_XARQ) {
4911 			pkt->pkt_state |= STATE_XARQ_DONE;
4912 		}
4913 		if (pkt->pkt_resid != cmd->cmd_dmacount) {
4914 			pkt->pkt_state |= STATE_XFERRED_DATA;
4915 		}
4916 		arqstat->sts_rqpkt_reason = pkt->pkt_reason;
4917 		arqstat->sts_rqpkt_state  = pkt->pkt_state;
4918 		arqstat->sts_rqpkt_state |= STATE_XFERRED_DATA;
4919 		arqstat->sts_rqpkt_statistics = pkt->pkt_statistics;
4920 		sensedata = (uint8_t *)&arqstat->sts_sensedata;
4921 
4922 		bcopy((uchar_t *)bp->b_un.b_addr, sensedata,
4923 		    ((cmd->cmd_rqslen >= sensecount) ? sensecount :
4924 		    cmd->cmd_rqslen));
4925 		arqstat->sts_rqpkt_resid = (cmd->cmd_rqslen - sensecount);
4926 		cmd->cmd_flags |= CFLAG_CMDARQ;
4927 		/*
4928 		 * Set proper status for pkt if autosense was valid
4929 		 */
4930 		if (scsi_state & MPI2_SCSI_STATE_AUTOSENSE_VALID) {
4931 			struct scsi_status zero_status = { 0 };
4932 			arqstat->sts_rqpkt_status = zero_status;
4933 		}
4934 
4935 		/*
4936 		 * ASC=0x47 is parity error
4937 		 * ASC=0x48 is initiator detected error received
4938 		 */
4939 		if ((scsi_sense_key(sensedata) == KEY_ABORTED_COMMAND) &&
4940 		    ((scsi_sense_asc(sensedata) == 0x47) ||
4941 		    (scsi_sense_asc(sensedata) == 0x48))) {
4942 			mptsas_log(mpt, CE_NOTE, "Aborted_command!");
4943 		}
4944 
4945 		/*
4946 		 * ASC/ASCQ=0x3F/0x0E means report_luns data changed
4947 		 * ASC/ASCQ=0x25/0x00 means invalid lun
4948 		 */
4949 		if (((scsi_sense_key(sensedata) == KEY_UNIT_ATTENTION) &&
4950 		    (scsi_sense_asc(sensedata) == 0x3F) &&
4951 		    (scsi_sense_ascq(sensedata) == 0x0E)) ||
4952 		    ((scsi_sense_key(sensedata) == KEY_ILLEGAL_REQUEST) &&
4953 		    (scsi_sense_asc(sensedata) == 0x25) &&
4954 		    (scsi_sense_ascq(sensedata) == 0x00))) {
4955 			mptsas_topo_change_list_t *topo_node = NULL;
4956 
4957 			topo_node = kmem_zalloc(
4958 			    sizeof (mptsas_topo_change_list_t),
4959 			    KM_NOSLEEP);
4960 			if (topo_node == NULL) {
4961 				mptsas_log(mpt, CE_NOTE, "No memory"
4962 				    "resource for handle SAS dynamic"
4963 				    "reconfigure.\n");
4964 				break;
4965 			}
4966 			topo_node->mpt = mpt;
4967 			topo_node->event = MPTSAS_DR_EVENT_RECONFIG_TARGET;
4968 			topo_node->un.phymask = ptgt->m_phymask;
4969 			topo_node->devhdl = ptgt->m_devhdl;
4970 			topo_node->object = (void *)ptgt;
4971 			topo_node->flags = MPTSAS_TOPO_FLAG_LUN_ASSOCIATED;
4972 
4973 			if ((ddi_taskq_dispatch(mpt->m_dr_taskq,
4974 			    mptsas_handle_dr,
4975 			    (void *)topo_node,
4976 			    DDI_NOSLEEP)) != DDI_SUCCESS) {
4977 				mptsas_log(mpt, CE_NOTE, "mptsas start taskq"
4978 				    "for handle SAS dynamic reconfigure"
4979 				    "failed. \n");
4980 			}
4981 		}
4982 		break;
4983 	case MPI2_SCSI_STATUS_GOOD:
4984 		switch (ioc_status & MPI2_IOCSTATUS_MASK) {
4985 		case MPI2_IOCSTATUS_SCSI_DEVICE_NOT_THERE:
4986 			pkt->pkt_reason = CMD_DEV_GONE;
4987 			pkt->pkt_state |= STATE_GOT_BUS;
4988 			if (ptgt->m_reset_delay == 0) {
4989 				mptsas_set_throttle(mpt, ptgt, DRAIN_THROTTLE);
4990 			}
4991 			NDBG31(("lost disk for target%d, command:%x",
4992 			    Tgt(cmd), pkt->pkt_cdbp[0]));
4993 			break;
4994 		case MPI2_IOCSTATUS_SCSI_DATA_OVERRUN:
4995 			NDBG31(("data overrun: xferred=%d", xferred));
4996 			NDBG31(("dmacount=%d", cmd->cmd_dmacount));
4997 			pkt->pkt_reason = CMD_DATA_OVR;
4998 			pkt->pkt_state |= (STATE_GOT_BUS | STATE_GOT_TARGET
4999 			    | STATE_SENT_CMD | STATE_GOT_STATUS
5000 			    | STATE_XFERRED_DATA);
5001 			pkt->pkt_resid = 0;
5002 			break;
5003 		case MPI2_IOCSTATUS_SCSI_RESIDUAL_MISMATCH:
5004 		case MPI2_IOCSTATUS_SCSI_DATA_UNDERRUN:
5005 			NDBG31(("data underrun: xferred=%d", xferred));
5006 			NDBG31(("dmacount=%d", cmd->cmd_dmacount));
5007 			pkt->pkt_state |= (STATE_GOT_BUS | STATE_GOT_TARGET
5008 			    | STATE_SENT_CMD | STATE_GOT_STATUS);
5009 			pkt->pkt_resid = (cmd->cmd_dmacount - xferred);
5010 			if (pkt->pkt_resid != cmd->cmd_dmacount) {
5011 				pkt->pkt_state |= STATE_XFERRED_DATA;
5012 			}
5013 			break;
5014 		case MPI2_IOCSTATUS_SCSI_TASK_TERMINATED:
5015 			mptsas_set_pkt_reason(mpt,
5016 			    cmd, CMD_RESET, STAT_BUS_RESET);
5017 			break;
5018 		case MPI2_IOCSTATUS_SCSI_IOC_TERMINATED:
5019 		case MPI2_IOCSTATUS_SCSI_EXT_TERMINATED:
5020 			mptsas_set_pkt_reason(mpt,
5021 			    cmd, CMD_RESET, STAT_DEV_RESET);
5022 			break;
5023 		case MPI2_IOCSTATUS_SCSI_IO_DATA_ERROR:
5024 		case MPI2_IOCSTATUS_SCSI_PROTOCOL_ERROR:
5025 			pkt->pkt_state |= (STATE_GOT_BUS | STATE_GOT_TARGET);
5026 			mptsas_set_pkt_reason(mpt,
5027 			    cmd, CMD_TERMINATED, STAT_TERMINATED);
5028 			break;
5029 		case MPI2_IOCSTATUS_INSUFFICIENT_RESOURCES:
5030 		case MPI2_IOCSTATUS_BUSY:
5031 			/*
5032 			 * set throttles to drain
5033 			 */
5034 			ptgt = (mptsas_target_t *)mptsas_hash_traverse(
5035 			    &mpt->m_active->m_tgttbl, MPTSAS_HASH_FIRST);
5036 			while (ptgt != NULL) {
5037 				mptsas_set_throttle(mpt, ptgt, DRAIN_THROTTLE);
5038 
5039 				ptgt = (mptsas_target_t *)mptsas_hash_traverse(
5040 				    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
5041 			}
5042 
5043 			/*
5044 			 * retry command
5045 			 */
5046 			cmd->cmd_flags |= CFLAG_RETRY;
5047 			cmd->cmd_pkt_flags |= FLAG_HEAD;
5048 
5049 			(void) mptsas_accept_pkt(mpt, cmd);
5050 			break;
5051 		default:
5052 			mptsas_log(mpt, CE_WARN,
5053 			    "unknown ioc_status = %x\n", ioc_status);
5054 			mptsas_log(mpt, CE_CONT, "scsi_state = %x, transfer "
5055 			    "count = %x, scsi_status = %x", scsi_state,
5056 			    xferred, scsi_status);
5057 			break;
5058 		}
5059 		break;
5060 	case MPI2_SCSI_STATUS_TASK_SET_FULL:
5061 		mptsas_handle_qfull(mpt, cmd);
5062 		break;
5063 	case MPI2_SCSI_STATUS_BUSY:
5064 		NDBG31(("scsi_status busy received"));
5065 		break;
5066 	case MPI2_SCSI_STATUS_RESERVATION_CONFLICT:
5067 		NDBG31(("scsi_status reservation conflict received"));
5068 		break;
5069 	default:
5070 		mptsas_log(mpt, CE_WARN, "scsi_status=%x, ioc_status=%x\n",
5071 		    scsi_status, ioc_status);
5072 		mptsas_log(mpt, CE_WARN,
5073 		    "mptsas_process_intr: invalid scsi status\n");
5074 		break;
5075 	}
5076 }
5077 
5078 static void
5079 mptsas_check_task_mgt(mptsas_t *mpt, pMpi2SCSIManagementReply_t reply,
5080 	mptsas_cmd_t *cmd)
5081 {
5082 	uint8_t		task_type;
5083 	uint16_t	ioc_status;
5084 	uint32_t	log_info;
5085 	uint16_t	dev_handle;
5086 	struct scsi_pkt *pkt = CMD2PKT(cmd);
5087 
5088 	task_type = ddi_get8(mpt->m_acc_reply_frame_hdl, &reply->TaskType);
5089 	ioc_status = ddi_get16(mpt->m_acc_reply_frame_hdl, &reply->IOCStatus);
5090 	log_info = ddi_get32(mpt->m_acc_reply_frame_hdl, &reply->IOCLogInfo);
5091 	dev_handle = ddi_get16(mpt->m_acc_reply_frame_hdl, &reply->DevHandle);
5092 
5093 	if (ioc_status != MPI2_IOCSTATUS_SUCCESS) {
5094 		mptsas_log(mpt, CE_WARN, "mptsas_check_task_mgt: Task 0x%x "
5095 		    "failed. IOCStatus=0x%x IOCLogInfo=0x%x target=%d\n",
5096 		    task_type, ioc_status, log_info, dev_handle);
5097 		pkt->pkt_reason = CMD_INCOMPLETE;
5098 		return;
5099 	}
5100 
5101 	switch (task_type) {
5102 	case MPI2_SCSITASKMGMT_TASKTYPE_ABORT_TASK:
5103 	case MPI2_SCSITASKMGMT_TASKTYPE_CLEAR_TASK_SET:
5104 	case MPI2_SCSITASKMGMT_TASKTYPE_QUERY_TASK:
5105 	case MPI2_SCSITASKMGMT_TASKTYPE_CLR_ACA:
5106 	case MPI2_SCSITASKMGMT_TASKTYPE_QRY_TASK_SET:
5107 	case MPI2_SCSITASKMGMT_TASKTYPE_QRY_UNIT_ATTENTION:
5108 		break;
5109 	case MPI2_SCSITASKMGMT_TASKTYPE_ABRT_TASK_SET:
5110 	case MPI2_SCSITASKMGMT_TASKTYPE_LOGICAL_UNIT_RESET:
5111 	case MPI2_SCSITASKMGMT_TASKTYPE_TARGET_RESET:
5112 		mptsas_flush_target(mpt, dev_handle, Lun(cmd), task_type);
5113 		break;
5114 	default:
5115 		mptsas_log(mpt, CE_WARN, "Unknown task management type %d.",
5116 		    task_type);
5117 		mptsas_log(mpt, CE_WARN, "ioc status = %x", ioc_status);
5118 		break;
5119 	}
5120 }
5121 
5122 static void
5123 mptsas_doneq_thread(mptsas_doneq_thread_arg_t *arg)
5124 {
5125 	mptsas_t			*mpt = arg->mpt;
5126 	uint64_t			t = arg->t;
5127 	mptsas_cmd_t			*cmd;
5128 	struct scsi_pkt			*pkt;
5129 	mptsas_doneq_thread_list_t	*item = &mpt->m_doneq_thread_id[t];
5130 
5131 	mutex_enter(&item->mutex);
5132 	while (item->flag & MPTSAS_DONEQ_THREAD_ACTIVE) {
5133 		if (!item->doneq) {
5134 			cv_wait(&item->cv, &item->mutex);
5135 		}
5136 		pkt = NULL;
5137 		if ((cmd = mptsas_doneq_thread_rm(mpt, t)) != NULL) {
5138 			cmd->cmd_flags |= CFLAG_COMPLETED;
5139 			pkt = CMD2PKT(cmd);
5140 		}
5141 		mutex_exit(&item->mutex);
5142 		if (pkt) {
5143 			mptsas_pkt_comp(pkt, cmd);
5144 		}
5145 		mutex_enter(&item->mutex);
5146 	}
5147 	mutex_exit(&item->mutex);
5148 	mutex_enter(&mpt->m_doneq_mutex);
5149 	mpt->m_doneq_thread_n--;
5150 	cv_broadcast(&mpt->m_doneq_thread_cv);
5151 	mutex_exit(&mpt->m_doneq_mutex);
5152 }
5153 
5154 
5155 /*
5156  * mpt interrupt handler.
5157  */
5158 static uint_t
5159 mptsas_intr(caddr_t arg1, caddr_t arg2)
5160 {
5161 	mptsas_t			*mpt = (void *)arg1;
5162 	pMpi2ReplyDescriptorsUnion_t	reply_desc_union;
5163 	uchar_t				did_reply = FALSE;
5164 
5165 	NDBG1(("mptsas_intr: arg1 0x%p arg2 0x%p", (void *)arg1, (void *)arg2));
5166 
5167 	mutex_enter(&mpt->m_mutex);
5168 
5169 	/*
5170 	 * If interrupts are shared by two channels then
5171 	 * check whether this interrupt is genuinely for this
5172 	 * channel by making sure first the chip is in high
5173 	 * power state.
5174 	 */
5175 	if ((mpt->m_options & MPTSAS_OPT_PM) &&
5176 	    (mpt->m_power_level != PM_LEVEL_D0)) {
5177 		mutex_exit(&mpt->m_mutex);
5178 		return (DDI_INTR_UNCLAIMED);
5179 	}
5180 
5181 	/*
5182 	 * If polling, interrupt was triggered by some shared interrupt because
5183 	 * IOC interrupts are disabled during polling, so polling routine will
5184 	 * handle any replies.  Considering this, if polling is happening,
5185 	 * return with interrupt unclaimed.
5186 	 */
5187 	if (mpt->m_polled_intr) {
5188 		mutex_exit(&mpt->m_mutex);
5189 		mptsas_log(mpt, CE_WARN, "mpt_sas: Unclaimed interrupt");
5190 		return (DDI_INTR_UNCLAIMED);
5191 	}
5192 
5193 	/*
5194 	 * Read the istat register.
5195 	 */
5196 	if ((INTPENDING(mpt)) != 0) {
5197 		/*
5198 		 * read fifo until empty.
5199 		 */
5200 #ifndef __lock_lint
5201 		_NOTE(CONSTCOND)
5202 #endif
5203 		while (TRUE) {
5204 			(void) ddi_dma_sync(mpt->m_dma_post_queue_hdl, 0, 0,
5205 			    DDI_DMA_SYNC_FORCPU);
5206 			reply_desc_union = (pMpi2ReplyDescriptorsUnion_t)
5207 			    MPTSAS_GET_NEXT_REPLY(mpt, mpt->m_post_index);
5208 
5209 			if (ddi_get32(mpt->m_acc_post_queue_hdl,
5210 			    &reply_desc_union->Words.Low) == 0xFFFFFFFF ||
5211 			    ddi_get32(mpt->m_acc_post_queue_hdl,
5212 			    &reply_desc_union->Words.High) == 0xFFFFFFFF) {
5213 				break;
5214 			}
5215 
5216 			/*
5217 			 * The reply is valid, process it according to its
5218 			 * type.  Also, set a flag for updated the reply index
5219 			 * after they've all been processed.
5220 			 */
5221 			did_reply = TRUE;
5222 
5223 			mptsas_process_intr(mpt, reply_desc_union);
5224 
5225 			if (++mpt->m_post_index == mpt->m_post_queue_depth) {
5226 				mpt->m_post_index = 0;
5227 			}
5228 		}
5229 
5230 		/*
5231 		 * Update the global reply index if at least one reply was
5232 		 * processed.
5233 		 */
5234 		if (did_reply) {
5235 			ddi_put32(mpt->m_datap,
5236 			    &mpt->m_reg->ReplyPostHostIndex, mpt->m_post_index);
5237 		}
5238 	} else {
5239 		mutex_exit(&mpt->m_mutex);
5240 		return (DDI_INTR_UNCLAIMED);
5241 	}
5242 	NDBG1(("mptsas_intr complete"));
5243 
5244 	/*
5245 	 * If no helper threads are created, process the doneq in ISR.
5246 	 * If helpers are created, use the doneq length as a metric to
5247 	 * measure the load on the interrupt CPU. If it is long enough,
5248 	 * which indicates the load is heavy, then we deliver the IO
5249 	 * completions to the helpers.
5250 	 * this measurement has some limitations although, it is simple
5251 	 * and straightforward and works well for most of the cases at
5252 	 * present.
5253 	 */
5254 
5255 	if (!mpt->m_doneq_thread_n ||
5256 	    (mpt->m_doneq_len <= mpt->m_doneq_length_threshold)) {
5257 		mptsas_doneq_empty(mpt);
5258 	} else {
5259 		mptsas_deliver_doneq_thread(mpt);
5260 	}
5261 
5262 	/*
5263 	 * If there are queued cmd, start them now.
5264 	 */
5265 	if (mpt->m_waitq != NULL) {
5266 		mptsas_restart_waitq(mpt);
5267 	}
5268 
5269 	mutex_exit(&mpt->m_mutex);
5270 	return (DDI_INTR_CLAIMED);
5271 }
5272 
5273 static void
5274 mptsas_process_intr(mptsas_t *mpt,
5275     pMpi2ReplyDescriptorsUnion_t reply_desc_union)
5276 {
5277 	uint8_t	reply_type;
5278 
5279 	ASSERT(mutex_owned(&mpt->m_mutex));
5280 
5281 	/*
5282 	 * The reply is valid, process it according to its
5283 	 * type.  Also, set a flag for updated the reply index
5284 	 * after they've all been processed.
5285 	 */
5286 	reply_type = ddi_get8(mpt->m_acc_post_queue_hdl,
5287 	    &reply_desc_union->Default.ReplyFlags);
5288 	reply_type &= MPI2_RPY_DESCRIPT_FLAGS_TYPE_MASK;
5289 	if (reply_type == MPI2_RPY_DESCRIPT_FLAGS_SCSI_IO_SUCCESS) {
5290 		mptsas_handle_scsi_io_success(mpt, reply_desc_union);
5291 	} else if (reply_type == MPI2_RPY_DESCRIPT_FLAGS_ADDRESS_REPLY) {
5292 		mptsas_handle_address_reply(mpt, reply_desc_union);
5293 	} else {
5294 		mptsas_log(mpt, CE_WARN, "?Bad reply type %x", reply_type);
5295 		ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_UNAFFECTED);
5296 	}
5297 
5298 	/*
5299 	 * Clear the reply descriptor for re-use and increment
5300 	 * index.
5301 	 */
5302 	ddi_put64(mpt->m_acc_post_queue_hdl,
5303 	    &((uint64_t *)(void *)mpt->m_post_queue)[mpt->m_post_index],
5304 	    0xFFFFFFFFFFFFFFFF);
5305 	(void) ddi_dma_sync(mpt->m_dma_post_queue_hdl, 0, 0,
5306 	    DDI_DMA_SYNC_FORDEV);
5307 }
5308 
5309 /*
5310  * handle qfull condition
5311  */
5312 static void
5313 mptsas_handle_qfull(mptsas_t *mpt, mptsas_cmd_t *cmd)
5314 {
5315 	mptsas_target_t	*ptgt = cmd->cmd_tgt_addr;
5316 
5317 	if ((++cmd->cmd_qfull_retries > ptgt->m_qfull_retries) ||
5318 	    (ptgt->m_qfull_retries == 0)) {
5319 		/*
5320 		 * We have exhausted the retries on QFULL, or,
5321 		 * the target driver has indicated that it
5322 		 * wants to handle QFULL itself by setting
5323 		 * qfull-retries capability to 0. In either case
5324 		 * we want the target driver's QFULL handling
5325 		 * to kick in. We do this by having pkt_reason
5326 		 * as CMD_CMPLT and pkt_scbp as STATUS_QFULL.
5327 		 */
5328 		mptsas_set_throttle(mpt, ptgt, DRAIN_THROTTLE);
5329 	} else {
5330 		if (ptgt->m_reset_delay == 0) {
5331 			ptgt->m_t_throttle =
5332 			    max((ptgt->m_t_ncmds - 2), 0);
5333 		}
5334 
5335 		cmd->cmd_pkt_flags |= FLAG_HEAD;
5336 		cmd->cmd_flags &= ~(CFLAG_TRANFLAG);
5337 		cmd->cmd_flags |= CFLAG_RETRY;
5338 
5339 		(void) mptsas_accept_pkt(mpt, cmd);
5340 
5341 		/*
5342 		 * when target gives queue full status with no commands
5343 		 * outstanding (m_t_ncmds == 0), throttle is set to 0
5344 		 * (HOLD_THROTTLE), and the queue full handling start
5345 		 * (see psarc/1994/313); if there are commands outstanding,
5346 		 * throttle is set to (m_t_ncmds - 2)
5347 		 */
5348 		if (ptgt->m_t_throttle == HOLD_THROTTLE) {
5349 			/*
5350 			 * By setting throttle to QFULL_THROTTLE, we
5351 			 * avoid submitting new commands and in
5352 			 * mptsas_restart_cmd find out slots which need
5353 			 * their throttles to be cleared.
5354 			 */
5355 			mptsas_set_throttle(mpt, ptgt, QFULL_THROTTLE);
5356 			if (mpt->m_restart_cmd_timeid == 0) {
5357 				mpt->m_restart_cmd_timeid =
5358 				    timeout(mptsas_restart_cmd, mpt,
5359 				    ptgt->m_qfull_retry_interval);
5360 			}
5361 		}
5362 	}
5363 }
5364 
5365 uint8_t
5366 mptsas_phymask_to_physport(mptsas_t *mpt, uint8_t phymask)
5367 {
5368 	int i;
5369 
5370 	/*
5371 	 * RAID doesn't have valid phymask and physport so we use phymask == 0
5372 	 * and physport == 0xff to indicate that it's RAID.
5373 	 */
5374 	if (phymask == 0) {
5375 		return (0xff);
5376 	}
5377 	for (i = 0; i < 8; i++) {
5378 		if (phymask & (1 << i)) {
5379 			break;
5380 		}
5381 	}
5382 	return (mpt->m_phy_info[i].port_num);
5383 }
5384 uint8_t
5385 mptsas_physport_to_phymask(mptsas_t *mpt, uint8_t physport)
5386 {
5387 	uint8_t		phy_mask = 0;
5388 	uint8_t		i = 0;
5389 
5390 	NDBG20(("mptsas%d physport_to_phymask enter", mpt->m_instance));
5391 
5392 	ASSERT(mutex_owned(&mpt->m_mutex));
5393 
5394 	/*
5395 	 * If physport is 0xFF, this is a RAID volume.  Use phymask of 0.
5396 	 */
5397 	if (physport == 0xFF) {
5398 		return (0);
5399 	}
5400 
5401 	for (i = 0; i < MPTSAS_MAX_PHYS; i++) {
5402 		if (mpt->m_phy_info[i].attached_devhdl &&
5403 		    (mpt->m_phy_info[i].phy_mask != 0) &&
5404 		    (mpt->m_phy_info[i].port_num == physport)) {
5405 			phy_mask = mpt->m_phy_info[i].phy_mask;
5406 			break;
5407 		}
5408 	}
5409 	NDBG20(("mptsas%d physport_to_phymask:physport :%x phymask :%x, ",
5410 	    mpt->m_instance, physport, phy_mask));
5411 	return (phy_mask);
5412 }
5413 
5414 /*
5415  * mpt free device handle after device gone, by use of passthrough
5416  */
5417 static int
5418 mptsas_free_devhdl(mptsas_t *mpt, uint16_t devhdl)
5419 {
5420 	Mpi2SasIoUnitControlRequest_t	req;
5421 	Mpi2SasIoUnitControlReply_t	rep;
5422 	int				ret;
5423 
5424 	ASSERT(mutex_owned(&mpt->m_mutex));
5425 
5426 	/*
5427 	 * Need to compose a SAS IO Unit Control request message
5428 	 * and call mptsas_do_passthru() function
5429 	 */
5430 	bzero(&req, sizeof (req));
5431 	bzero(&rep, sizeof (rep));
5432 
5433 	req.Function = MPI2_FUNCTION_SAS_IO_UNIT_CONTROL;
5434 	req.Operation = MPI2_SAS_OP_REMOVE_DEVICE;
5435 	req.DevHandle = LE_16(devhdl);
5436 
5437 	ret = mptsas_do_passthru(mpt, (uint8_t *)&req, (uint8_t *)&rep, NULL,
5438 	    sizeof (req), sizeof (rep), NULL, 0, NULL, 0, 60, FKIOCTL);
5439 	if (ret != 0) {
5440 		cmn_err(CE_WARN, "mptsas_free_devhdl: passthru SAS IO Unit "
5441 		    "Control error %d", ret);
5442 		return (DDI_FAILURE);
5443 	}
5444 
5445 	/* do passthrough success, check the ioc status */
5446 	if (LE_16(rep.IOCStatus) != MPI2_IOCSTATUS_SUCCESS) {
5447 		cmn_err(CE_WARN, "mptsas_free_devhdl: passthru SAS IO Unit "
5448 		    "Control IOCStatus %d", LE_16(rep.IOCStatus));
5449 		return (DDI_FAILURE);
5450 	}
5451 
5452 	return (DDI_SUCCESS);
5453 }
5454 
5455 static void
5456 mptsas_update_phymask(mptsas_t *mpt)
5457 {
5458 	uint8_t	mask = 0, phy_mask;
5459 	char	*phy_mask_name;
5460 	uint8_t current_port;
5461 	int	i, j;
5462 
5463 	NDBG20(("mptsas%d update phymask ", mpt->m_instance));
5464 
5465 	ASSERT(mutex_owned(&mpt->m_mutex));
5466 
5467 	(void) mptsas_get_sas_io_unit_page(mpt);
5468 
5469 	phy_mask_name = kmem_zalloc(8, KM_SLEEP);
5470 
5471 	for (i = 0; i < mpt->m_num_phys; i++) {
5472 		phy_mask = 0x00;
5473 
5474 		if (mpt->m_phy_info[i].attached_devhdl == 0)
5475 			continue;
5476 
5477 		bzero(phy_mask_name, sizeof (phy_mask_name));
5478 
5479 		current_port = mpt->m_phy_info[i].port_num;
5480 
5481 		if ((mask & (1 << i)) != 0)
5482 			continue;
5483 
5484 		for (j = 0; j < mpt->m_num_phys; j++) {
5485 			if (mpt->m_phy_info[j].attached_devhdl &&
5486 			    (mpt->m_phy_info[j].port_num == current_port)) {
5487 				phy_mask |= (1 << j);
5488 			}
5489 		}
5490 		mask = mask | phy_mask;
5491 
5492 		for (j = 0; j < mpt->m_num_phys; j++) {
5493 			if ((phy_mask >> j) & 0x01) {
5494 				mpt->m_phy_info[j].phy_mask = phy_mask;
5495 			}
5496 		}
5497 
5498 		(void) sprintf(phy_mask_name, "%x", phy_mask);
5499 
5500 		mutex_exit(&mpt->m_mutex);
5501 		/*
5502 		 * register a iport, if the port has already been existed
5503 		 * SCSA will do nothing and just return.
5504 		 */
5505 		(void) scsi_hba_iport_register(mpt->m_dip, phy_mask_name);
5506 		mutex_enter(&mpt->m_mutex);
5507 	}
5508 	kmem_free(phy_mask_name, 8);
5509 	NDBG20(("mptsas%d update phymask return", mpt->m_instance));
5510 }
5511 
5512 /*
5513  * mptsas_handle_dr is a task handler for DR, the DR action includes:
5514  * 1. Directly attched Device Added/Removed.
5515  * 2. Expander Device Added/Removed.
5516  * 3. Indirectly Attached Device Added/Expander.
5517  * 4. LUNs of a existing device status change.
5518  * 5. RAID volume created/deleted.
5519  * 6. Member of RAID volume is released because of RAID deletion.
5520  * 7. Physical disks are removed because of RAID creation.
5521  */
5522 static void
5523 mptsas_handle_dr(void *args) {
5524 	mptsas_topo_change_list_t	*topo_node = NULL;
5525 	mptsas_topo_change_list_t	*save_node = NULL;
5526 	mptsas_t			*mpt;
5527 	dev_info_t			*parent = NULL;
5528 	uint8_t				phymask = 0;
5529 	char				*phy_mask_name;
5530 	uint8_t				flags = 0, physport = 0xff;
5531 	uint8_t				port_update = 0;
5532 	uint_t				event;
5533 
5534 	topo_node = (mptsas_topo_change_list_t *)args;
5535 
5536 	mpt = topo_node->mpt;
5537 	event = topo_node->event;
5538 	flags = topo_node->flags;
5539 
5540 	phy_mask_name = kmem_zalloc(8, KM_SLEEP);
5541 
5542 	NDBG20(("mptsas%d handle_dr enter", mpt->m_instance));
5543 
5544 	switch (event) {
5545 	case MPTSAS_DR_EVENT_RECONFIG_TARGET:
5546 		if ((flags == MPTSAS_TOPO_FLAG_DIRECT_ATTACHED_DEVICE) ||
5547 		    (flags == MPTSAS_TOPO_FLAG_EXPANDER_ATTACHED_DEVICE) ||
5548 		    (flags == MPTSAS_TOPO_FLAG_RAID_PHYSDRV_ASSOCIATED)) {
5549 			/*
5550 			 * Direct attached or expander attached device added
5551 			 * into system or a Phys Disk that is being unhidden.
5552 			 */
5553 			port_update = 1;
5554 		}
5555 		break;
5556 	case MPTSAS_DR_EVENT_RECONFIG_SMP:
5557 		/*
5558 		 * New expander added into system, it must be the head
5559 		 * of topo_change_list_t
5560 		 */
5561 		port_update = 1;
5562 		break;
5563 	default:
5564 		port_update = 0;
5565 		break;
5566 	}
5567 	/*
5568 	 * All cases port_update == 1 may cause initiator port form change
5569 	 */
5570 	mutex_enter(&mpt->m_mutex);
5571 	if (mpt->m_port_chng && port_update) {
5572 		/*
5573 		 * mpt->m_port_chng flag indicates some PHYs of initiator
5574 		 * port have changed to online. So when expander added or
5575 		 * directly attached device online event come, we force to
5576 		 * update port information by issueing SAS IO Unit Page and
5577 		 * update PHYMASKs.
5578 		 */
5579 		(void) mptsas_update_phymask(mpt);
5580 		mpt->m_port_chng = 0;
5581 
5582 	}
5583 	mutex_exit(&mpt->m_mutex);
5584 	while (topo_node) {
5585 		phymask = 0;
5586 		if (parent == NULL) {
5587 			physport = topo_node->un.physport;
5588 			event = topo_node->event;
5589 			flags = topo_node->flags;
5590 			if (event & (MPTSAS_DR_EVENT_OFFLINE_TARGET |
5591 			    MPTSAS_DR_EVENT_OFFLINE_SMP)) {
5592 				/*
5593 				 * For all offline events, phymask is known
5594 				 */
5595 				phymask = topo_node->un.phymask;
5596 				goto find_parent;
5597 			}
5598 			if (event & MPTSAS_TOPO_FLAG_REMOVE_HANDLE) {
5599 				goto handle_topo_change;
5600 			}
5601 			if (flags & MPTSAS_TOPO_FLAG_LUN_ASSOCIATED) {
5602 				phymask = topo_node->un.phymask;
5603 				goto find_parent;
5604 			}
5605 
5606 			if ((flags ==
5607 			    MPTSAS_TOPO_FLAG_RAID_PHYSDRV_ASSOCIATED) &&
5608 			    (event == MPTSAS_DR_EVENT_RECONFIG_TARGET)) {
5609 				/*
5610 				 * There is no any field in IR_CONFIG_CHANGE
5611 				 * event indicate physport/phynum, let's get
5612 				 * parent after SAS Device Page0 request.
5613 				 */
5614 				goto handle_topo_change;
5615 			}
5616 
5617 			mutex_enter(&mpt->m_mutex);
5618 			if (flags == MPTSAS_TOPO_FLAG_DIRECT_ATTACHED_DEVICE) {
5619 				/*
5620 				 * If the direct attached device added or a
5621 				 * phys disk is being unhidden, argument
5622 				 * physport actually is PHY#, so we have to get
5623 				 * phymask according PHY#.
5624 				 */
5625 				physport = mpt->m_phy_info[physport].port_num;
5626 			}
5627 
5628 			/*
5629 			 * Translate physport to phymask so that we can search
5630 			 * parent dip.
5631 			 */
5632 			phymask = mptsas_physport_to_phymask(mpt,
5633 			    physport);
5634 			mutex_exit(&mpt->m_mutex);
5635 
5636 find_parent:
5637 			bzero(phy_mask_name, 8);
5638 			/*
5639 			 * For RAID topology change node, write the iport name
5640 			 * as v0.
5641 			 */
5642 			if (flags & MPTSAS_TOPO_FLAG_RAID_ASSOCIATED) {
5643 				(void) sprintf(phy_mask_name, "v0");
5644 			} else {
5645 				/*
5646 				 * phymask can bo 0 if the drive has been
5647 				 * pulled by the time an add event is
5648 				 * processed.  If phymask is 0, just skip this
5649 				 * event and continue.
5650 				 */
5651 				if (phymask == 0) {
5652 					mutex_enter(&mpt->m_mutex);
5653 					save_node = topo_node;
5654 					topo_node = topo_node->next;
5655 					ASSERT(save_node);
5656 					kmem_free(save_node,
5657 					    sizeof (mptsas_topo_change_list_t));
5658 					mutex_exit(&mpt->m_mutex);
5659 
5660 					parent = NULL;
5661 					continue;
5662 				}
5663 				(void) sprintf(phy_mask_name, "%x", phymask);
5664 			}
5665 			parent = scsi_hba_iport_find(mpt->m_dip,
5666 			    phy_mask_name);
5667 			if (parent == NULL) {
5668 				mptsas_log(mpt, CE_WARN, "Failed to find an "
5669 				    "iport, should not happen!");
5670 				goto out;
5671 			}
5672 
5673 		}
5674 		ASSERT(parent);
5675 handle_topo_change:
5676 
5677 		mutex_enter(&mpt->m_mutex);
5678 
5679 		mptsas_handle_topo_change(topo_node, parent);
5680 		save_node = topo_node;
5681 		topo_node = topo_node->next;
5682 		ASSERT(save_node);
5683 		kmem_free(save_node, sizeof (mptsas_topo_change_list_t));
5684 		mutex_exit(&mpt->m_mutex);
5685 
5686 		if ((flags == MPTSAS_TOPO_FLAG_DIRECT_ATTACHED_DEVICE) ||
5687 		    (flags == MPTSAS_TOPO_FLAG_RAID_PHYSDRV_ASSOCIATED) ||
5688 		    (flags == MPTSAS_TOPO_FLAG_RAID_ASSOCIATED)) {
5689 			/*
5690 			 * If direct attached device associated, make sure
5691 			 * reset the parent before start the next one. But
5692 			 * all devices associated with expander shares the
5693 			 * parent.  Also, reset parent if this is for RAID.
5694 			 */
5695 			parent = NULL;
5696 		}
5697 	}
5698 out:
5699 	kmem_free(phy_mask_name, 8);
5700 }
5701 
5702 static void
5703 mptsas_handle_topo_change(mptsas_topo_change_list_t *topo_node,
5704     dev_info_t *parent)
5705 {
5706 	mptsas_target_t	*ptgt = NULL;
5707 	mptsas_smp_t	*psmp = NULL;
5708 	mptsas_t	*mpt = (void *)topo_node->mpt;
5709 	uint16_t	devhdl;
5710 	uint64_t	sas_wwn = 0;
5711 	int		rval = 0;
5712 	uint32_t	page_address;
5713 	uint8_t		phy, flags;
5714 	char		*addr = NULL;
5715 	dev_info_t	*lundip;
5716 	int		circ = 0, circ1 = 0;
5717 
5718 	NDBG20(("mptsas%d handle_topo_change enter", mpt->m_instance));
5719 
5720 	ASSERT(mutex_owned(&mpt->m_mutex));
5721 
5722 	switch (topo_node->event) {
5723 	case MPTSAS_DR_EVENT_RECONFIG_TARGET:
5724 	{
5725 		char *phy_mask_name;
5726 		uint8_t phymask = 0;
5727 
5728 		if (topo_node->flags == MPTSAS_TOPO_FLAG_RAID_ASSOCIATED) {
5729 			/*
5730 			 * Get latest RAID info.
5731 			 */
5732 			(void) mptsas_get_raid_info(mpt);
5733 			ptgt = mptsas_search_by_devhdl(
5734 			    &mpt->m_active->m_tgttbl, topo_node->devhdl);
5735 			if (ptgt == NULL)
5736 				break;
5737 		} else {
5738 			ptgt = (void *)topo_node->object;
5739 		}
5740 
5741 		if (ptgt == NULL) {
5742 			/*
5743 			 * Get sas device page 0 by DevHandle to make sure if
5744 			 * SSP/SATA end device exist.
5745 			 */
5746 			page_address = (MPI2_SAS_DEVICE_PGAD_FORM_HANDLE &
5747 			    MPI2_SAS_DEVICE_PGAD_FORM_MASK) |
5748 			    topo_node->devhdl;
5749 
5750 			rval = mptsas_get_target_device_info(mpt, page_address,
5751 			    &devhdl, &ptgt);
5752 			if (rval == DEV_INFO_WRONG_DEVICE_TYPE) {
5753 				mptsas_log(mpt, CE_NOTE,
5754 				    "mptsas_handle_topo_change: target %d is "
5755 				    "not a SAS/SATA device. \n",
5756 				    topo_node->devhdl);
5757 			} else if (rval == DEV_INFO_FAIL_ALLOC) {
5758 				mptsas_log(mpt, CE_NOTE,
5759 				    "mptsas_handle_topo_change: could not "
5760 				    "allocate memory. \n");
5761 			}
5762 			/*
5763 			 * If rval is DEV_INFO_PHYS_DISK than there is nothing
5764 			 * else to do, just leave.
5765 			 */
5766 			if (rval != DEV_INFO_SUCCESS) {
5767 				return;
5768 			}
5769 		}
5770 
5771 		ASSERT(ptgt->m_devhdl == topo_node->devhdl);
5772 
5773 		mutex_exit(&mpt->m_mutex);
5774 		flags = topo_node->flags;
5775 
5776 		if (flags == MPTSAS_TOPO_FLAG_RAID_PHYSDRV_ASSOCIATED) {
5777 			phymask = ptgt->m_phymask;
5778 			phy_mask_name = kmem_zalloc(8, KM_SLEEP);
5779 			(void) sprintf(phy_mask_name, "%x", phymask);
5780 			parent = scsi_hba_iport_find(mpt->m_dip,
5781 			    phy_mask_name);
5782 			kmem_free(phy_mask_name, 8);
5783 			if (parent == NULL) {
5784 				mptsas_log(mpt, CE_WARN, "Failed to find a "
5785 				    "iport for PD, should not happen!");
5786 				mutex_enter(&mpt->m_mutex);
5787 				break;
5788 			}
5789 		}
5790 
5791 		if (flags == MPTSAS_TOPO_FLAG_RAID_ASSOCIATED) {
5792 			ndi_devi_enter(parent, &circ1);
5793 			(void) mptsas_config_raid(parent, topo_node->devhdl,
5794 			    &lundip);
5795 			ndi_devi_exit(parent, circ1);
5796 		} else {
5797 			/*
5798 			 * hold nexus for bus configure
5799 			 */
5800 			ndi_devi_enter(scsi_vhci_dip, &circ);
5801 			ndi_devi_enter(parent, &circ1);
5802 			rval = mptsas_config_target(parent, ptgt);
5803 			/*
5804 			 * release nexus for bus configure
5805 			 */
5806 			ndi_devi_exit(parent, circ1);
5807 			ndi_devi_exit(scsi_vhci_dip, circ);
5808 
5809 		}
5810 		mutex_enter(&mpt->m_mutex);
5811 
5812 		NDBG20(("mptsas%d handle_topo_change to online devhdl:%x, "
5813 		    "phymask:%x.", mpt->m_instance, ptgt->m_devhdl,
5814 		    ptgt->m_phymask));
5815 		break;
5816 	}
5817 	case MPTSAS_DR_EVENT_OFFLINE_TARGET:
5818 	{
5819 		mptsas_hash_table_t *tgttbl = &mpt->m_active->m_tgttbl;
5820 		devhdl = topo_node->devhdl;
5821 		ptgt = mptsas_search_by_devhdl(tgttbl, devhdl);
5822 		if (ptgt == NULL)
5823 			break;
5824 
5825 		sas_wwn = ptgt->m_sas_wwn;
5826 		phy = ptgt->m_phynum;
5827 
5828 		addr = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP);
5829 
5830 		if (sas_wwn) {
5831 			(void) sprintf(addr, "w%016"PRIx64, sas_wwn);
5832 		} else {
5833 			(void) sprintf(addr, "p%x", phy);
5834 		}
5835 		ASSERT(ptgt->m_devhdl == devhdl);
5836 
5837 		if (topo_node->flags == MPTSAS_TOPO_FLAG_RAID_ASSOCIATED) {
5838 			/*
5839 			 * Get latest RAID info, if RAID volume status change
5840 			 */
5841 			(void) mptsas_get_raid_info(mpt);
5842 		}
5843 		/*
5844 		 * Abort all outstanding command on the device
5845 		 */
5846 		rval = mptsas_do_scsi_reset(mpt, devhdl);
5847 		if (rval) {
5848 			NDBG20(("mptsas%d handle_topo_change to reset target "
5849 			    "before offline devhdl:%x, phymask:%x, rval:%x",
5850 			    mpt->m_instance, ptgt->m_devhdl, ptgt->m_phymask,
5851 			    rval));
5852 		}
5853 
5854 		mutex_exit(&mpt->m_mutex);
5855 
5856 		ndi_devi_enter(scsi_vhci_dip, &circ);
5857 		ndi_devi_enter(parent, &circ1);
5858 		rval = mptsas_offline_target(parent, addr);
5859 		ndi_devi_exit(parent, circ1);
5860 		ndi_devi_exit(scsi_vhci_dip, circ);
5861 		NDBG20(("mptsas%d handle_topo_change to offline devhdl:%x, "
5862 		    "phymask:%x, rval:%x", mpt->m_instance,
5863 		    ptgt->m_devhdl, ptgt->m_phymask, rval));
5864 
5865 		kmem_free(addr, SCSI_MAXNAMELEN);
5866 
5867 		mutex_enter(&mpt->m_mutex);
5868 		if (rval == DDI_SUCCESS) {
5869 			mptsas_tgt_free(&mpt->m_active->m_tgttbl,
5870 			    ptgt->m_sas_wwn, ptgt->m_phymask);
5871 			ptgt = NULL;
5872 		} else {
5873 			/*
5874 			 * clean DR_INTRANSITION flag to allow I/O down to
5875 			 * PHCI driver since failover finished.
5876 			 * Invalidate the devhdl
5877 			 */
5878 			ptgt->m_devhdl = MPTSAS_INVALID_DEVHDL;
5879 			mutex_enter(&mpt->m_tx_waitq_mutex);
5880 			ptgt->m_dr_flag = MPTSAS_DR_INACTIVE;
5881 			mutex_exit(&mpt->m_tx_waitq_mutex);
5882 		}
5883 
5884 		/*
5885 		 * Send SAS IO Unit Control to free the dev handle
5886 		 */
5887 		flags = topo_node->flags;
5888 		if ((flags == MPTSAS_TOPO_FLAG_DIRECT_ATTACHED_DEVICE) ||
5889 		    (flags == MPTSAS_TOPO_FLAG_EXPANDER_ATTACHED_DEVICE)) {
5890 			rval = mptsas_free_devhdl(mpt, devhdl);
5891 
5892 			NDBG20(("mptsas%d handle_topo_change to remove "
5893 			    "devhdl:%x, rval:%x", mpt->m_instance, devhdl,
5894 			    rval));
5895 		}
5896 		break;
5897 	}
5898 	case MPTSAS_TOPO_FLAG_REMOVE_HANDLE:
5899 	{
5900 		devhdl = topo_node->devhdl;
5901 		/*
5902 		 * If this is the remove handle event, do a reset first.
5903 		 */
5904 		if (topo_node->event == MPTSAS_TOPO_FLAG_REMOVE_HANDLE) {
5905 			rval = mptsas_do_scsi_reset(mpt, devhdl);
5906 			if (rval) {
5907 				NDBG20(("mpt%d reset target before remove "
5908 				    "devhdl:%x, rval:%x", mpt->m_instance,
5909 				    devhdl, rval));
5910 			}
5911 		}
5912 
5913 		/*
5914 		 * Send SAS IO Unit Control to free the dev handle
5915 		 */
5916 		rval = mptsas_free_devhdl(mpt, devhdl);
5917 		NDBG20(("mptsas%d handle_topo_change to remove "
5918 		    "devhdl:%x, rval:%x", mpt->m_instance, devhdl,
5919 		    rval));
5920 		break;
5921 	}
5922 	case MPTSAS_DR_EVENT_RECONFIG_SMP:
5923 	{
5924 		mptsas_smp_t smp;
5925 		dev_info_t *smpdip;
5926 		mptsas_hash_table_t *smptbl = &mpt->m_active->m_smptbl;
5927 
5928 		devhdl = topo_node->devhdl;
5929 
5930 		page_address = (MPI2_SAS_EXPAND_PGAD_FORM_HNDL &
5931 		    MPI2_SAS_EXPAND_PGAD_FORM_MASK) | (uint32_t)devhdl;
5932 		rval = mptsas_get_sas_expander_page0(mpt, page_address, &smp);
5933 		if (rval != DDI_SUCCESS) {
5934 			mptsas_log(mpt, CE_WARN, "failed to online smp, "
5935 			    "handle %x", devhdl);
5936 			return;
5937 		}
5938 
5939 		psmp = mptsas_smp_alloc(smptbl, &smp);
5940 		if (psmp == NULL) {
5941 			return;
5942 		}
5943 
5944 		mutex_exit(&mpt->m_mutex);
5945 		ndi_devi_enter(parent, &circ1);
5946 		(void) mptsas_online_smp(parent, psmp, &smpdip);
5947 		ndi_devi_exit(parent, circ1);
5948 		mutex_enter(&mpt->m_mutex);
5949 		break;
5950 	}
5951 	case MPTSAS_DR_EVENT_OFFLINE_SMP:
5952 	{
5953 		mptsas_hash_table_t *smptbl = &mpt->m_active->m_smptbl;
5954 		devhdl = topo_node->devhdl;
5955 		psmp = mptsas_search_by_devhdl(smptbl, devhdl);
5956 		if (psmp == NULL)
5957 			break;
5958 		/*
5959 		 * The mptsas_smp_t data is released only if the dip is offlined
5960 		 * successfully.
5961 		 */
5962 		mutex_exit(&mpt->m_mutex);
5963 		ndi_devi_enter(parent, &circ1);
5964 		rval = mptsas_offline_smp(parent, psmp, NDI_DEVI_REMOVE);
5965 		ndi_devi_exit(parent, circ1);
5966 		mutex_enter(&mpt->m_mutex);
5967 		NDBG20(("mptsas%d handle_topo_change to remove devhdl:%x, "
5968 		    "rval:%x", mpt->m_instance, psmp->m_devhdl, rval));
5969 		if (rval == DDI_SUCCESS) {
5970 			mptsas_smp_free(smptbl, psmp->m_sasaddr,
5971 			    psmp->m_phymask);
5972 		} else {
5973 			psmp->m_devhdl = MPTSAS_INVALID_DEVHDL;
5974 		}
5975 		break;
5976 	}
5977 	default:
5978 		return;
5979 	}
5980 }
5981 
5982 /*
5983  * Record the event if its type is enabled in mpt instance by ioctl.
5984  */
5985 static void
5986 mptsas_record_event(void *args)
5987 {
5988 	m_replyh_arg_t			*replyh_arg;
5989 	pMpi2EventNotificationReply_t	eventreply;
5990 	uint32_t			event, rfm;
5991 	mptsas_t			*mpt;
5992 	int				i, j;
5993 	uint16_t			event_data_len;
5994 	boolean_t			sendAEN = FALSE;
5995 
5996 	replyh_arg = (m_replyh_arg_t *)args;
5997 	rfm = replyh_arg->rfm;
5998 	mpt = replyh_arg->mpt;
5999 
6000 	eventreply = (pMpi2EventNotificationReply_t)
6001 	    (mpt->m_reply_frame + (rfm - mpt->m_reply_frame_dma_addr));
6002 	event = ddi_get16(mpt->m_acc_reply_frame_hdl, &eventreply->Event);
6003 
6004 
6005 	/*
6006 	 * Generate a system event to let anyone who cares know that a
6007 	 * LOG_ENTRY_ADDED event has occurred.  This is sent no matter what the
6008 	 * event mask is set to.
6009 	 */
6010 	if (event == MPI2_EVENT_LOG_ENTRY_ADDED) {
6011 		sendAEN = TRUE;
6012 	}
6013 
6014 	/*
6015 	 * Record the event only if it is not masked.  Determine which dword
6016 	 * and bit of event mask to test.
6017 	 */
6018 	i = (uint8_t)(event / 32);
6019 	j = (uint8_t)(event % 32);
6020 	if ((i < 4) && ((1 << j) & mpt->m_event_mask[i])) {
6021 		i = mpt->m_event_index;
6022 		mpt->m_events[i].Type = event;
6023 		mpt->m_events[i].Number = ++mpt->m_event_number;
6024 		bzero(mpt->m_events[i].Data, MPTSAS_MAX_EVENT_DATA_LENGTH * 4);
6025 		event_data_len = ddi_get16(mpt->m_acc_reply_frame_hdl,
6026 		    &eventreply->EventDataLength);
6027 
6028 		if (event_data_len > 0) {
6029 			/*
6030 			 * Limit data to size in m_event entry
6031 			 */
6032 			if (event_data_len > MPTSAS_MAX_EVENT_DATA_LENGTH) {
6033 				event_data_len = MPTSAS_MAX_EVENT_DATA_LENGTH;
6034 			}
6035 			for (j = 0; j < event_data_len; j++) {
6036 				mpt->m_events[i].Data[j] =
6037 				    ddi_get32(mpt->m_acc_reply_frame_hdl,
6038 				    &(eventreply->EventData[j]));
6039 			}
6040 
6041 			/*
6042 			 * check for index wrap-around
6043 			 */
6044 			if (++i == MPTSAS_EVENT_QUEUE_SIZE) {
6045 				i = 0;
6046 			}
6047 			mpt->m_event_index = (uint8_t)i;
6048 
6049 			/*
6050 			 * Set flag to send the event.
6051 			 */
6052 			sendAEN = TRUE;
6053 		}
6054 	}
6055 
6056 	/*
6057 	 * Generate a system event if flag is set to let anyone who cares know
6058 	 * that an event has occurred.
6059 	 */
6060 	if (sendAEN) {
6061 		(void) ddi_log_sysevent(mpt->m_dip, DDI_VENDOR_LSI, "MPT_SAS",
6062 		    "SAS", NULL, NULL, DDI_NOSLEEP);
6063 	}
6064 }
6065 
6066 #define	SMP_RESET_IN_PROGRESS MPI2_EVENT_SAS_TOPO_LR_SMP_RESET_IN_PROGRESS
6067 /*
6068  * handle sync events from ioc in interrupt
6069  * return value:
6070  * DDI_SUCCESS: The event is handled by this func
6071  * DDI_FAILURE: Event is not handled
6072  */
6073 static int
6074 mptsas_handle_event_sync(void *args)
6075 {
6076 	m_replyh_arg_t			*replyh_arg;
6077 	pMpi2EventNotificationReply_t	eventreply;
6078 	uint32_t			event, rfm;
6079 	mptsas_t			*mpt;
6080 	uint_t				iocstatus;
6081 
6082 	replyh_arg = (m_replyh_arg_t *)args;
6083 	rfm = replyh_arg->rfm;
6084 	mpt = replyh_arg->mpt;
6085 
6086 	ASSERT(mutex_owned(&mpt->m_mutex));
6087 
6088 	eventreply = (pMpi2EventNotificationReply_t)
6089 	    (mpt->m_reply_frame + (rfm - mpt->m_reply_frame_dma_addr));
6090 	event = ddi_get16(mpt->m_acc_reply_frame_hdl, &eventreply->Event);
6091 
6092 	if (iocstatus = ddi_get16(mpt->m_acc_reply_frame_hdl,
6093 	    &eventreply->IOCStatus)) {
6094 		if (iocstatus == MPI2_IOCSTATUS_FLAG_LOG_INFO_AVAILABLE) {
6095 			mptsas_log(mpt, CE_WARN,
6096 			    "!mptsas_handle_event_sync: IOCStatus=0x%x, "
6097 			    "IOCLogInfo=0x%x", iocstatus,
6098 			    ddi_get32(mpt->m_acc_reply_frame_hdl,
6099 			    &eventreply->IOCLogInfo));
6100 		} else {
6101 			mptsas_log(mpt, CE_WARN,
6102 			    "mptsas_handle_event_sync: IOCStatus=0x%x, "
6103 			    "IOCLogInfo=0x%x", iocstatus,
6104 			    ddi_get32(mpt->m_acc_reply_frame_hdl,
6105 			    &eventreply->IOCLogInfo));
6106 		}
6107 	}
6108 
6109 	/*
6110 	 * figure out what kind of event we got and handle accordingly
6111 	 */
6112 	switch (event) {
6113 	case MPI2_EVENT_SAS_TOPOLOGY_CHANGE_LIST:
6114 	{
6115 		pMpi2EventDataSasTopologyChangeList_t	sas_topo_change_list;
6116 		uint8_t				num_entries, expstatus, phy;
6117 		uint8_t				phystatus, physport, state, i;
6118 		uint8_t				start_phy_num, link_rate;
6119 		uint16_t			dev_handle;
6120 		uint16_t			enc_handle, expd_handle;
6121 		char				string[80], curr[80], prev[80];
6122 		mptsas_topo_change_list_t	*topo_head = NULL;
6123 		mptsas_topo_change_list_t	*topo_tail = NULL;
6124 		mptsas_topo_change_list_t	*topo_node = NULL;
6125 		mptsas_target_t			*ptgt;
6126 		mptsas_smp_t			*psmp;
6127 		mptsas_hash_table_t		*tgttbl, *smptbl;
6128 		uint8_t				flags = 0, exp_flag;
6129 
6130 		NDBG20(("mptsas_handle_event_sync: SAS topology change"));
6131 
6132 		tgttbl = &mpt->m_active->m_tgttbl;
6133 		smptbl = &mpt->m_active->m_smptbl;
6134 
6135 		sas_topo_change_list = (pMpi2EventDataSasTopologyChangeList_t)
6136 		    eventreply->EventData;
6137 
6138 		enc_handle = ddi_get16(mpt->m_acc_reply_frame_hdl,
6139 		    &sas_topo_change_list->EnclosureHandle);
6140 		expd_handle = ddi_get16(mpt->m_acc_reply_frame_hdl,
6141 		    &sas_topo_change_list->ExpanderDevHandle);
6142 		num_entries = ddi_get8(mpt->m_acc_reply_frame_hdl,
6143 		    &sas_topo_change_list->NumEntries);
6144 		start_phy_num = ddi_get8(mpt->m_acc_reply_frame_hdl,
6145 		    &sas_topo_change_list->StartPhyNum);
6146 		expstatus = ddi_get8(mpt->m_acc_reply_frame_hdl,
6147 		    &sas_topo_change_list->ExpStatus);
6148 		physport = ddi_get8(mpt->m_acc_reply_frame_hdl,
6149 		    &sas_topo_change_list->PhysicalPort);
6150 
6151 		string[0] = 0;
6152 		if (expd_handle) {
6153 			flags = MPTSAS_TOPO_FLAG_EXPANDER_ASSOCIATED;
6154 			switch (expstatus) {
6155 			case MPI2_EVENT_SAS_TOPO_ES_ADDED:
6156 				(void) sprintf(string, " added");
6157 				/*
6158 				 * New expander device added
6159 				 */
6160 				mpt->m_port_chng = 1;
6161 				topo_node = kmem_zalloc(
6162 				    sizeof (mptsas_topo_change_list_t),
6163 				    KM_SLEEP);
6164 				topo_node->mpt = mpt;
6165 				topo_node->event = MPTSAS_DR_EVENT_RECONFIG_SMP;
6166 				topo_node->un.physport = physport;
6167 				topo_node->devhdl = expd_handle;
6168 				topo_node->flags = flags;
6169 				topo_node->object = NULL;
6170 				if (topo_head == NULL) {
6171 					topo_head = topo_tail = topo_node;
6172 				} else {
6173 					topo_tail->next = topo_node;
6174 					topo_tail = topo_node;
6175 				}
6176 				break;
6177 			case MPI2_EVENT_SAS_TOPO_ES_NOT_RESPONDING:
6178 				(void) sprintf(string, " not responding, "
6179 				    "removed");
6180 				psmp = mptsas_search_by_devhdl(smptbl,
6181 				    expd_handle);
6182 				if (psmp == NULL)
6183 					break;
6184 
6185 				topo_node = kmem_zalloc(
6186 				    sizeof (mptsas_topo_change_list_t),
6187 				    KM_SLEEP);
6188 				topo_node->mpt = mpt;
6189 				topo_node->un.phymask = psmp->m_phymask;
6190 				topo_node->event = MPTSAS_DR_EVENT_OFFLINE_SMP;
6191 				topo_node->devhdl = expd_handle;
6192 				topo_node->flags = flags;
6193 				topo_node->object = NULL;
6194 				if (topo_head == NULL) {
6195 					topo_head = topo_tail = topo_node;
6196 				} else {
6197 					topo_tail->next = topo_node;
6198 					topo_tail = topo_node;
6199 				}
6200 				break;
6201 			case MPI2_EVENT_SAS_TOPO_ES_RESPONDING:
6202 				break;
6203 			case MPI2_EVENT_SAS_TOPO_ES_DELAY_NOT_RESPONDING:
6204 				(void) sprintf(string, " not responding, "
6205 				    "delaying removal");
6206 				break;
6207 			default:
6208 				break;
6209 			}
6210 		} else {
6211 			flags = MPTSAS_TOPO_FLAG_DIRECT_ATTACHED_DEVICE;
6212 		}
6213 
6214 		NDBG20(("SAS TOPOLOGY CHANGE for enclosure %x expander %x%s\n",
6215 		    enc_handle, expd_handle, string));
6216 		for (i = 0; i < num_entries; i++) {
6217 			phy = i + start_phy_num;
6218 			phystatus = ddi_get8(mpt->m_acc_reply_frame_hdl,
6219 			    &sas_topo_change_list->PHY[i].PhyStatus);
6220 			dev_handle = ddi_get16(mpt->m_acc_reply_frame_hdl,
6221 			    &sas_topo_change_list->PHY[i].AttachedDevHandle);
6222 			if (phystatus & MPI2_EVENT_SAS_TOPO_PHYSTATUS_VACANT) {
6223 				continue;
6224 			}
6225 			curr[0] = 0;
6226 			prev[0] = 0;
6227 			string[0] = 0;
6228 			switch (phystatus & MPI2_EVENT_SAS_TOPO_RC_MASK) {
6229 			case MPI2_EVENT_SAS_TOPO_RC_TARG_ADDED:
6230 			{
6231 				NDBG20(("mptsas%d phy %d physical_port %d "
6232 				    "dev_handle %d added", mpt->m_instance, phy,
6233 				    physport, dev_handle));
6234 				link_rate = ddi_get8(mpt->m_acc_reply_frame_hdl,
6235 				    &sas_topo_change_list->PHY[i].LinkRate);
6236 				state = (link_rate &
6237 				    MPI2_EVENT_SAS_TOPO_LR_CURRENT_MASK) >>
6238 				    MPI2_EVENT_SAS_TOPO_LR_CURRENT_SHIFT;
6239 				switch (state) {
6240 				case MPI2_EVENT_SAS_TOPO_LR_PHY_DISABLED:
6241 					(void) sprintf(curr, "is disabled");
6242 					break;
6243 				case MPI2_EVENT_SAS_TOPO_LR_NEGOTIATION_FAILED:
6244 					(void) sprintf(curr, "is offline, "
6245 					    "failed speed negotiation");
6246 					break;
6247 				case MPI2_EVENT_SAS_TOPO_LR_SATA_OOB_COMPLETE:
6248 					(void) sprintf(curr, "SATA OOB "
6249 					    "complete");
6250 					break;
6251 				case SMP_RESET_IN_PROGRESS:
6252 					(void) sprintf(curr, "SMP reset in "
6253 					    "progress");
6254 					break;
6255 				case MPI2_EVENT_SAS_TOPO_LR_RATE_1_5:
6256 					(void) sprintf(curr, "is online at "
6257 					    "1.5 Gbps");
6258 					break;
6259 				case MPI2_EVENT_SAS_TOPO_LR_RATE_3_0:
6260 					(void) sprintf(curr, "is online at 3.0 "
6261 					    "Gbps");
6262 					break;
6263 				case MPI2_EVENT_SAS_TOPO_LR_RATE_6_0:
6264 					(void) sprintf(curr, "is online at 6.0 "
6265 					    "Gbps");
6266 					break;
6267 				default:
6268 					(void) sprintf(curr, "state is "
6269 					    "unknown");
6270 					break;
6271 				}
6272 				/*
6273 				 * New target device added into the system.
6274 				 * Set association flag according to if an
6275 				 * expander is used or not.
6276 				 */
6277 				exp_flag =
6278 				    MPTSAS_TOPO_FLAG_EXPANDER_ATTACHED_DEVICE;
6279 				if (flags ==
6280 				    MPTSAS_TOPO_FLAG_EXPANDER_ASSOCIATED) {
6281 					flags = exp_flag;
6282 				}
6283 				topo_node = kmem_zalloc(
6284 				    sizeof (mptsas_topo_change_list_t),
6285 				    KM_SLEEP);
6286 				topo_node->mpt = mpt;
6287 				topo_node->event =
6288 				    MPTSAS_DR_EVENT_RECONFIG_TARGET;
6289 				if (expd_handle == 0) {
6290 					/*
6291 					 * Per MPI 2, if expander dev handle
6292 					 * is 0, it's a directly attached
6293 					 * device. So driver use PHY to decide
6294 					 * which iport is associated
6295 					 */
6296 					physport = phy;
6297 					mpt->m_port_chng = 1;
6298 				}
6299 				topo_node->un.physport = physport;
6300 				topo_node->devhdl = dev_handle;
6301 				topo_node->flags = flags;
6302 				topo_node->object = NULL;
6303 				if (topo_head == NULL) {
6304 					topo_head = topo_tail = topo_node;
6305 				} else {
6306 					topo_tail->next = topo_node;
6307 					topo_tail = topo_node;
6308 				}
6309 				break;
6310 			}
6311 			case MPI2_EVENT_SAS_TOPO_RC_TARG_NOT_RESPONDING:
6312 			{
6313 				NDBG20(("mptsas%d phy %d physical_port %d "
6314 				    "dev_handle %d removed", mpt->m_instance,
6315 				    phy, physport, dev_handle));
6316 				/*
6317 				 * Set association flag according to if an
6318 				 * expander is used or not.
6319 				 */
6320 				exp_flag =
6321 				    MPTSAS_TOPO_FLAG_EXPANDER_ATTACHED_DEVICE;
6322 				if (flags ==
6323 				    MPTSAS_TOPO_FLAG_EXPANDER_ASSOCIATED) {
6324 					flags = exp_flag;
6325 				}
6326 				/*
6327 				 * Target device is removed from the system
6328 				 * Before the device is really offline from
6329 				 * from system.
6330 				 */
6331 				ptgt = mptsas_search_by_devhdl(tgttbl,
6332 				    dev_handle);
6333 				/*
6334 				 * If ptgt is NULL here, it means that the
6335 				 * DevHandle is not in the hash table.  This is
6336 				 * reasonable sometimes.  For example, if a
6337 				 * disk was pulled, then added, then pulled
6338 				 * again, the disk will not have been put into
6339 				 * the hash table because the add event will
6340 				 * have an invalid phymask.  BUT, this does not
6341 				 * mean that the DevHandle is invalid.  The
6342 				 * controller will still have a valid DevHandle
6343 				 * that must be removed.  To do this, use the
6344 				 * MPTSAS_TOPO_FLAG_REMOVE_HANDLE event.
6345 				 */
6346 				if (ptgt == NULL) {
6347 					topo_node = kmem_zalloc(
6348 					    sizeof (mptsas_topo_change_list_t),
6349 					    KM_SLEEP);
6350 					topo_node->mpt = mpt;
6351 					topo_node->un.phymask = 0;
6352 					topo_node->event =
6353 					    MPTSAS_TOPO_FLAG_REMOVE_HANDLE;
6354 					topo_node->devhdl = dev_handle;
6355 					topo_node->flags = flags;
6356 					topo_node->object = NULL;
6357 					if (topo_head == NULL) {
6358 						topo_head = topo_tail =
6359 						    topo_node;
6360 					} else {
6361 						topo_tail->next = topo_node;
6362 						topo_tail = topo_node;
6363 					}
6364 					break;
6365 				}
6366 
6367 				/*
6368 				 * Update DR flag immediately avoid I/O failure
6369 				 * before failover finish. Pay attention to the
6370 				 * mutex protect, we need grab m_tx_waitq_mutex
6371 				 * during set m_dr_flag because we won't add
6372 				 * the following command into waitq, instead,
6373 				 * we need return TRAN_BUSY in the tran_start
6374 				 * context.
6375 				 */
6376 				mutex_enter(&mpt->m_tx_waitq_mutex);
6377 				ptgt->m_dr_flag = MPTSAS_DR_INTRANSITION;
6378 				mutex_exit(&mpt->m_tx_waitq_mutex);
6379 
6380 				topo_node = kmem_zalloc(
6381 				    sizeof (mptsas_topo_change_list_t),
6382 				    KM_SLEEP);
6383 				topo_node->mpt = mpt;
6384 				topo_node->un.phymask = ptgt->m_phymask;
6385 				topo_node->event =
6386 				    MPTSAS_DR_EVENT_OFFLINE_TARGET;
6387 				topo_node->devhdl = dev_handle;
6388 				topo_node->flags = flags;
6389 				topo_node->object = NULL;
6390 				if (topo_head == NULL) {
6391 					topo_head = topo_tail = topo_node;
6392 				} else {
6393 					topo_tail->next = topo_node;
6394 					topo_tail = topo_node;
6395 				}
6396 
6397 				break;
6398 			}
6399 			case MPI2_EVENT_SAS_TOPO_RC_PHY_CHANGED:
6400 				link_rate = ddi_get8(mpt->m_acc_reply_frame_hdl,
6401 				    &sas_topo_change_list->PHY[i].LinkRate);
6402 				state = (link_rate &
6403 				    MPI2_EVENT_SAS_TOPO_LR_CURRENT_MASK) >>
6404 				    MPI2_EVENT_SAS_TOPO_LR_CURRENT_SHIFT;
6405 				switch (state) {
6406 				case MPI2_EVENT_SAS_TOPO_LR_PHY_DISABLED:
6407 					(void) sprintf(curr, "is disabled");
6408 					break;
6409 				case MPI2_EVENT_SAS_TOPO_LR_NEGOTIATION_FAILED:
6410 					(void) sprintf(curr, "is offline, "
6411 					    "failed speed negotiation");
6412 					break;
6413 				case MPI2_EVENT_SAS_TOPO_LR_SATA_OOB_COMPLETE:
6414 					(void) sprintf(curr, "SATA OOB "
6415 					    "complete");
6416 					break;
6417 				case SMP_RESET_IN_PROGRESS:
6418 					(void) sprintf(curr, "SMP reset in "
6419 					    "progress");
6420 					break;
6421 				case MPI2_EVENT_SAS_TOPO_LR_RATE_1_5:
6422 					(void) sprintf(curr, "is online at "
6423 					    "1.5 Gbps");
6424 					if ((expd_handle == 0) &&
6425 					    (enc_handle == 1)) {
6426 						mpt->m_port_chng = 1;
6427 					}
6428 					break;
6429 				case MPI2_EVENT_SAS_TOPO_LR_RATE_3_0:
6430 					(void) sprintf(curr, "is online at 3.0 "
6431 					    "Gbps");
6432 					if ((expd_handle == 0) &&
6433 					    (enc_handle == 1)) {
6434 						mpt->m_port_chng = 1;
6435 					}
6436 					break;
6437 				case MPI2_EVENT_SAS_TOPO_LR_RATE_6_0:
6438 					(void) sprintf(curr, "is online at "
6439 					    "6.0 Gbps");
6440 					if ((expd_handle == 0) &&
6441 					    (enc_handle == 1)) {
6442 						mpt->m_port_chng = 1;
6443 					}
6444 					break;
6445 				default:
6446 					(void) sprintf(curr, "state is "
6447 					    "unknown");
6448 					break;
6449 				}
6450 
6451 				state = (link_rate &
6452 				    MPI2_EVENT_SAS_TOPO_LR_PREV_MASK) >>
6453 				    MPI2_EVENT_SAS_TOPO_LR_PREV_SHIFT;
6454 				switch (state) {
6455 				case MPI2_EVENT_SAS_TOPO_LR_PHY_DISABLED:
6456 					(void) sprintf(prev, ", was disabled");
6457 					break;
6458 				case MPI2_EVENT_SAS_TOPO_LR_NEGOTIATION_FAILED:
6459 					(void) sprintf(prev, ", was offline, "
6460 					    "failed speed negotiation");
6461 					break;
6462 				case MPI2_EVENT_SAS_TOPO_LR_SATA_OOB_COMPLETE:
6463 					(void) sprintf(prev, ", was SATA OOB "
6464 					    "complete");
6465 					break;
6466 				case SMP_RESET_IN_PROGRESS:
6467 					(void) sprintf(prev, ", was SMP reset "
6468 					    "in progress");
6469 					break;
6470 				case MPI2_EVENT_SAS_TOPO_LR_RATE_1_5:
6471 					(void) sprintf(prev, ", was online at "
6472 					    "1.5 Gbps");
6473 					break;
6474 				case MPI2_EVENT_SAS_TOPO_LR_RATE_3_0:
6475 					(void) sprintf(prev, ", was online at "
6476 					    "3.0 Gbps");
6477 					break;
6478 				case MPI2_EVENT_SAS_TOPO_LR_RATE_6_0:
6479 					(void) sprintf(prev, ", was online at "
6480 					    "6.0 Gbps");
6481 					break;
6482 				default:
6483 				break;
6484 				}
6485 				(void) sprintf(&string[strlen(string)], "link "
6486 				    "changed, ");
6487 				break;
6488 			case MPI2_EVENT_SAS_TOPO_RC_NO_CHANGE:
6489 				continue;
6490 			case MPI2_EVENT_SAS_TOPO_RC_DELAY_NOT_RESPONDING:
6491 				(void) sprintf(&string[strlen(string)],
6492 				    "target not responding, delaying "
6493 				    "removal");
6494 				break;
6495 			}
6496 			NDBG20(("mptsas%d phy %d DevHandle %x, %s%s%s\n",
6497 			    mpt->m_instance, phy, dev_handle, string, curr,
6498 			    prev));
6499 		}
6500 		if (topo_head != NULL) {
6501 			/*
6502 			 * Launch DR taskq to handle topology change
6503 			 */
6504 			if ((ddi_taskq_dispatch(mpt->m_dr_taskq,
6505 			    mptsas_handle_dr, (void *)topo_head,
6506 			    DDI_NOSLEEP)) != DDI_SUCCESS) {
6507 				mptsas_log(mpt, CE_NOTE, "mptsas start taskq "
6508 				    "for handle SAS DR event failed. \n");
6509 			}
6510 		}
6511 		break;
6512 	}
6513 	case MPI2_EVENT_IR_CONFIGURATION_CHANGE_LIST:
6514 	{
6515 		Mpi2EventDataIrConfigChangeList_t	*irChangeList;
6516 		mptsas_topo_change_list_t		*topo_head = NULL;
6517 		mptsas_topo_change_list_t		*topo_tail = NULL;
6518 		mptsas_topo_change_list_t		*topo_node = NULL;
6519 		mptsas_target_t				*ptgt;
6520 		mptsas_hash_table_t			*tgttbl;
6521 		uint8_t					num_entries, i, reason;
6522 		uint16_t				volhandle, diskhandle;
6523 
6524 		irChangeList = (pMpi2EventDataIrConfigChangeList_t)
6525 		    eventreply->EventData;
6526 		num_entries = ddi_get8(mpt->m_acc_reply_frame_hdl,
6527 		    &irChangeList->NumElements);
6528 
6529 		tgttbl = &mpt->m_active->m_tgttbl;
6530 
6531 		NDBG20(("mptsas%d IR_CONFIGURATION_CHANGE_LIST event received",
6532 		    mpt->m_instance));
6533 
6534 		for (i = 0; i < num_entries; i++) {
6535 			reason = ddi_get8(mpt->m_acc_reply_frame_hdl,
6536 			    &irChangeList->ConfigElement[i].ReasonCode);
6537 			volhandle = ddi_get16(mpt->m_acc_reply_frame_hdl,
6538 			    &irChangeList->ConfigElement[i].VolDevHandle);
6539 			diskhandle = ddi_get16(mpt->m_acc_reply_frame_hdl,
6540 			    &irChangeList->ConfigElement[i].PhysDiskDevHandle);
6541 
6542 			switch (reason) {
6543 			case MPI2_EVENT_IR_CHANGE_RC_ADDED:
6544 			case MPI2_EVENT_IR_CHANGE_RC_VOLUME_CREATED:
6545 			{
6546 				NDBG20(("mptsas %d volume added\n",
6547 				    mpt->m_instance));
6548 
6549 				topo_node = kmem_zalloc(
6550 				    sizeof (mptsas_topo_change_list_t),
6551 				    KM_SLEEP);
6552 
6553 				topo_node->mpt = mpt;
6554 				topo_node->event =
6555 				    MPTSAS_DR_EVENT_RECONFIG_TARGET;
6556 				topo_node->un.physport = 0xff;
6557 				topo_node->devhdl = volhandle;
6558 				topo_node->flags =
6559 				    MPTSAS_TOPO_FLAG_RAID_ASSOCIATED;
6560 				topo_node->object = NULL;
6561 				if (topo_head == NULL) {
6562 					topo_head = topo_tail = topo_node;
6563 				} else {
6564 					topo_tail->next = topo_node;
6565 					topo_tail = topo_node;
6566 				}
6567 				break;
6568 			}
6569 			case MPI2_EVENT_IR_CHANGE_RC_REMOVED:
6570 			case MPI2_EVENT_IR_CHANGE_RC_VOLUME_DELETED:
6571 			{
6572 				NDBG20(("mptsas %d volume deleted\n",
6573 				    mpt->m_instance));
6574 				ptgt = mptsas_search_by_devhdl(tgttbl,
6575 				    volhandle);
6576 				if (ptgt == NULL)
6577 					break;
6578 
6579 				/*
6580 				 * Clear any flags related to volume
6581 				 */
6582 				(void) mptsas_delete_volume(mpt, volhandle);
6583 
6584 				/*
6585 				 * Update DR flag immediately avoid I/O failure
6586 				 */
6587 				mutex_enter(&mpt->m_tx_waitq_mutex);
6588 				ptgt->m_dr_flag = MPTSAS_DR_INTRANSITION;
6589 				mutex_exit(&mpt->m_tx_waitq_mutex);
6590 
6591 				topo_node = kmem_zalloc(
6592 				    sizeof (mptsas_topo_change_list_t),
6593 				    KM_SLEEP);
6594 				topo_node->mpt = mpt;
6595 				topo_node->un.phymask = ptgt->m_phymask;
6596 				topo_node->event =
6597 				    MPTSAS_DR_EVENT_OFFLINE_TARGET;
6598 				topo_node->devhdl = volhandle;
6599 				topo_node->flags =
6600 				    MPTSAS_TOPO_FLAG_RAID_ASSOCIATED;
6601 				topo_node->object = (void *)ptgt;
6602 				if (topo_head == NULL) {
6603 					topo_head = topo_tail = topo_node;
6604 				} else {
6605 					topo_tail->next = topo_node;
6606 					topo_tail = topo_node;
6607 				}
6608 				break;
6609 			}
6610 			case MPI2_EVENT_IR_CHANGE_RC_PD_CREATED:
6611 			case MPI2_EVENT_IR_CHANGE_RC_HIDE:
6612 			{
6613 				ptgt = mptsas_search_by_devhdl(tgttbl,
6614 				    diskhandle);
6615 				if (ptgt == NULL)
6616 					break;
6617 
6618 				/*
6619 				 * Update DR flag immediately avoid I/O failure
6620 				 */
6621 				mutex_enter(&mpt->m_tx_waitq_mutex);
6622 				ptgt->m_dr_flag = MPTSAS_DR_INTRANSITION;
6623 				mutex_exit(&mpt->m_tx_waitq_mutex);
6624 
6625 				topo_node = kmem_zalloc(
6626 				    sizeof (mptsas_topo_change_list_t),
6627 				    KM_SLEEP);
6628 				topo_node->mpt = mpt;
6629 				topo_node->un.phymask = ptgt->m_phymask;
6630 				topo_node->event =
6631 				    MPTSAS_DR_EVENT_OFFLINE_TARGET;
6632 				topo_node->devhdl = diskhandle;
6633 				topo_node->flags =
6634 				    MPTSAS_TOPO_FLAG_RAID_PHYSDRV_ASSOCIATED;
6635 				topo_node->object = (void *)ptgt;
6636 				if (topo_head == NULL) {
6637 					topo_head = topo_tail = topo_node;
6638 				} else {
6639 					topo_tail->next = topo_node;
6640 					topo_tail = topo_node;
6641 				}
6642 				break;
6643 			}
6644 			case MPI2_EVENT_IR_CHANGE_RC_UNHIDE:
6645 			case MPI2_EVENT_IR_CHANGE_RC_PD_DELETED:
6646 			{
6647 				/*
6648 				 * The physical drive is released by a IR
6649 				 * volume. But we cannot get the the physport
6650 				 * or phynum from the event data, so we only
6651 				 * can get the physport/phynum after SAS
6652 				 * Device Page0 request for the devhdl.
6653 				 */
6654 				topo_node = kmem_zalloc(
6655 				    sizeof (mptsas_topo_change_list_t),
6656 				    KM_SLEEP);
6657 				topo_node->mpt = mpt;
6658 				topo_node->un.phymask = 0;
6659 				topo_node->event =
6660 				    MPTSAS_DR_EVENT_RECONFIG_TARGET;
6661 				topo_node->devhdl = diskhandle;
6662 				topo_node->flags =
6663 				    MPTSAS_TOPO_FLAG_RAID_PHYSDRV_ASSOCIATED;
6664 				topo_node->object = NULL;
6665 				mpt->m_port_chng = 1;
6666 				if (topo_head == NULL) {
6667 					topo_head = topo_tail = topo_node;
6668 				} else {
6669 					topo_tail->next = topo_node;
6670 					topo_tail = topo_node;
6671 				}
6672 				break;
6673 			}
6674 			default:
6675 				break;
6676 			}
6677 		}
6678 
6679 		if (topo_head != NULL) {
6680 			/*
6681 			 * Launch DR taskq to handle topology change
6682 			 */
6683 			if ((ddi_taskq_dispatch(mpt->m_dr_taskq,
6684 			    mptsas_handle_dr, (void *)topo_head,
6685 			    DDI_NOSLEEP)) != DDI_SUCCESS) {
6686 				mptsas_log(mpt, CE_NOTE, "mptsas start taskq "
6687 				    "for handle SAS DR event failed. \n");
6688 			}
6689 		}
6690 		break;
6691 	}
6692 	default:
6693 		return (DDI_FAILURE);
6694 	}
6695 
6696 	return (DDI_SUCCESS);
6697 }
6698 
6699 /*
6700  * handle events from ioc
6701  */
6702 static void
6703 mptsas_handle_event(void *args)
6704 {
6705 	m_replyh_arg_t			*replyh_arg;
6706 	pMpi2EventNotificationReply_t	eventreply;
6707 	uint32_t			event, iocloginfo, rfm;
6708 	uint32_t			status;
6709 	uint8_t				port;
6710 	mptsas_t			*mpt;
6711 	uint_t				iocstatus;
6712 
6713 	replyh_arg = (m_replyh_arg_t *)args;
6714 	rfm = replyh_arg->rfm;
6715 	mpt = replyh_arg->mpt;
6716 
6717 	mutex_enter(&mpt->m_mutex);
6718 
6719 	eventreply = (pMpi2EventNotificationReply_t)
6720 	    (mpt->m_reply_frame + (rfm - mpt->m_reply_frame_dma_addr));
6721 	event = ddi_get16(mpt->m_acc_reply_frame_hdl, &eventreply->Event);
6722 
6723 	if (iocstatus = ddi_get16(mpt->m_acc_reply_frame_hdl,
6724 	    &eventreply->IOCStatus)) {
6725 		if (iocstatus == MPI2_IOCSTATUS_FLAG_LOG_INFO_AVAILABLE) {
6726 			mptsas_log(mpt, CE_WARN,
6727 			    "!mptsas_handle_event: IOCStatus=0x%x, "
6728 			    "IOCLogInfo=0x%x", iocstatus,
6729 			    ddi_get32(mpt->m_acc_reply_frame_hdl,
6730 			    &eventreply->IOCLogInfo));
6731 		} else {
6732 			mptsas_log(mpt, CE_WARN,
6733 			    "mptsas_handle_event: IOCStatus=0x%x, "
6734 			    "IOCLogInfo=0x%x", iocstatus,
6735 			    ddi_get32(mpt->m_acc_reply_frame_hdl,
6736 			    &eventreply->IOCLogInfo));
6737 		}
6738 	}
6739 
6740 	/*
6741 	 * figure out what kind of event we got and handle accordingly
6742 	 */
6743 	switch (event) {
6744 	case MPI2_EVENT_LOG_ENTRY_ADDED:
6745 		break;
6746 	case MPI2_EVENT_LOG_DATA:
6747 		iocloginfo = ddi_get32(mpt->m_acc_reply_frame_hdl,
6748 		    &eventreply->IOCLogInfo);
6749 		NDBG20(("mptsas %d log info %x received.\n", mpt->m_instance,
6750 		    iocloginfo));
6751 		break;
6752 	case MPI2_EVENT_STATE_CHANGE:
6753 		NDBG20(("mptsas%d state change.", mpt->m_instance));
6754 		break;
6755 	case MPI2_EVENT_HARD_RESET_RECEIVED:
6756 		NDBG20(("mptsas%d event change.", mpt->m_instance));
6757 		break;
6758 	case MPI2_EVENT_SAS_DISCOVERY:
6759 	{
6760 		MPI2_EVENT_DATA_SAS_DISCOVERY	*sasdiscovery;
6761 		char				string[80];
6762 		uint8_t				rc;
6763 
6764 		sasdiscovery =
6765 		    (pMpi2EventDataSasDiscovery_t)eventreply->EventData;
6766 
6767 		rc = ddi_get8(mpt->m_acc_reply_frame_hdl,
6768 		    &sasdiscovery->ReasonCode);
6769 		port = ddi_get8(mpt->m_acc_reply_frame_hdl,
6770 		    &sasdiscovery->PhysicalPort);
6771 		status = ddi_get32(mpt->m_acc_reply_frame_hdl,
6772 		    &sasdiscovery->DiscoveryStatus);
6773 
6774 		string[0] = 0;
6775 		switch (rc) {
6776 		case MPI2_EVENT_SAS_DISC_RC_STARTED:
6777 			(void) sprintf(string, "STARTING");
6778 			break;
6779 		case MPI2_EVENT_SAS_DISC_RC_COMPLETED:
6780 			(void) sprintf(string, "COMPLETED");
6781 			break;
6782 		default:
6783 			(void) sprintf(string, "UNKNOWN");
6784 			break;
6785 		}
6786 
6787 		NDBG20(("SAS DISCOVERY is %s for port %d, status %x", string,
6788 		    port, status));
6789 
6790 		break;
6791 	}
6792 	case MPI2_EVENT_EVENT_CHANGE:
6793 		NDBG20(("mptsas%d event change.", mpt->m_instance));
6794 		break;
6795 	case MPI2_EVENT_TASK_SET_FULL:
6796 	{
6797 		pMpi2EventDataTaskSetFull_t	taskfull;
6798 
6799 		taskfull = (pMpi2EventDataTaskSetFull_t)eventreply->EventData;
6800 
6801 		NDBG20(("TASK_SET_FULL received for mptsas%d, depth %d\n",
6802 		    mpt->m_instance,  ddi_get16(mpt->m_acc_reply_frame_hdl,
6803 		    &taskfull->CurrentDepth)));
6804 		break;
6805 	}
6806 	case MPI2_EVENT_SAS_TOPOLOGY_CHANGE_LIST:
6807 	{
6808 		/*
6809 		 * SAS TOPOLOGY CHANGE LIST Event has already been handled
6810 		 * in mptsas_handle_event_sync() of interrupt context
6811 		 */
6812 		break;
6813 	}
6814 	case MPI2_EVENT_SAS_ENCL_DEVICE_STATUS_CHANGE:
6815 	{
6816 		pMpi2EventDataSasEnclDevStatusChange_t	encstatus;
6817 		uint8_t					rc;
6818 		char					string[80];
6819 
6820 		encstatus = (pMpi2EventDataSasEnclDevStatusChange_t)
6821 		    eventreply->EventData;
6822 
6823 		rc = ddi_get8(mpt->m_acc_reply_frame_hdl,
6824 		    &encstatus->ReasonCode);
6825 		switch (rc) {
6826 		case MPI2_EVENT_SAS_ENCL_RC_ADDED:
6827 			(void) sprintf(string, "added");
6828 			break;
6829 		case MPI2_EVENT_SAS_ENCL_RC_NOT_RESPONDING:
6830 			(void) sprintf(string, ", not responding");
6831 			break;
6832 		default:
6833 		break;
6834 		}
6835 		NDBG20(("mptsas%d ENCLOSURE STATUS CHANGE for enclosure %x%s\n",
6836 		    mpt->m_instance, ddi_get16(mpt->m_acc_reply_frame_hdl,
6837 		    &encstatus->EnclosureHandle), string));
6838 		break;
6839 	}
6840 
6841 	/*
6842 	 * MPI2_EVENT_SAS_DEVICE_STATUS_CHANGE is handled by
6843 	 * mptsas_handle_event_sync,in here just send ack message.
6844 	 */
6845 	case MPI2_EVENT_SAS_DEVICE_STATUS_CHANGE:
6846 	{
6847 		pMpi2EventDataSasDeviceStatusChange_t	statuschange;
6848 		uint8_t					rc;
6849 		uint16_t				devhdl;
6850 		uint64_t				wwn = 0;
6851 		uint32_t				wwn_lo, wwn_hi;
6852 
6853 		statuschange = (pMpi2EventDataSasDeviceStatusChange_t)
6854 		    eventreply->EventData;
6855 		rc = ddi_get8(mpt->m_acc_reply_frame_hdl,
6856 		    &statuschange->ReasonCode);
6857 		wwn_lo = ddi_get32(mpt->m_acc_reply_frame_hdl,
6858 		    (uint32_t *)(void *)&statuschange->SASAddress);
6859 		wwn_hi = ddi_get32(mpt->m_acc_reply_frame_hdl,
6860 		    (uint32_t *)(void *)&statuschange->SASAddress + 1);
6861 		wwn = ((uint64_t)wwn_hi << 32) | wwn_lo;
6862 		devhdl =  ddi_get16(mpt->m_acc_reply_frame_hdl,
6863 		    &statuschange->DevHandle);
6864 
6865 		NDBG13(("MPI2_EVENT_SAS_DEVICE_STATUS_CHANGE wwn is %"PRIx64,
6866 		    wwn));
6867 
6868 		switch (rc) {
6869 		case MPI2_EVENT_SAS_DEV_STAT_RC_SMART_DATA:
6870 			NDBG20(("SMART data received, ASC/ASCQ = %02x/%02x",
6871 			    ddi_get8(mpt->m_acc_reply_frame_hdl,
6872 			    &statuschange->ASC),
6873 			    ddi_get8(mpt->m_acc_reply_frame_hdl,
6874 			    &statuschange->ASCQ)));
6875 			break;
6876 
6877 		case MPI2_EVENT_SAS_DEV_STAT_RC_UNSUPPORTED:
6878 			NDBG20(("Device not supported"));
6879 			break;
6880 
6881 		case MPI2_EVENT_SAS_DEV_STAT_RC_INTERNAL_DEVICE_RESET:
6882 			NDBG20(("IOC internally generated the Target Reset "
6883 			    "for devhdl:%x", devhdl));
6884 			break;
6885 
6886 		case MPI2_EVENT_SAS_DEV_STAT_RC_CMP_INTERNAL_DEV_RESET:
6887 			NDBG20(("IOC's internally generated Target Reset "
6888 			    "completed for devhdl:%x", devhdl));
6889 			break;
6890 
6891 		case MPI2_EVENT_SAS_DEV_STAT_RC_TASK_ABORT_INTERNAL:
6892 			NDBG20(("IOC internally generated Abort Task"));
6893 			break;
6894 
6895 		case MPI2_EVENT_SAS_DEV_STAT_RC_CMP_TASK_ABORT_INTERNAL:
6896 			NDBG20(("IOC's internally generated Abort Task "
6897 			    "completed"));
6898 			break;
6899 
6900 		case MPI2_EVENT_SAS_DEV_STAT_RC_ABORT_TASK_SET_INTERNAL:
6901 			NDBG20(("IOC internally generated Abort Task Set"));
6902 			break;
6903 
6904 		case MPI2_EVENT_SAS_DEV_STAT_RC_CLEAR_TASK_SET_INTERNAL:
6905 			NDBG20(("IOC internally generated Clear Task Set"));
6906 			break;
6907 
6908 		case MPI2_EVENT_SAS_DEV_STAT_RC_QUERY_TASK_INTERNAL:
6909 			NDBG20(("IOC internally generated Query Task"));
6910 			break;
6911 
6912 		case MPI2_EVENT_SAS_DEV_STAT_RC_ASYNC_NOTIFICATION:
6913 			NDBG20(("Device sent an Asynchronous Notification"));
6914 			break;
6915 
6916 		default:
6917 			break;
6918 		}
6919 		break;
6920 	}
6921 	case MPI2_EVENT_IR_CONFIGURATION_CHANGE_LIST:
6922 	{
6923 		/*
6924 		 * IR TOPOLOGY CHANGE LIST Event has already been handled
6925 		 * in mpt_handle_event_sync() of interrupt context
6926 		 */
6927 		break;
6928 	}
6929 	case MPI2_EVENT_IR_OPERATION_STATUS:
6930 	{
6931 		Mpi2EventDataIrOperationStatus_t	*irOpStatus;
6932 		char					reason_str[80];
6933 		uint8_t					rc, percent;
6934 		uint16_t				handle;
6935 
6936 		irOpStatus = (pMpi2EventDataIrOperationStatus_t)
6937 		    eventreply->EventData;
6938 		rc = ddi_get8(mpt->m_acc_reply_frame_hdl,
6939 		    &irOpStatus->RAIDOperation);
6940 		percent = ddi_get8(mpt->m_acc_reply_frame_hdl,
6941 		    &irOpStatus->PercentComplete);
6942 		handle = ddi_get16(mpt->m_acc_reply_frame_hdl,
6943 		    &irOpStatus->VolDevHandle);
6944 
6945 		switch (rc) {
6946 			case MPI2_EVENT_IR_RAIDOP_RESYNC:
6947 				(void) sprintf(reason_str, "resync");
6948 				break;
6949 			case MPI2_EVENT_IR_RAIDOP_ONLINE_CAP_EXPANSION:
6950 				(void) sprintf(reason_str, "online capacity "
6951 				    "expansion");
6952 				break;
6953 			case MPI2_EVENT_IR_RAIDOP_CONSISTENCY_CHECK:
6954 				(void) sprintf(reason_str, "consistency check");
6955 				break;
6956 			default:
6957 				(void) sprintf(reason_str, "unknown reason %x",
6958 				    rc);
6959 		}
6960 
6961 		NDBG20(("mptsas%d raid operational status: (%s)"
6962 		    "\thandle(0x%04x), percent complete(%d)\n",
6963 		    mpt->m_instance, reason_str, handle, percent));
6964 		break;
6965 	}
6966 	case MPI2_EVENT_IR_VOLUME:
6967 	{
6968 		Mpi2EventDataIrVolume_t		*irVolume;
6969 		uint16_t			devhandle;
6970 		uint32_t			state;
6971 		int				config, vol;
6972 		mptsas_slots_t			*slots = mpt->m_active;
6973 		uint8_t				found = FALSE;
6974 
6975 		irVolume = (pMpi2EventDataIrVolume_t)eventreply->EventData;
6976 		state = ddi_get32(mpt->m_acc_reply_frame_hdl,
6977 		    &irVolume->NewValue);
6978 		devhandle = ddi_get16(mpt->m_acc_reply_frame_hdl,
6979 		    &irVolume->VolDevHandle);
6980 
6981 		NDBG20(("EVENT_IR_VOLUME event is received"));
6982 
6983 		/*
6984 		 * Get latest RAID info and then find the DevHandle for this
6985 		 * event in the configuration.  If the DevHandle is not found
6986 		 * just exit the event.
6987 		 */
6988 		(void) mptsas_get_raid_info(mpt);
6989 		for (config = 0; config < slots->m_num_raid_configs;
6990 		    config++) {
6991 			for (vol = 0; vol < MPTSAS_MAX_RAIDVOLS; vol++) {
6992 				if (slots->m_raidconfig[config].m_raidvol[vol].
6993 				    m_raidhandle == devhandle) {
6994 					found = TRUE;
6995 					break;
6996 				}
6997 			}
6998 		}
6999 		if (!found) {
7000 			break;
7001 		}
7002 
7003 		switch (irVolume->ReasonCode) {
7004 		case MPI2_EVENT_IR_VOLUME_RC_SETTINGS_CHANGED:
7005 		{
7006 			uint32_t i;
7007 			slots->m_raidconfig[config].m_raidvol[vol].m_settings =
7008 			    state;
7009 
7010 			i = state & MPI2_RAIDVOL0_SETTING_MASK_WRITE_CACHING;
7011 			mptsas_log(mpt, CE_NOTE, " Volume %d settings changed"
7012 			    ", auto-config of hot-swap drives is %s"
7013 			    ", write caching is %s"
7014 			    ", hot-spare pool mask is %02x\n",
7015 			    vol, state &
7016 			    MPI2_RAIDVOL0_SETTING_AUTO_CONFIG_HSWAP_DISABLE
7017 			    ? "disabled" : "enabled",
7018 			    i == MPI2_RAIDVOL0_SETTING_UNCHANGED
7019 			    ? "controlled by member disks" :
7020 			    i == MPI2_RAIDVOL0_SETTING_DISABLE_WRITE_CACHING
7021 			    ? "disabled" :
7022 			    i == MPI2_RAIDVOL0_SETTING_ENABLE_WRITE_CACHING
7023 			    ? "enabled" :
7024 			    "incorrectly set",
7025 			    (state >> 16) & 0xff);
7026 				break;
7027 		}
7028 		case MPI2_EVENT_IR_VOLUME_RC_STATE_CHANGED:
7029 		{
7030 			slots->m_raidconfig[config].m_raidvol[vol].m_state =
7031 			    (uint8_t)state;
7032 
7033 			mptsas_log(mpt, CE_NOTE,
7034 			    "Volume %d is now %s\n", vol,
7035 			    state == MPI2_RAID_VOL_STATE_OPTIMAL
7036 			    ? "optimal" :
7037 			    state == MPI2_RAID_VOL_STATE_DEGRADED
7038 			    ? "degraded" :
7039 			    state == MPI2_RAID_VOL_STATE_ONLINE
7040 			    ? "online" :
7041 			    state == MPI2_RAID_VOL_STATE_INITIALIZING
7042 			    ? "initializing" :
7043 			    state == MPI2_RAID_VOL_STATE_FAILED
7044 			    ? "failed" :
7045 			    state == MPI2_RAID_VOL_STATE_MISSING
7046 			    ? "missing" :
7047 			    "state unknown");
7048 			break;
7049 		}
7050 		case MPI2_EVENT_IR_VOLUME_RC_STATUS_FLAGS_CHANGED:
7051 		{
7052 			slots->m_raidconfig[config].m_raidvol[vol].
7053 			    m_statusflags = state;
7054 
7055 			mptsas_log(mpt, CE_NOTE,
7056 			    " Volume %d is now %s%s%s%s%s%s%s%s%s\n",
7057 			    vol,
7058 			    state & MPI2_RAIDVOL0_STATUS_FLAG_ENABLED
7059 			    ? ", enabled" : ", disabled",
7060 			    state & MPI2_RAIDVOL0_STATUS_FLAG_QUIESCED
7061 			    ? ", quiesced" : "",
7062 			    state & MPI2_RAIDVOL0_STATUS_FLAG_VOLUME_INACTIVE
7063 			    ? ", inactive" : ", active",
7064 			    state &
7065 			    MPI2_RAIDVOL0_STATUS_FLAG_BAD_BLOCK_TABLE_FULL
7066 			    ? ", bad block table is full" : "",
7067 			    state &
7068 			    MPI2_RAIDVOL0_STATUS_FLAG_RESYNC_IN_PROGRESS
7069 			    ? ", resync in progress" : "",
7070 			    state & MPI2_RAIDVOL0_STATUS_FLAG_BACKGROUND_INIT
7071 			    ? ", background initialization in progress" : "",
7072 			    state &
7073 			    MPI2_RAIDVOL0_STATUS_FLAG_CAPACITY_EXPANSION
7074 			    ? ", capacity expansion in progress" : "",
7075 			    state &
7076 			    MPI2_RAIDVOL0_STATUS_FLAG_CONSISTENCY_CHECK
7077 			    ? ", consistency check in progress" : "",
7078 			    state & MPI2_RAIDVOL0_STATUS_FLAG_DATA_SCRUB
7079 			    ? ", data scrub in progress" : "");
7080 			break;
7081 		}
7082 		default:
7083 			break;
7084 		}
7085 		break;
7086 	}
7087 	case MPI2_EVENT_IR_PHYSICAL_DISK:
7088 	{
7089 		Mpi2EventDataIrPhysicalDisk_t	*irPhysDisk;
7090 		uint16_t			devhandle, enchandle, slot;
7091 		uint32_t			status, state;
7092 		uint8_t				physdisknum, reason;
7093 
7094 		irPhysDisk = (Mpi2EventDataIrPhysicalDisk_t *)
7095 		    eventreply->EventData;
7096 		physdisknum = ddi_get8(mpt->m_acc_reply_frame_hdl,
7097 		    &irPhysDisk->PhysDiskNum);
7098 		devhandle = ddi_get16(mpt->m_acc_reply_frame_hdl,
7099 		    &irPhysDisk->PhysDiskDevHandle);
7100 		enchandle = ddi_get16(mpt->m_acc_reply_frame_hdl,
7101 		    &irPhysDisk->EnclosureHandle);
7102 		slot = ddi_get16(mpt->m_acc_reply_frame_hdl,
7103 		    &irPhysDisk->Slot);
7104 		state = ddi_get32(mpt->m_acc_reply_frame_hdl,
7105 		    &irPhysDisk->NewValue);
7106 		reason = ddi_get8(mpt->m_acc_reply_frame_hdl,
7107 		    &irPhysDisk->ReasonCode);
7108 
7109 		NDBG20(("EVENT_IR_PHYSICAL_DISK event is received"));
7110 
7111 		switch (reason) {
7112 		case MPI2_EVENT_IR_PHYSDISK_RC_SETTINGS_CHANGED:
7113 			mptsas_log(mpt, CE_NOTE,
7114 			    " PhysDiskNum %d with DevHandle 0x%x in slot %d "
7115 			    "for enclosure with handle 0x%x is now in hot "
7116 			    "spare pool %d",
7117 			    physdisknum, devhandle, slot, enchandle,
7118 			    (state >> 16) & 0xff);
7119 			break;
7120 
7121 		case MPI2_EVENT_IR_PHYSDISK_RC_STATUS_FLAGS_CHANGED:
7122 			status = state;
7123 			mptsas_log(mpt, CE_NOTE,
7124 			    " PhysDiskNum %d with DevHandle 0x%x in slot %d "
7125 			    "for enclosure with handle 0x%x is now "
7126 			    "%s%s%s%s%s\n", physdisknum, devhandle, slot,
7127 			    enchandle,
7128 			    status & MPI2_PHYSDISK0_STATUS_FLAG_INACTIVE_VOLUME
7129 			    ? ", inactive" : ", active",
7130 			    status & MPI2_PHYSDISK0_STATUS_FLAG_OUT_OF_SYNC
7131 			    ? ", out of sync" : "",
7132 			    status & MPI2_PHYSDISK0_STATUS_FLAG_QUIESCED
7133 			    ? ", quiesced" : "",
7134 			    status &
7135 			    MPI2_PHYSDISK0_STATUS_FLAG_WRITE_CACHE_ENABLED
7136 			    ? ", write cache enabled" : "",
7137 			    status & MPI2_PHYSDISK0_STATUS_FLAG_OCE_TARGET
7138 			    ? ", capacity expansion target" : "");
7139 			break;
7140 
7141 		case MPI2_EVENT_IR_PHYSDISK_RC_STATE_CHANGED:
7142 			mptsas_log(mpt, CE_NOTE,
7143 			    " PhysDiskNum %d with DevHandle 0x%x in slot %d "
7144 			    "for enclosure with handle 0x%x is now %s\n",
7145 			    physdisknum, devhandle, slot, enchandle,
7146 			    state == MPI2_RAID_PD_STATE_OPTIMAL
7147 			    ? "optimal" :
7148 			    state == MPI2_RAID_PD_STATE_REBUILDING
7149 			    ? "rebuilding" :
7150 			    state == MPI2_RAID_PD_STATE_DEGRADED
7151 			    ? "degraded" :
7152 			    state == MPI2_RAID_PD_STATE_HOT_SPARE
7153 			    ? "a hot spare" :
7154 			    state == MPI2_RAID_PD_STATE_ONLINE
7155 			    ? "online" :
7156 			    state == MPI2_RAID_PD_STATE_OFFLINE
7157 			    ? "offline" :
7158 			    state == MPI2_RAID_PD_STATE_NOT_COMPATIBLE
7159 			    ? "not compatible" :
7160 			    state == MPI2_RAID_PD_STATE_NOT_CONFIGURED
7161 			    ? "not configured" :
7162 			    "state unknown");
7163 			break;
7164 		}
7165 		break;
7166 	}
7167 	default:
7168 		NDBG20(("mptsas%d: unknown event %x received",
7169 		    mpt->m_instance, event));
7170 		break;
7171 	}
7172 
7173 	/*
7174 	 * Return the reply frame to the free queue.
7175 	 */
7176 	ddi_put32(mpt->m_acc_free_queue_hdl,
7177 	    &((uint32_t *)(void *)mpt->m_free_queue)[mpt->m_free_index], rfm);
7178 	(void) ddi_dma_sync(mpt->m_dma_free_queue_hdl, 0, 0,
7179 	    DDI_DMA_SYNC_FORDEV);
7180 	if (++mpt->m_free_index == mpt->m_free_queue_depth) {
7181 		mpt->m_free_index = 0;
7182 	}
7183 	ddi_put32(mpt->m_datap, &mpt->m_reg->ReplyFreeHostIndex,
7184 	    mpt->m_free_index);
7185 	mutex_exit(&mpt->m_mutex);
7186 }
7187 
7188 /*
7189  * invoked from timeout() to restart qfull cmds with throttle == 0
7190  */
7191 static void
7192 mptsas_restart_cmd(void *arg)
7193 {
7194 	mptsas_t	*mpt = arg;
7195 	mptsas_target_t	*ptgt = NULL;
7196 
7197 	mutex_enter(&mpt->m_mutex);
7198 
7199 	mpt->m_restart_cmd_timeid = 0;
7200 
7201 	ptgt = (mptsas_target_t *)mptsas_hash_traverse(&mpt->m_active->m_tgttbl,
7202 	    MPTSAS_HASH_FIRST);
7203 	while (ptgt != NULL) {
7204 		if (ptgt->m_reset_delay == 0) {
7205 			if (ptgt->m_t_throttle == QFULL_THROTTLE) {
7206 				mptsas_set_throttle(mpt, ptgt,
7207 				    MAX_THROTTLE);
7208 			}
7209 		}
7210 
7211 		ptgt = (mptsas_target_t *)mptsas_hash_traverse(
7212 		    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
7213 	}
7214 	mptsas_restart_hba(mpt);
7215 	mutex_exit(&mpt->m_mutex);
7216 }
7217 
7218 void
7219 mptsas_remove_cmd(mptsas_t *mpt, mptsas_cmd_t *cmd)
7220 {
7221 	int		slot;
7222 	mptsas_slots_t	*slots = mpt->m_active;
7223 	int		t;
7224 	mptsas_target_t	*ptgt = cmd->cmd_tgt_addr;
7225 
7226 	ASSERT(cmd != NULL);
7227 	ASSERT(cmd->cmd_queued == FALSE);
7228 
7229 	/*
7230 	 * Task Management cmds are removed in their own routines.  Also,
7231 	 * we don't want to modify timeout based on TM cmds.
7232 	 */
7233 	if (cmd->cmd_flags & CFLAG_TM_CMD) {
7234 		return;
7235 	}
7236 
7237 	t = Tgt(cmd);
7238 	slot = cmd->cmd_slot;
7239 
7240 	/*
7241 	 * remove the cmd.
7242 	 */
7243 	if (cmd == slots->m_slot[slot]) {
7244 		NDBG31(("mptsas_remove_cmd: removing cmd=0x%p", (void *)cmd));
7245 		slots->m_slot[slot] = NULL;
7246 		mpt->m_ncmds--;
7247 
7248 		/*
7249 		 * only decrement per target ncmds if command
7250 		 * has a target associated with it.
7251 		 */
7252 		if ((cmd->cmd_flags & CFLAG_CMDIOC) == 0) {
7253 			ptgt->m_t_ncmds--;
7254 			/*
7255 			 * reset throttle if we just ran an untagged command
7256 			 * to a tagged target
7257 			 */
7258 			if ((ptgt->m_t_ncmds == 0) &&
7259 			    ((cmd->cmd_pkt_flags & FLAG_TAGMASK) == 0)) {
7260 				mptsas_set_throttle(mpt, ptgt, MAX_THROTTLE);
7261 			}
7262 		}
7263 
7264 	}
7265 
7266 	/*
7267 	 * This is all we need to do for ioc commands.
7268 	 */
7269 	if (cmd->cmd_flags & CFLAG_CMDIOC) {
7270 		mptsas_return_to_pool(mpt, cmd);
7271 		return;
7272 	}
7273 
7274 	/*
7275 	 * Figure out what to set tag Q timeout for...
7276 	 *
7277 	 * Optimize: If we have duplicate's of same timeout
7278 	 * we're using, then we'll use it again until we run
7279 	 * out of duplicates.  This should be the normal case
7280 	 * for block and raw I/O.
7281 	 * If no duplicates, we have to scan through tag que and
7282 	 * find the longest timeout value and use it.  This is
7283 	 * going to take a while...
7284 	 * Add 1 to m_n_slots to account for TM request.
7285 	 */
7286 	if (cmd->cmd_pkt->pkt_time == ptgt->m_timebase) {
7287 		if (--(ptgt->m_dups) == 0) {
7288 			if (ptgt->m_t_ncmds) {
7289 				mptsas_cmd_t *ssp;
7290 				uint_t n = 0;
7291 				ushort_t nslots = (slots->m_n_slots + 1);
7292 				ushort_t i;
7293 				/*
7294 				 * This crude check assumes we don't do
7295 				 * this too often which seems reasonable
7296 				 * for block and raw I/O.
7297 				 */
7298 				for (i = 0; i < nslots; i++) {
7299 					ssp = slots->m_slot[i];
7300 					if (ssp && (Tgt(ssp) == t) &&
7301 					    (ssp->cmd_pkt->pkt_time > n)) {
7302 						n = ssp->cmd_pkt->pkt_time;
7303 						ptgt->m_dups = 1;
7304 					} else if (ssp && (Tgt(ssp) == t) &&
7305 					    (ssp->cmd_pkt->pkt_time == n)) {
7306 						ptgt->m_dups++;
7307 					}
7308 				}
7309 				ptgt->m_timebase = n;
7310 			} else {
7311 				ptgt->m_dups = 0;
7312 				ptgt->m_timebase = 0;
7313 			}
7314 		}
7315 	}
7316 	ptgt->m_timeout = ptgt->m_timebase;
7317 
7318 	ASSERT(cmd != slots->m_slot[cmd->cmd_slot]);
7319 }
7320 
7321 /*
7322  * accept all cmds on the tx_waitq if any and then
7323  * start a fresh request from the top of the device queue.
7324  *
7325  * since there are always cmds queued on the tx_waitq, and rare cmds on
7326  * the instance waitq, so this function should not be invoked in the ISR,
7327  * the mptsas_restart_waitq() is invoked in the ISR instead. otherwise, the
7328  * burden belongs to the IO dispatch CPUs is moved the interrupt CPU.
7329  */
7330 static void
7331 mptsas_restart_hba(mptsas_t *mpt)
7332 {
7333 	ASSERT(mutex_owned(&mpt->m_mutex));
7334 
7335 	mutex_enter(&mpt->m_tx_waitq_mutex);
7336 	if (mpt->m_tx_waitq) {
7337 		mptsas_accept_tx_waitq(mpt);
7338 	}
7339 	mutex_exit(&mpt->m_tx_waitq_mutex);
7340 	mptsas_restart_waitq(mpt);
7341 }
7342 
7343 /*
7344  * start a fresh request from the top of the device queue
7345  */
7346 static void
7347 mptsas_restart_waitq(mptsas_t *mpt)
7348 {
7349 	mptsas_cmd_t	*cmd, *next_cmd;
7350 	mptsas_target_t *ptgt = NULL;
7351 
7352 	NDBG1(("mptsas_restart_waitq: mpt=0x%p", (void *)mpt));
7353 
7354 	ASSERT(mutex_owned(&mpt->m_mutex));
7355 
7356 	/*
7357 	 * If there is a reset delay, don't start any cmds.  Otherwise, start
7358 	 * as many cmds as possible.
7359 	 * Since SMID 0 is reserved and the TM slot is reserved, the actual max
7360 	 * commands is m_max_requests - 2.
7361 	 */
7362 	cmd = mpt->m_waitq;
7363 
7364 	while (cmd != NULL) {
7365 		next_cmd = cmd->cmd_linkp;
7366 		if (cmd->cmd_flags & CFLAG_PASSTHRU) {
7367 			if (mptsas_save_cmd(mpt, cmd) == TRUE) {
7368 				/*
7369 				 * passthru command get slot need
7370 				 * set CFLAG_PREPARED.
7371 				 */
7372 				cmd->cmd_flags |= CFLAG_PREPARED;
7373 				mptsas_waitq_delete(mpt, cmd);
7374 				mptsas_start_passthru(mpt, cmd);
7375 			}
7376 			cmd = next_cmd;
7377 			continue;
7378 		}
7379 		if (cmd->cmd_flags & CFLAG_CONFIG) {
7380 			if (mptsas_save_cmd(mpt, cmd) == TRUE) {
7381 				/*
7382 				 * Send the config page request and delete it
7383 				 * from the waitq.
7384 				 */
7385 				cmd->cmd_flags |= CFLAG_PREPARED;
7386 				mptsas_waitq_delete(mpt, cmd);
7387 				mptsas_start_config_page_access(mpt, cmd);
7388 			}
7389 			cmd = next_cmd;
7390 			continue;
7391 		}
7392 
7393 		ptgt = cmd->cmd_tgt_addr;
7394 		if (ptgt && (ptgt->m_t_throttle == DRAIN_THROTTLE) &&
7395 		    (ptgt->m_t_ncmds == 0)) {
7396 			mptsas_set_throttle(mpt, ptgt, MAX_THROTTLE);
7397 		}
7398 		if ((mpt->m_ncmds <= (mpt->m_max_requests - 2)) &&
7399 		    (ptgt && (ptgt->m_reset_delay == 0)) &&
7400 		    (ptgt && (ptgt->m_t_ncmds <
7401 		    ptgt->m_t_throttle))) {
7402 			if (mptsas_save_cmd(mpt, cmd) == TRUE) {
7403 				mptsas_waitq_delete(mpt, cmd);
7404 				(void) mptsas_start_cmd(mpt, cmd);
7405 			}
7406 		}
7407 		cmd = next_cmd;
7408 	}
7409 }
7410 /*
7411  * Cmds are queued if tran_start() doesn't get the m_mutexlock(no wait).
7412  * Accept all those queued cmds before new cmd is accept so that the
7413  * cmds are sent in order.
7414  */
7415 static void
7416 mptsas_accept_tx_waitq(mptsas_t *mpt)
7417 {
7418 	mptsas_cmd_t *cmd;
7419 
7420 	ASSERT(mutex_owned(&mpt->m_mutex));
7421 	ASSERT(mutex_owned(&mpt->m_tx_waitq_mutex));
7422 
7423 	/*
7424 	 * A Bus Reset could occur at any time and flush the tx_waitq,
7425 	 * so we cannot count on the tx_waitq to contain even one cmd.
7426 	 * And when the m_tx_waitq_mutex is released and run
7427 	 * mptsas_accept_pkt(), the tx_waitq may be flushed.
7428 	 */
7429 	cmd = mpt->m_tx_waitq;
7430 	for (;;) {
7431 		if ((cmd = mpt->m_tx_waitq) == NULL) {
7432 			mpt->m_tx_draining = 0;
7433 			break;
7434 		}
7435 		if ((mpt->m_tx_waitq = cmd->cmd_linkp) == NULL) {
7436 			mpt->m_tx_waitqtail = &mpt->m_tx_waitq;
7437 		}
7438 		cmd->cmd_linkp = NULL;
7439 		mutex_exit(&mpt->m_tx_waitq_mutex);
7440 		if (mptsas_accept_pkt(mpt, cmd) != TRAN_ACCEPT)
7441 			cmn_err(CE_WARN, "mpt: mptsas_accept_tx_waitq: failed "
7442 			    "to accept cmd on queue\n");
7443 		mutex_enter(&mpt->m_tx_waitq_mutex);
7444 	}
7445 }
7446 
7447 
7448 /*
7449  * mpt tag type lookup
7450  */
7451 static char mptsas_tag_lookup[] =
7452 	{0, MSG_HEAD_QTAG, MSG_ORDERED_QTAG, 0, MSG_SIMPLE_QTAG};
7453 
7454 static int
7455 mptsas_start_cmd(mptsas_t *mpt, mptsas_cmd_t *cmd)
7456 {
7457 	struct scsi_pkt		*pkt = CMD2PKT(cmd);
7458 	uint32_t		control = 0;
7459 	int			n;
7460 	caddr_t			mem;
7461 	pMpi2SCSIIORequest_t	io_request;
7462 	ddi_dma_handle_t	dma_hdl = mpt->m_dma_req_frame_hdl;
7463 	ddi_acc_handle_t	acc_hdl = mpt->m_acc_req_frame_hdl;
7464 	mptsas_target_t		*ptgt = cmd->cmd_tgt_addr;
7465 	uint16_t		SMID, io_flags = 0;
7466 	uint32_t		request_desc_low, request_desc_high;
7467 
7468 	NDBG1(("mptsas_start_cmd: cmd=0x%p", (void *)cmd));
7469 
7470 	/*
7471 	 * Set SMID and increment index.  Rollover to 1 instead of 0 if index
7472 	 * is at the max.  0 is an invalid SMID, so we call the first index 1.
7473 	 */
7474 	SMID = cmd->cmd_slot;
7475 
7476 	/*
7477 	 * It is possible for back to back device reset to
7478 	 * happen before the reset delay has expired.  That's
7479 	 * ok, just let the device reset go out on the bus.
7480 	 */
7481 	if ((cmd->cmd_pkt_flags & FLAG_NOINTR) == 0) {
7482 		ASSERT(ptgt->m_reset_delay == 0);
7483 	}
7484 
7485 	/*
7486 	 * if a non-tagged cmd is submitted to an active tagged target
7487 	 * then drain before submitting this cmd; SCSI-2 allows RQSENSE
7488 	 * to be untagged
7489 	 */
7490 	if (((cmd->cmd_pkt_flags & FLAG_TAGMASK) == 0) &&
7491 	    (ptgt->m_t_ncmds > 1) &&
7492 	    ((cmd->cmd_flags & CFLAG_TM_CMD) == 0) &&
7493 	    (*(cmd->cmd_pkt->pkt_cdbp) != SCMD_REQUEST_SENSE)) {
7494 		if ((cmd->cmd_pkt_flags & FLAG_NOINTR) == 0) {
7495 			NDBG23(("target=%d, untagged cmd, start draining\n",
7496 			    ptgt->m_devhdl));
7497 
7498 			if (ptgt->m_reset_delay == 0) {
7499 				mptsas_set_throttle(mpt, ptgt, DRAIN_THROTTLE);
7500 			}
7501 
7502 			mptsas_remove_cmd(mpt, cmd);
7503 			cmd->cmd_pkt_flags |= FLAG_HEAD;
7504 			mptsas_waitq_add(mpt, cmd);
7505 		}
7506 		return (DDI_FAILURE);
7507 	}
7508 
7509 	/*
7510 	 * Set correct tag bits.
7511 	 */
7512 	if (cmd->cmd_pkt_flags & FLAG_TAGMASK) {
7513 		switch (mptsas_tag_lookup[((cmd->cmd_pkt_flags &
7514 		    FLAG_TAGMASK) >> 12)]) {
7515 		case MSG_SIMPLE_QTAG:
7516 			control |= MPI2_SCSIIO_CONTROL_SIMPLEQ;
7517 			break;
7518 		case MSG_HEAD_QTAG:
7519 			control |= MPI2_SCSIIO_CONTROL_HEADOFQ;
7520 			break;
7521 		case MSG_ORDERED_QTAG:
7522 			control |= MPI2_SCSIIO_CONTROL_ORDEREDQ;
7523 			break;
7524 		default:
7525 			mptsas_log(mpt, CE_WARN, "mpt: Invalid tag type\n");
7526 			break;
7527 		}
7528 	} else {
7529 		if (*(cmd->cmd_pkt->pkt_cdbp) != SCMD_REQUEST_SENSE) {
7530 				ptgt->m_t_throttle = 1;
7531 		}
7532 		control |= MPI2_SCSIIO_CONTROL_SIMPLEQ;
7533 	}
7534 
7535 	if (cmd->cmd_pkt_flags & FLAG_TLR) {
7536 		control |= MPI2_SCSIIO_CONTROL_TLR_ON;
7537 	}
7538 
7539 	mem = mpt->m_req_frame + (mpt->m_req_frame_size * SMID);
7540 	io_request = (pMpi2SCSIIORequest_t)mem;
7541 
7542 	bzero(io_request, sizeof (Mpi2SCSIIORequest_t));
7543 	ddi_put8(acc_hdl, &io_request->SGLOffset0, offsetof
7544 	    (MPI2_SCSI_IO_REQUEST, SGL) / 4);
7545 	mptsas_init_std_hdr(acc_hdl, io_request, ptgt->m_devhdl, Lun(cmd), 0,
7546 	    MPI2_FUNCTION_SCSI_IO_REQUEST);
7547 
7548 	(void) ddi_rep_put8(acc_hdl, (uint8_t *)pkt->pkt_cdbp,
7549 	    io_request->CDB.CDB32, cmd->cmd_cdblen, DDI_DEV_AUTOINCR);
7550 
7551 	io_flags = cmd->cmd_cdblen;
7552 	ddi_put16(acc_hdl, &io_request->IoFlags, io_flags);
7553 	/*
7554 	 * setup the Scatter/Gather DMA list for this request
7555 	 */
7556 	if (cmd->cmd_cookiec > 0) {
7557 		mptsas_sge_setup(mpt, cmd, &control, io_request, acc_hdl);
7558 	} else {
7559 		ddi_put32(acc_hdl, &io_request->SGL.MpiSimple.FlagsLength,
7560 		    ((uint32_t)MPI2_SGE_FLAGS_LAST_ELEMENT |
7561 		    MPI2_SGE_FLAGS_END_OF_BUFFER |
7562 		    MPI2_SGE_FLAGS_SIMPLE_ELEMENT |
7563 		    MPI2_SGE_FLAGS_END_OF_LIST) << MPI2_SGE_FLAGS_SHIFT);
7564 	}
7565 
7566 	/*
7567 	 * save ARQ information
7568 	 */
7569 	ddi_put8(acc_hdl, &io_request->SenseBufferLength, cmd->cmd_rqslen);
7570 	if ((cmd->cmd_flags & (CFLAG_SCBEXTERN | CFLAG_EXTARQBUFVALID)) ==
7571 	    (CFLAG_SCBEXTERN | CFLAG_EXTARQBUFVALID)) {
7572 		ddi_put32(acc_hdl, &io_request->SenseBufferLowAddress,
7573 		    cmd->cmd_ext_arqcookie.dmac_address);
7574 	} else {
7575 		ddi_put32(acc_hdl, &io_request->SenseBufferLowAddress,
7576 		    cmd->cmd_arqcookie.dmac_address);
7577 	}
7578 
7579 	ddi_put32(acc_hdl, &io_request->Control, control);
7580 
7581 	NDBG31(("starting message=0x%p, with cmd=0x%p",
7582 	    (void *)(uintptr_t)mpt->m_req_frame_dma_addr, (void *)cmd));
7583 
7584 	(void) ddi_dma_sync(dma_hdl, 0, 0, DDI_DMA_SYNC_FORDEV);
7585 
7586 	/*
7587 	 * Build request descriptor and write it to the request desc post reg.
7588 	 */
7589 	request_desc_low = (SMID << 16) + MPI2_REQ_DESCRIPT_FLAGS_SCSI_IO;
7590 	request_desc_high = ptgt->m_devhdl << 16;
7591 	MPTSAS_START_CMD(mpt, request_desc_low, request_desc_high);
7592 
7593 	/*
7594 	 * Start timeout.
7595 	 */
7596 #ifdef MPTSAS_TEST
7597 	/*
7598 	 * Temporarily set timebase = 0;  needed for
7599 	 * timeout torture test.
7600 	 */
7601 	if (mptsas_test_timeouts) {
7602 		ptgt->m_timebase = 0;
7603 	}
7604 #endif
7605 	n = pkt->pkt_time - ptgt->m_timebase;
7606 
7607 	if (n == 0) {
7608 		(ptgt->m_dups)++;
7609 		ptgt->m_timeout = ptgt->m_timebase;
7610 	} else if (n > 0) {
7611 		ptgt->m_timeout =
7612 		    ptgt->m_timebase = pkt->pkt_time;
7613 		ptgt->m_dups = 1;
7614 	} else if (n < 0) {
7615 		ptgt->m_timeout = ptgt->m_timebase;
7616 	}
7617 #ifdef MPTSAS_TEST
7618 	/*
7619 	 * Set back to a number higher than
7620 	 * mptsas_scsi_watchdog_tick
7621 	 * so timeouts will happen in mptsas_watchsubr
7622 	 */
7623 	if (mptsas_test_timeouts) {
7624 		ptgt->m_timebase = 60;
7625 	}
7626 #endif
7627 
7628 	if ((mptsas_check_dma_handle(dma_hdl) != DDI_SUCCESS) ||
7629 	    (mptsas_check_acc_handle(acc_hdl) != DDI_SUCCESS)) {
7630 		ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_UNAFFECTED);
7631 		return (DDI_FAILURE);
7632 	}
7633 	return (DDI_SUCCESS);
7634 }
7635 
7636 /*
7637  * Select a helper thread to handle current doneq
7638  */
7639 static void
7640 mptsas_deliver_doneq_thread(mptsas_t *mpt)
7641 {
7642 	uint64_t			t, i;
7643 	uint32_t			min = 0xffffffff;
7644 	mptsas_doneq_thread_list_t	*item;
7645 
7646 	for (i = 0; i < mpt->m_doneq_thread_n; i++) {
7647 		item = &mpt->m_doneq_thread_id[i];
7648 		/*
7649 		 * If the completed command on help thread[i] less than
7650 		 * doneq_thread_threshold, then pick the thread[i]. Otherwise
7651 		 * pick a thread which has least completed command.
7652 		 */
7653 
7654 		mutex_enter(&item->mutex);
7655 		if (item->len < mpt->m_doneq_thread_threshold) {
7656 			t = i;
7657 			mutex_exit(&item->mutex);
7658 			break;
7659 		}
7660 		if (item->len < min) {
7661 			min = item->len;
7662 			t = i;
7663 		}
7664 		mutex_exit(&item->mutex);
7665 	}
7666 	mutex_enter(&mpt->m_doneq_thread_id[t].mutex);
7667 	mptsas_doneq_mv(mpt, t);
7668 	cv_signal(&mpt->m_doneq_thread_id[t].cv);
7669 	mutex_exit(&mpt->m_doneq_thread_id[t].mutex);
7670 }
7671 
7672 /*
7673  * move the current global doneq to the doneq of thead[t]
7674  */
7675 static void
7676 mptsas_doneq_mv(mptsas_t *mpt, uint64_t t)
7677 {
7678 	mptsas_cmd_t			*cmd;
7679 	mptsas_doneq_thread_list_t	*item = &mpt->m_doneq_thread_id[t];
7680 
7681 	ASSERT(mutex_owned(&item->mutex));
7682 	while ((cmd = mpt->m_doneq) != NULL) {
7683 		if ((mpt->m_doneq = cmd->cmd_linkp) == NULL) {
7684 			mpt->m_donetail = &mpt->m_doneq;
7685 		}
7686 		cmd->cmd_linkp = NULL;
7687 		*item->donetail = cmd;
7688 		item->donetail = &cmd->cmd_linkp;
7689 		mpt->m_doneq_len--;
7690 		item->len++;
7691 	}
7692 }
7693 
7694 void
7695 mptsas_fma_check(mptsas_t *mpt, mptsas_cmd_t *cmd)
7696 {
7697 	struct scsi_pkt	*pkt = CMD2PKT(cmd);
7698 
7699 	/* Check all acc and dma handles */
7700 	if ((mptsas_check_acc_handle(mpt->m_datap) !=
7701 	    DDI_SUCCESS) ||
7702 	    (mptsas_check_acc_handle(mpt->m_acc_req_frame_hdl) !=
7703 	    DDI_SUCCESS) ||
7704 	    (mptsas_check_acc_handle(mpt->m_acc_reply_frame_hdl) !=
7705 	    DDI_SUCCESS) ||
7706 	    (mptsas_check_acc_handle(mpt->m_acc_free_queue_hdl) !=
7707 	    DDI_SUCCESS) ||
7708 	    (mptsas_check_acc_handle(mpt->m_acc_post_queue_hdl) !=
7709 	    DDI_SUCCESS) ||
7710 	    (mptsas_check_acc_handle(mpt->m_hshk_acc_hdl) !=
7711 	    DDI_SUCCESS) ||
7712 	    (mptsas_check_acc_handle(mpt->m_config_handle) !=
7713 	    DDI_SUCCESS)) {
7714 		ddi_fm_service_impact(mpt->m_dip,
7715 		    DDI_SERVICE_UNAFFECTED);
7716 		ddi_fm_acc_err_clear(mpt->m_config_handle,
7717 		    DDI_FME_VER0);
7718 		pkt->pkt_reason = CMD_TRAN_ERR;
7719 		pkt->pkt_statistics = 0;
7720 	}
7721 	if ((mptsas_check_dma_handle(mpt->m_dma_req_frame_hdl) !=
7722 	    DDI_SUCCESS) ||
7723 	    (mptsas_check_dma_handle(mpt->m_dma_reply_frame_hdl) !=
7724 	    DDI_SUCCESS) ||
7725 	    (mptsas_check_dma_handle(mpt->m_dma_free_queue_hdl) !=
7726 	    DDI_SUCCESS) ||
7727 	    (mptsas_check_dma_handle(mpt->m_dma_post_queue_hdl) !=
7728 	    DDI_SUCCESS) ||
7729 	    (mptsas_check_dma_handle(mpt->m_hshk_dma_hdl) !=
7730 	    DDI_SUCCESS)) {
7731 		ddi_fm_service_impact(mpt->m_dip,
7732 		    DDI_SERVICE_UNAFFECTED);
7733 		pkt->pkt_reason = CMD_TRAN_ERR;
7734 		pkt->pkt_statistics = 0;
7735 	}
7736 	if (cmd->cmd_dmahandle &&
7737 	    (mptsas_check_dma_handle(cmd->cmd_dmahandle) != DDI_SUCCESS)) {
7738 		ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_UNAFFECTED);
7739 		pkt->pkt_reason = CMD_TRAN_ERR;
7740 		pkt->pkt_statistics = 0;
7741 	}
7742 	if ((cmd->cmd_extra_frames &&
7743 	    ((mptsas_check_dma_handle(cmd->cmd_extra_frames->m_dma_hdl) !=
7744 	    DDI_SUCCESS) ||
7745 	    (mptsas_check_acc_handle(cmd->cmd_extra_frames->m_acc_hdl) !=
7746 	    DDI_SUCCESS)))) {
7747 		ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_UNAFFECTED);
7748 		pkt->pkt_reason = CMD_TRAN_ERR;
7749 		pkt->pkt_statistics = 0;
7750 	}
7751 	if (cmd->cmd_arqhandle &&
7752 	    (mptsas_check_dma_handle(cmd->cmd_arqhandle) != DDI_SUCCESS)) {
7753 		ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_UNAFFECTED);
7754 		pkt->pkt_reason = CMD_TRAN_ERR;
7755 		pkt->pkt_statistics = 0;
7756 	}
7757 	if (cmd->cmd_ext_arqhandle &&
7758 	    (mptsas_check_dma_handle(cmd->cmd_ext_arqhandle) != DDI_SUCCESS)) {
7759 		ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_UNAFFECTED);
7760 		pkt->pkt_reason = CMD_TRAN_ERR;
7761 		pkt->pkt_statistics = 0;
7762 	}
7763 }
7764 
7765 /*
7766  * These routines manipulate the queue of commands that
7767  * are waiting for their completion routines to be called.
7768  * The queue is usually in FIFO order but on an MP system
7769  * it's possible for the completion routines to get out
7770  * of order. If that's a problem you need to add a global
7771  * mutex around the code that calls the completion routine
7772  * in the interrupt handler.
7773  */
7774 static void
7775 mptsas_doneq_add(mptsas_t *mpt, mptsas_cmd_t *cmd)
7776 {
7777 	struct scsi_pkt	*pkt = CMD2PKT(cmd);
7778 
7779 	NDBG31(("mptsas_doneq_add: cmd=0x%p", (void *)cmd));
7780 
7781 	ASSERT((cmd->cmd_flags & CFLAG_COMPLETED) == 0);
7782 	cmd->cmd_linkp = NULL;
7783 	cmd->cmd_flags |= CFLAG_FINISHED;
7784 	cmd->cmd_flags &= ~CFLAG_IN_TRANSPORT;
7785 
7786 	mptsas_fma_check(mpt, cmd);
7787 
7788 	/*
7789 	 * only add scsi pkts that have completion routines to
7790 	 * the doneq.  no intr cmds do not have callbacks.
7791 	 */
7792 	if (pkt && (pkt->pkt_comp)) {
7793 		*mpt->m_donetail = cmd;
7794 		mpt->m_donetail = &cmd->cmd_linkp;
7795 		mpt->m_doneq_len++;
7796 	}
7797 }
7798 
7799 static mptsas_cmd_t *
7800 mptsas_doneq_thread_rm(mptsas_t *mpt, uint64_t t)
7801 {
7802 	mptsas_cmd_t			*cmd;
7803 	mptsas_doneq_thread_list_t	*item = &mpt->m_doneq_thread_id[t];
7804 
7805 	/* pop one off the done queue */
7806 	if ((cmd = item->doneq) != NULL) {
7807 		/* if the queue is now empty fix the tail pointer */
7808 		NDBG31(("mptsas_doneq_thread_rm: cmd=0x%p", (void *)cmd));
7809 		if ((item->doneq = cmd->cmd_linkp) == NULL) {
7810 			item->donetail = &item->doneq;
7811 		}
7812 		cmd->cmd_linkp = NULL;
7813 		item->len--;
7814 	}
7815 	return (cmd);
7816 }
7817 
7818 static void
7819 mptsas_doneq_empty(mptsas_t *mpt)
7820 {
7821 	if (mpt->m_doneq && !mpt->m_in_callback) {
7822 		mptsas_cmd_t	*cmd, *next;
7823 		struct scsi_pkt *pkt;
7824 
7825 		mpt->m_in_callback = 1;
7826 		cmd = mpt->m_doneq;
7827 		mpt->m_doneq = NULL;
7828 		mpt->m_donetail = &mpt->m_doneq;
7829 		mpt->m_doneq_len = 0;
7830 
7831 		mutex_exit(&mpt->m_mutex);
7832 		/*
7833 		 * run the completion routines of all the
7834 		 * completed commands
7835 		 */
7836 		while (cmd != NULL) {
7837 			next = cmd->cmd_linkp;
7838 			cmd->cmd_linkp = NULL;
7839 			/* run this command's completion routine */
7840 			cmd->cmd_flags |= CFLAG_COMPLETED;
7841 			pkt = CMD2PKT(cmd);
7842 			mptsas_pkt_comp(pkt, cmd);
7843 			cmd = next;
7844 		}
7845 		mutex_enter(&mpt->m_mutex);
7846 		mpt->m_in_callback = 0;
7847 	}
7848 }
7849 
7850 /*
7851  * These routines manipulate the target's queue of pending requests
7852  */
7853 void
7854 mptsas_waitq_add(mptsas_t *mpt, mptsas_cmd_t *cmd)
7855 {
7856 	NDBG7(("mptsas_waitq_add: cmd=0x%p", (void *)cmd));
7857 	mptsas_target_t *ptgt = cmd->cmd_tgt_addr;
7858 	cmd->cmd_queued = TRUE;
7859 	if (ptgt)
7860 		ptgt->m_t_nwait++;
7861 	if (cmd->cmd_pkt_flags & FLAG_HEAD) {
7862 		if ((cmd->cmd_linkp = mpt->m_waitq) == NULL) {
7863 			mpt->m_waitqtail = &cmd->cmd_linkp;
7864 		}
7865 		mpt->m_waitq = cmd;
7866 	} else {
7867 		cmd->cmd_linkp = NULL;
7868 		*(mpt->m_waitqtail) = cmd;
7869 		mpt->m_waitqtail = &cmd->cmd_linkp;
7870 	}
7871 }
7872 
7873 static mptsas_cmd_t *
7874 mptsas_waitq_rm(mptsas_t *mpt)
7875 {
7876 	mptsas_cmd_t	*cmd;
7877 	mptsas_target_t *ptgt;
7878 	NDBG7(("mptsas_waitq_rm"));
7879 
7880 	MPTSAS_WAITQ_RM(mpt, cmd);
7881 
7882 	NDBG7(("mptsas_waitq_rm: cmd=0x%p", (void *)cmd));
7883 	if (cmd) {
7884 		ptgt = cmd->cmd_tgt_addr;
7885 		if (ptgt) {
7886 			ptgt->m_t_nwait--;
7887 			ASSERT(ptgt->m_t_nwait >= 0);
7888 		}
7889 	}
7890 	return (cmd);
7891 }
7892 
7893 /*
7894  * remove specified cmd from the middle of the wait queue.
7895  */
7896 static void
7897 mptsas_waitq_delete(mptsas_t *mpt, mptsas_cmd_t *cmd)
7898 {
7899 	mptsas_cmd_t	*prevp = mpt->m_waitq;
7900 	mptsas_target_t *ptgt = cmd->cmd_tgt_addr;
7901 
7902 	NDBG7(("mptsas_waitq_delete: mpt=0x%p cmd=0x%p",
7903 	    (void *)mpt, (void *)cmd));
7904 	if (ptgt) {
7905 		ptgt->m_t_nwait--;
7906 		ASSERT(ptgt->m_t_nwait >= 0);
7907 	}
7908 
7909 	if (prevp == cmd) {
7910 		if ((mpt->m_waitq = cmd->cmd_linkp) == NULL)
7911 			mpt->m_waitqtail = &mpt->m_waitq;
7912 
7913 		cmd->cmd_linkp = NULL;
7914 		cmd->cmd_queued = FALSE;
7915 		NDBG7(("mptsas_waitq_delete: mpt=0x%p cmd=0x%p",
7916 		    (void *)mpt, (void *)cmd));
7917 		return;
7918 	}
7919 
7920 	while (prevp != NULL) {
7921 		if (prevp->cmd_linkp == cmd) {
7922 			if ((prevp->cmd_linkp = cmd->cmd_linkp) == NULL)
7923 				mpt->m_waitqtail = &prevp->cmd_linkp;
7924 
7925 			cmd->cmd_linkp = NULL;
7926 			cmd->cmd_queued = FALSE;
7927 			NDBG7(("mptsas_waitq_delete: mpt=0x%p cmd=0x%p",
7928 			    (void *)mpt, (void *)cmd));
7929 			return;
7930 		}
7931 		prevp = prevp->cmd_linkp;
7932 	}
7933 	cmn_err(CE_PANIC, "mpt: mptsas_waitq_delete: queue botch");
7934 }
7935 
7936 static mptsas_cmd_t *
7937 mptsas_tx_waitq_rm(mptsas_t *mpt)
7938 {
7939 	mptsas_cmd_t *cmd;
7940 	NDBG7(("mptsas_tx_waitq_rm"));
7941 
7942 	MPTSAS_TX_WAITQ_RM(mpt, cmd);
7943 
7944 	NDBG7(("mptsas_tx_waitq_rm: cmd=0x%p", (void *)cmd));
7945 
7946 	return (cmd);
7947 }
7948 
7949 /*
7950  * remove specified cmd from the middle of the tx_waitq.
7951  */
7952 static void
7953 mptsas_tx_waitq_delete(mptsas_t *mpt, mptsas_cmd_t *cmd)
7954 {
7955 	mptsas_cmd_t *prevp = mpt->m_tx_waitq;
7956 
7957 	NDBG7(("mptsas_tx_waitq_delete: mpt=0x%p cmd=0x%p",
7958 	    (void *)mpt, (void *)cmd));
7959 
7960 	if (prevp == cmd) {
7961 		if ((mpt->m_tx_waitq = cmd->cmd_linkp) == NULL)
7962 			mpt->m_tx_waitqtail = &mpt->m_tx_waitq;
7963 
7964 		cmd->cmd_linkp = NULL;
7965 		cmd->cmd_queued = FALSE;
7966 		NDBG7(("mptsas_tx_waitq_delete: mpt=0x%p cmd=0x%p",
7967 		    (void *)mpt, (void *)cmd));
7968 		return;
7969 	}
7970 
7971 	while (prevp != NULL) {
7972 		if (prevp->cmd_linkp == cmd) {
7973 			if ((prevp->cmd_linkp = cmd->cmd_linkp) == NULL)
7974 				mpt->m_tx_waitqtail = &prevp->cmd_linkp;
7975 
7976 			cmd->cmd_linkp = NULL;
7977 			cmd->cmd_queued = FALSE;
7978 			NDBG7(("mptsas_tx_waitq_delete: mpt=0x%p cmd=0x%p",
7979 			    (void *)mpt, (void *)cmd));
7980 			return;
7981 		}
7982 		prevp = prevp->cmd_linkp;
7983 	}
7984 	cmn_err(CE_PANIC, "mpt: mptsas_tx_waitq_delete: queue botch");
7985 }
7986 
7987 /*
7988  * device and bus reset handling
7989  *
7990  * Notes:
7991  *	- RESET_ALL:	reset the controller
7992  *	- RESET_TARGET:	reset the target specified in scsi_address
7993  */
7994 static int
7995 mptsas_scsi_reset(struct scsi_address *ap, int level)
7996 {
7997 	mptsas_t		*mpt = ADDR2MPT(ap);
7998 	int			rval;
7999 	mptsas_tgt_private_t	*tgt_private;
8000 	mptsas_target_t		*ptgt = NULL;
8001 
8002 	tgt_private = (mptsas_tgt_private_t *)ap->a_hba_tran->tran_tgt_private;
8003 	ptgt = tgt_private->t_private;
8004 	if (ptgt == NULL) {
8005 		return (FALSE);
8006 	}
8007 	NDBG22(("mptsas_scsi_reset: target=%d level=%d", ptgt->m_devhdl,
8008 	    level));
8009 
8010 	mutex_enter(&mpt->m_mutex);
8011 	/*
8012 	 * if we are not in panic set up a reset delay for this target
8013 	 */
8014 	if (!ddi_in_panic()) {
8015 		mptsas_setup_bus_reset_delay(mpt);
8016 	} else {
8017 		drv_usecwait(mpt->m_scsi_reset_delay * 1000);
8018 	}
8019 	rval = mptsas_do_scsi_reset(mpt, ptgt->m_devhdl);
8020 	mutex_exit(&mpt->m_mutex);
8021 
8022 	/*
8023 	 * The transport layer expect to only see TRUE and
8024 	 * FALSE. Therefore, we will adjust the return value
8025 	 * if mptsas_do_scsi_reset returns FAILED.
8026 	 */
8027 	if (rval == FAILED)
8028 		rval = FALSE;
8029 	return (rval);
8030 }
8031 
8032 static int
8033 mptsas_do_scsi_reset(mptsas_t *mpt, uint16_t devhdl)
8034 {
8035 	int		rval = FALSE;
8036 	uint8_t		config, disk;
8037 	mptsas_slots_t	*slots = mpt->m_active;
8038 
8039 	ASSERT(mutex_owned(&mpt->m_mutex));
8040 
8041 	if (mptsas_debug_resets) {
8042 		mptsas_log(mpt, CE_WARN, "mptsas_do_scsi_reset: target=%d",
8043 		    devhdl);
8044 	}
8045 
8046 	/*
8047 	 * Issue a Target Reset message to the target specified but not to a
8048 	 * disk making up a raid volume.  Just look through the RAID config
8049 	 * Phys Disk list of DevHandles.  If the target's DevHandle is in this
8050 	 * list, then don't reset this target.
8051 	 */
8052 	for (config = 0; config < slots->m_num_raid_configs; config++) {
8053 		for (disk = 0; disk < MPTSAS_MAX_DISKS_IN_CONFIG; disk++) {
8054 			if (devhdl == slots->m_raidconfig[config].
8055 			    m_physdisk_devhdl[disk]) {
8056 				return (TRUE);
8057 			}
8058 		}
8059 	}
8060 
8061 	rval = mptsas_ioc_task_management(mpt,
8062 	    MPI2_SCSITASKMGMT_TASKTYPE_TARGET_RESET, devhdl, 0);
8063 
8064 	mptsas_doneq_empty(mpt);
8065 	return (rval);
8066 }
8067 
8068 static int
8069 mptsas_scsi_reset_notify(struct scsi_address *ap, int flag,
8070 	void (*callback)(caddr_t), caddr_t arg)
8071 {
8072 	mptsas_t	*mpt = ADDR2MPT(ap);
8073 
8074 	NDBG22(("mptsas_scsi_reset_notify: tgt=%d", ap->a_target));
8075 
8076 	return (scsi_hba_reset_notify_setup(ap, flag, callback, arg,
8077 	    &mpt->m_mutex, &mpt->m_reset_notify_listf));
8078 }
8079 
8080 static int
8081 mptsas_get_name(struct scsi_device *sd, char *name, int len)
8082 {
8083 	dev_info_t	*lun_dip = NULL;
8084 
8085 	ASSERT(sd != NULL);
8086 	ASSERT(name != NULL);
8087 	lun_dip = sd->sd_dev;
8088 	ASSERT(lun_dip != NULL);
8089 
8090 	if (mptsas_name_child(lun_dip, name, len) == DDI_SUCCESS) {
8091 		return (1);
8092 	} else {
8093 		return (0);
8094 	}
8095 }
8096 
8097 static int
8098 mptsas_get_bus_addr(struct scsi_device *sd, char *name, int len)
8099 {
8100 	return (mptsas_get_name(sd, name, len));
8101 }
8102 
8103 void
8104 mptsas_set_throttle(mptsas_t *mpt, mptsas_target_t *ptgt, int what)
8105 {
8106 
8107 	NDBG25(("mptsas_set_throttle: throttle=%x", what));
8108 
8109 	/*
8110 	 * if the bus is draining/quiesced, no changes to the throttles
8111 	 * are allowed. Not allowing change of throttles during draining
8112 	 * limits error recovery but will reduce draining time
8113 	 *
8114 	 * all throttles should have been set to HOLD_THROTTLE
8115 	 */
8116 	if (mpt->m_softstate & (MPTSAS_SS_QUIESCED | MPTSAS_SS_DRAINING)) {
8117 		return;
8118 	}
8119 
8120 	if (what == HOLD_THROTTLE) {
8121 		ptgt->m_t_throttle = HOLD_THROTTLE;
8122 	} else if (ptgt->m_reset_delay == 0) {
8123 		ptgt->m_t_throttle = what;
8124 	}
8125 }
8126 
8127 /*
8128  * Clean up from a device reset.
8129  * For the case of target reset, this function clears the waitq of all
8130  * commands for a particular target.   For the case of abort task set, this
8131  * function clears the waitq of all commonds for a particular target/lun.
8132  */
8133 static void
8134 mptsas_flush_target(mptsas_t *mpt, ushort_t target, int lun, uint8_t tasktype)
8135 {
8136 	mptsas_slots_t	*slots = mpt->m_active;
8137 	mptsas_cmd_t	*cmd, *next_cmd;
8138 	int		slot;
8139 	uchar_t		reason;
8140 	uint_t		stat;
8141 
8142 	NDBG25(("mptsas_flush_target: target=%d lun=%d", target, lun));
8143 
8144 	/*
8145 	 * Make sure the I/O Controller has flushed all cmds
8146 	 * that are associated with this target for a target reset
8147 	 * and target/lun for abort task set.
8148 	 * Account for TM requests, which use the last SMID.
8149 	 */
8150 	for (slot = 0; slot <= mpt->m_active->m_n_slots; slot++) {
8151 		if ((cmd = slots->m_slot[slot]) == NULL)
8152 			continue;
8153 		reason = CMD_RESET;
8154 		stat = STAT_DEV_RESET;
8155 		switch (tasktype) {
8156 		case MPI2_SCSITASKMGMT_TASKTYPE_TARGET_RESET:
8157 			if (Tgt(cmd) == target) {
8158 				mptsas_log(mpt, CE_NOTE, "mptsas_flush_target "
8159 				    "discovered non-NULL cmd in slot %d, "
8160 				    "tasktype 0x%x", slot, tasktype);
8161 				mptsas_dump_cmd(mpt, cmd);
8162 				mptsas_remove_cmd(mpt, cmd);
8163 				mptsas_set_pkt_reason(mpt, cmd, reason, stat);
8164 				mptsas_doneq_add(mpt, cmd);
8165 			}
8166 			break;
8167 		case MPI2_SCSITASKMGMT_TASKTYPE_ABRT_TASK_SET:
8168 			reason = CMD_ABORTED;
8169 			stat = STAT_ABORTED;
8170 			/*FALLTHROUGH*/
8171 		case MPI2_SCSITASKMGMT_TASKTYPE_LOGICAL_UNIT_RESET:
8172 			if ((Tgt(cmd) == target) && (Lun(cmd) == lun)) {
8173 
8174 				mptsas_log(mpt, CE_NOTE, "mptsas_flush_target "
8175 				    "discovered non-NULL cmd in slot %d, "
8176 				    "tasktype 0x%x", slot, tasktype);
8177 				mptsas_dump_cmd(mpt, cmd);
8178 				mptsas_remove_cmd(mpt, cmd);
8179 				mptsas_set_pkt_reason(mpt, cmd, reason,
8180 				    stat);
8181 				mptsas_doneq_add(mpt, cmd);
8182 			}
8183 			break;
8184 		default:
8185 			break;
8186 		}
8187 	}
8188 
8189 	/*
8190 	 * Flush the waitq and tx_waitq of this target's cmds
8191 	 */
8192 	cmd = mpt->m_waitq;
8193 
8194 	reason = CMD_RESET;
8195 	stat = STAT_DEV_RESET;
8196 
8197 	switch (tasktype) {
8198 	case MPI2_SCSITASKMGMT_TASKTYPE_TARGET_RESET:
8199 		while (cmd != NULL) {
8200 			next_cmd = cmd->cmd_linkp;
8201 			if (Tgt(cmd) == target) {
8202 				mptsas_waitq_delete(mpt, cmd);
8203 				mptsas_set_pkt_reason(mpt, cmd,
8204 				    reason, stat);
8205 				mptsas_doneq_add(mpt, cmd);
8206 			}
8207 			cmd = next_cmd;
8208 		}
8209 		mutex_enter(&mpt->m_tx_waitq_mutex);
8210 		cmd = mpt->m_tx_waitq;
8211 		while (cmd != NULL) {
8212 			next_cmd = cmd->cmd_linkp;
8213 			if (Tgt(cmd) == target) {
8214 				mptsas_tx_waitq_delete(mpt, cmd);
8215 				mutex_exit(&mpt->m_tx_waitq_mutex);
8216 				mptsas_set_pkt_reason(mpt, cmd,
8217 				    reason, stat);
8218 				mptsas_doneq_add(mpt, cmd);
8219 				mutex_enter(&mpt->m_tx_waitq_mutex);
8220 			}
8221 			cmd = next_cmd;
8222 		}
8223 		mutex_exit(&mpt->m_tx_waitq_mutex);
8224 		break;
8225 	case MPI2_SCSITASKMGMT_TASKTYPE_ABRT_TASK_SET:
8226 		reason = CMD_ABORTED;
8227 		stat =  STAT_ABORTED;
8228 		/*FALLTHROUGH*/
8229 	case MPI2_SCSITASKMGMT_TASKTYPE_LOGICAL_UNIT_RESET:
8230 		while (cmd != NULL) {
8231 			next_cmd = cmd->cmd_linkp;
8232 			if ((Tgt(cmd) == target) && (Lun(cmd) == lun)) {
8233 				mptsas_waitq_delete(mpt, cmd);
8234 				mptsas_set_pkt_reason(mpt, cmd,
8235 				    reason, stat);
8236 				mptsas_doneq_add(mpt, cmd);
8237 			}
8238 			cmd = next_cmd;
8239 		}
8240 		mutex_enter(&mpt->m_tx_waitq_mutex);
8241 		cmd = mpt->m_tx_waitq;
8242 		while (cmd != NULL) {
8243 			next_cmd = cmd->cmd_linkp;
8244 			if ((Tgt(cmd) == target) && (Lun(cmd) == lun)) {
8245 				mptsas_tx_waitq_delete(mpt, cmd);
8246 				mutex_exit(&mpt->m_tx_waitq_mutex);
8247 				mptsas_set_pkt_reason(mpt, cmd,
8248 				    reason, stat);
8249 				mptsas_doneq_add(mpt, cmd);
8250 				mutex_enter(&mpt->m_tx_waitq_mutex);
8251 			}
8252 			cmd = next_cmd;
8253 		}
8254 		mutex_exit(&mpt->m_tx_waitq_mutex);
8255 		break;
8256 	default:
8257 		mptsas_log(mpt, CE_WARN, "Unknown task management type %d.",
8258 		    tasktype);
8259 		break;
8260 	}
8261 }
8262 
8263 /*
8264  * Clean up hba state, abort all outstanding command and commands in waitq
8265  * reset timeout of all targets.
8266  */
8267 static void
8268 mptsas_flush_hba(mptsas_t *mpt)
8269 {
8270 	mptsas_slots_t	*slots = mpt->m_active;
8271 	mptsas_cmd_t	*cmd;
8272 	int		slot;
8273 
8274 	NDBG25(("mptsas_flush_hba"));
8275 
8276 	/*
8277 	 * The I/O Controller should have already sent back
8278 	 * all commands via the scsi I/O reply frame.  Make
8279 	 * sure all commands have been flushed.
8280 	 * Account for TM request, which use the last SMID.
8281 	 */
8282 	for (slot = 0; slot <= mpt->m_active->m_n_slots; slot++) {
8283 		if ((cmd = slots->m_slot[slot]) == NULL)
8284 			continue;
8285 
8286 		if (cmd->cmd_flags & CFLAG_CMDIOC)
8287 			continue;
8288 
8289 		mptsas_log(mpt, CE_NOTE, "mptsas_flush_hba discovered non-NULL "
8290 		    "cmd in slot %d", slot);
8291 		mptsas_dump_cmd(mpt, cmd);
8292 
8293 		mptsas_remove_cmd(mpt, cmd);
8294 		mptsas_set_pkt_reason(mpt, cmd, CMD_RESET, STAT_BUS_RESET);
8295 		mptsas_doneq_add(mpt, cmd);
8296 	}
8297 
8298 	/*
8299 	 * Flush the waitq.
8300 	 */
8301 	while ((cmd = mptsas_waitq_rm(mpt)) != NULL) {
8302 		mptsas_set_pkt_reason(mpt, cmd, CMD_RESET, STAT_BUS_RESET);
8303 		if ((cmd->cmd_flags & CFLAG_PASSTHRU) ||
8304 		    (cmd->cmd_flags & CFLAG_CONFIG)) {
8305 			cmd->cmd_flags |= CFLAG_FINISHED;
8306 			cv_broadcast(&mpt->m_passthru_cv);
8307 			cv_broadcast(&mpt->m_config_cv);
8308 		} else {
8309 			mptsas_doneq_add(mpt, cmd);
8310 		}
8311 	}
8312 
8313 	/*
8314 	 * Flush the tx_waitq
8315 	 */
8316 	mutex_enter(&mpt->m_tx_waitq_mutex);
8317 	while ((cmd = mptsas_tx_waitq_rm(mpt)) != NULL) {
8318 		mutex_exit(&mpt->m_tx_waitq_mutex);
8319 		mptsas_set_pkt_reason(mpt, cmd, CMD_RESET, STAT_BUS_RESET);
8320 		mptsas_doneq_add(mpt, cmd);
8321 		mutex_enter(&mpt->m_tx_waitq_mutex);
8322 	}
8323 	mutex_exit(&mpt->m_tx_waitq_mutex);
8324 }
8325 
8326 /*
8327  * set pkt_reason and OR in pkt_statistics flag
8328  */
8329 static void
8330 mptsas_set_pkt_reason(mptsas_t *mpt, mptsas_cmd_t *cmd, uchar_t reason,
8331     uint_t stat)
8332 {
8333 #ifndef __lock_lint
8334 	_NOTE(ARGUNUSED(mpt))
8335 #endif
8336 
8337 	NDBG25(("mptsas_set_pkt_reason: cmd=0x%p reason=%x stat=%x",
8338 	    (void *)cmd, reason, stat));
8339 
8340 	if (cmd) {
8341 		if (cmd->cmd_pkt->pkt_reason == CMD_CMPLT) {
8342 			cmd->cmd_pkt->pkt_reason = reason;
8343 		}
8344 		cmd->cmd_pkt->pkt_statistics |= stat;
8345 	}
8346 }
8347 
8348 static void
8349 mptsas_start_watch_reset_delay()
8350 {
8351 	NDBG22(("mptsas_start_watch_reset_delay"));
8352 
8353 	mutex_enter(&mptsas_global_mutex);
8354 	if (mptsas_reset_watch == NULL && mptsas_timeouts_enabled) {
8355 		mptsas_reset_watch = timeout(mptsas_watch_reset_delay, NULL,
8356 		    drv_usectohz((clock_t)
8357 		    MPTSAS_WATCH_RESET_DELAY_TICK * 1000));
8358 		ASSERT(mptsas_reset_watch != NULL);
8359 	}
8360 	mutex_exit(&mptsas_global_mutex);
8361 }
8362 
8363 static void
8364 mptsas_setup_bus_reset_delay(mptsas_t *mpt)
8365 {
8366 	mptsas_target_t	*ptgt = NULL;
8367 
8368 	NDBG22(("mptsas_setup_bus_reset_delay"));
8369 	ptgt = (mptsas_target_t *)mptsas_hash_traverse(&mpt->m_active->m_tgttbl,
8370 	    MPTSAS_HASH_FIRST);
8371 	while (ptgt != NULL) {
8372 		mptsas_set_throttle(mpt, ptgt, HOLD_THROTTLE);
8373 		ptgt->m_reset_delay = mpt->m_scsi_reset_delay;
8374 
8375 		ptgt = (mptsas_target_t *)mptsas_hash_traverse(
8376 		    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
8377 	}
8378 
8379 	mptsas_start_watch_reset_delay();
8380 }
8381 
8382 /*
8383  * mptsas_watch_reset_delay(_subr) is invoked by timeout() and checks every
8384  * mpt instance for active reset delays
8385  */
8386 static void
8387 mptsas_watch_reset_delay(void *arg)
8388 {
8389 #ifndef __lock_lint
8390 	_NOTE(ARGUNUSED(arg))
8391 #endif
8392 
8393 	mptsas_t	*mpt;
8394 	int		not_done = 0;
8395 
8396 	NDBG22(("mptsas_watch_reset_delay"));
8397 
8398 	mutex_enter(&mptsas_global_mutex);
8399 	mptsas_reset_watch = 0;
8400 	mutex_exit(&mptsas_global_mutex);
8401 	rw_enter(&mptsas_global_rwlock, RW_READER);
8402 	for (mpt = mptsas_head; mpt != NULL; mpt = mpt->m_next) {
8403 		if (mpt->m_tran == 0) {
8404 			continue;
8405 		}
8406 		mutex_enter(&mpt->m_mutex);
8407 		not_done += mptsas_watch_reset_delay_subr(mpt);
8408 		mutex_exit(&mpt->m_mutex);
8409 	}
8410 	rw_exit(&mptsas_global_rwlock);
8411 
8412 	if (not_done) {
8413 		mptsas_start_watch_reset_delay();
8414 	}
8415 }
8416 
8417 static int
8418 mptsas_watch_reset_delay_subr(mptsas_t *mpt)
8419 {
8420 	int		done = 0;
8421 	int		restart = 0;
8422 	mptsas_target_t	*ptgt = NULL;
8423 
8424 	NDBG22(("mptsas_watch_reset_delay_subr: mpt=0x%p", (void *)mpt));
8425 
8426 	ASSERT(mutex_owned(&mpt->m_mutex));
8427 
8428 	ptgt = (mptsas_target_t *)mptsas_hash_traverse(&mpt->m_active->m_tgttbl,
8429 	    MPTSAS_HASH_FIRST);
8430 	while (ptgt != NULL) {
8431 		if (ptgt->m_reset_delay != 0) {
8432 			ptgt->m_reset_delay -=
8433 			    MPTSAS_WATCH_RESET_DELAY_TICK;
8434 			if (ptgt->m_reset_delay <= 0) {
8435 				ptgt->m_reset_delay = 0;
8436 				mptsas_set_throttle(mpt, ptgt,
8437 				    MAX_THROTTLE);
8438 				restart++;
8439 			} else {
8440 				done = -1;
8441 			}
8442 		}
8443 
8444 		ptgt = (mptsas_target_t *)mptsas_hash_traverse(
8445 		    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
8446 	}
8447 
8448 	if (restart > 0) {
8449 		mptsas_restart_hba(mpt);
8450 	}
8451 	return (done);
8452 }
8453 
8454 #ifdef MPTSAS_TEST
8455 static void
8456 mptsas_test_reset(mptsas_t *mpt, int target)
8457 {
8458 	mptsas_target_t    *ptgt = NULL;
8459 
8460 	if (mptsas_rtest == target) {
8461 		if (mptsas_do_scsi_reset(mpt, target) == TRUE) {
8462 			mptsas_rtest = -1;
8463 		}
8464 		if (mptsas_rtest == -1) {
8465 			NDBG22(("mptsas_test_reset success"));
8466 		}
8467 	}
8468 }
8469 #endif
8470 
8471 /*
8472  * abort handling:
8473  *
8474  * Notes:
8475  *	- if pkt is not NULL, abort just that command
8476  *	- if pkt is NULL, abort all outstanding commands for target
8477  */
8478 static int
8479 mptsas_scsi_abort(struct scsi_address *ap, struct scsi_pkt *pkt)
8480 {
8481 	mptsas_t		*mpt = ADDR2MPT(ap);
8482 	int			rval;
8483 	mptsas_tgt_private_t	*tgt_private;
8484 	int			target, lun;
8485 
8486 	tgt_private = (mptsas_tgt_private_t *)ap->a_hba_tran->
8487 	    tran_tgt_private;
8488 	ASSERT(tgt_private != NULL);
8489 	target = tgt_private->t_private->m_devhdl;
8490 	lun = tgt_private->t_lun;
8491 
8492 	NDBG23(("mptsas_scsi_abort: target=%d.%d", target, lun));
8493 
8494 	mutex_enter(&mpt->m_mutex);
8495 	rval = mptsas_do_scsi_abort(mpt, target, lun, pkt);
8496 	mutex_exit(&mpt->m_mutex);
8497 	return (rval);
8498 }
8499 
8500 static int
8501 mptsas_do_scsi_abort(mptsas_t *mpt, int target, int lun, struct scsi_pkt *pkt)
8502 {
8503 	mptsas_cmd_t	*sp = NULL;
8504 	mptsas_slots_t	*slots = mpt->m_active;
8505 	int		rval = FALSE;
8506 
8507 	ASSERT(mutex_owned(&mpt->m_mutex));
8508 
8509 	/*
8510 	 * Abort the command pkt on the target/lun in ap.  If pkt is
8511 	 * NULL, abort all outstanding commands on that target/lun.
8512 	 * If you can abort them, return 1, else return 0.
8513 	 * Each packet that's aborted should be sent back to the target
8514 	 * driver through the callback routine, with pkt_reason set to
8515 	 * CMD_ABORTED.
8516 	 *
8517 	 * abort cmd pkt on HBA hardware; clean out of outstanding
8518 	 * command lists, etc.
8519 	 */
8520 	if (pkt != NULL) {
8521 		/* abort the specified packet */
8522 		sp = PKT2CMD(pkt);
8523 
8524 		if (sp->cmd_queued) {
8525 			NDBG23(("mptsas_do_scsi_abort: queued sp=0x%p aborted",
8526 			    (void *)sp));
8527 			mptsas_waitq_delete(mpt, sp);
8528 			mptsas_set_pkt_reason(mpt, sp, CMD_ABORTED,
8529 			    STAT_ABORTED);
8530 			mptsas_doneq_add(mpt, sp);
8531 			rval = TRUE;
8532 			goto done;
8533 		}
8534 
8535 		/*
8536 		 * Have mpt firmware abort this command
8537 		 */
8538 
8539 		if (slots->m_slot[sp->cmd_slot] != NULL) {
8540 			rval = mptsas_ioc_task_management(mpt,
8541 			    MPI2_SCSITASKMGMT_TASKTYPE_ABORT_TASK, target,
8542 			    lun);
8543 
8544 			/*
8545 			 * The transport layer expects only TRUE and FALSE.
8546 			 * Therefore, if mptsas_ioc_task_management returns
8547 			 * FAILED we will return FALSE.
8548 			 */
8549 			if (rval == FAILED)
8550 				rval = FALSE;
8551 			goto done;
8552 		}
8553 	}
8554 
8555 	/*
8556 	 * If pkt is NULL then abort task set
8557 	 */
8558 	rval = mptsas_ioc_task_management(mpt,
8559 	    MPI2_SCSITASKMGMT_TASKTYPE_ABRT_TASK_SET, target, lun);
8560 
8561 	/*
8562 	 * The transport layer expects only TRUE and FALSE.
8563 	 * Therefore, if mptsas_ioc_task_management returns
8564 	 * FAILED we will return FALSE.
8565 	 */
8566 	if (rval == FAILED)
8567 		rval = FALSE;
8568 
8569 #ifdef MPTSAS_TEST
8570 	if (rval && mptsas_test_stop) {
8571 		debug_enter("mptsas_do_scsi_abort");
8572 	}
8573 #endif
8574 
8575 done:
8576 	mptsas_doneq_empty(mpt);
8577 	return (rval);
8578 }
8579 
8580 /*
8581  * capability handling:
8582  * (*tran_getcap).  Get the capability named, and return its value.
8583  */
8584 static int
8585 mptsas_scsi_getcap(struct scsi_address *ap, char *cap, int tgtonly)
8586 {
8587 	mptsas_t	*mpt = ADDR2MPT(ap);
8588 	int		ckey;
8589 	int		rval = FALSE;
8590 
8591 	NDBG24(("mptsas_scsi_getcap: target=%d, cap=%s tgtonly=%x",
8592 	    ap->a_target, cap, tgtonly));
8593 
8594 	mutex_enter(&mpt->m_mutex);
8595 
8596 	if ((mptsas_capchk(cap, tgtonly, &ckey)) != TRUE) {
8597 		mutex_exit(&mpt->m_mutex);
8598 		return (UNDEFINED);
8599 	}
8600 
8601 	switch (ckey) {
8602 	case SCSI_CAP_DMA_MAX:
8603 		rval = (int)mpt->m_msg_dma_attr.dma_attr_maxxfer;
8604 		break;
8605 	case SCSI_CAP_ARQ:
8606 		rval = TRUE;
8607 		break;
8608 	case SCSI_CAP_MSG_OUT:
8609 	case SCSI_CAP_PARITY:
8610 	case SCSI_CAP_UNTAGGED_QING:
8611 		rval = TRUE;
8612 		break;
8613 	case SCSI_CAP_TAGGED_QING:
8614 		rval = TRUE;
8615 		break;
8616 	case SCSI_CAP_RESET_NOTIFICATION:
8617 		rval = TRUE;
8618 		break;
8619 	case SCSI_CAP_LINKED_CMDS:
8620 		rval = FALSE;
8621 		break;
8622 	case SCSI_CAP_QFULL_RETRIES:
8623 		rval = ((mptsas_tgt_private_t *)(ap->a_hba_tran->
8624 		    tran_tgt_private))->t_private->m_qfull_retries;
8625 		break;
8626 	case SCSI_CAP_QFULL_RETRY_INTERVAL:
8627 		rval = drv_hztousec(((mptsas_tgt_private_t *)
8628 		    (ap->a_hba_tran->tran_tgt_private))->
8629 		    t_private->m_qfull_retry_interval) / 1000;
8630 		break;
8631 	case SCSI_CAP_CDB_LEN:
8632 		rval = CDB_GROUP4;
8633 		break;
8634 	case SCSI_CAP_INTERCONNECT_TYPE:
8635 		rval = INTERCONNECT_SAS;
8636 		break;
8637 	case SCSI_CAP_TRAN_LAYER_RETRIES:
8638 		if (mpt->m_ioc_capabilities &
8639 		    MPI2_IOCFACTS_CAPABILITY_TLR)
8640 			rval = TRUE;
8641 		else
8642 			rval = FALSE;
8643 		break;
8644 	default:
8645 		rval = UNDEFINED;
8646 		break;
8647 	}
8648 
8649 	NDBG24(("mptsas_scsi_getcap: %s, rval=%x", cap, rval));
8650 
8651 	mutex_exit(&mpt->m_mutex);
8652 	return (rval);
8653 }
8654 
8655 /*
8656  * (*tran_setcap).  Set the capability named to the value given.
8657  */
8658 static int
8659 mptsas_scsi_setcap(struct scsi_address *ap, char *cap, int value, int tgtonly)
8660 {
8661 	mptsas_t	*mpt = ADDR2MPT(ap);
8662 	int		ckey;
8663 	int		rval = FALSE;
8664 
8665 	NDBG24(("mptsas_scsi_setcap: target=%d, cap=%s value=%x tgtonly=%x",
8666 	    ap->a_target, cap, value, tgtonly));
8667 
8668 	if (!tgtonly) {
8669 		return (rval);
8670 	}
8671 
8672 	mutex_enter(&mpt->m_mutex);
8673 
8674 	if ((mptsas_capchk(cap, tgtonly, &ckey)) != TRUE) {
8675 		mutex_exit(&mpt->m_mutex);
8676 		return (UNDEFINED);
8677 	}
8678 
8679 	switch (ckey) {
8680 	case SCSI_CAP_DMA_MAX:
8681 	case SCSI_CAP_MSG_OUT:
8682 	case SCSI_CAP_PARITY:
8683 	case SCSI_CAP_INITIATOR_ID:
8684 	case SCSI_CAP_LINKED_CMDS:
8685 	case SCSI_CAP_UNTAGGED_QING:
8686 	case SCSI_CAP_RESET_NOTIFICATION:
8687 		/*
8688 		 * None of these are settable via
8689 		 * the capability interface.
8690 		 */
8691 		break;
8692 	case SCSI_CAP_ARQ:
8693 		/*
8694 		 * We cannot turn off arq so return false if asked to
8695 		 */
8696 		if (value) {
8697 			rval = TRUE;
8698 		} else {
8699 			rval = FALSE;
8700 		}
8701 		break;
8702 	case SCSI_CAP_TAGGED_QING:
8703 		mptsas_set_throttle(mpt, ((mptsas_tgt_private_t *)
8704 		    (ap->a_hba_tran->tran_tgt_private))->t_private,
8705 		    MAX_THROTTLE);
8706 		rval = TRUE;
8707 		break;
8708 	case SCSI_CAP_QFULL_RETRIES:
8709 		((mptsas_tgt_private_t *)(ap->a_hba_tran->tran_tgt_private))->
8710 		    t_private->m_qfull_retries = (uchar_t)value;
8711 		rval = TRUE;
8712 		break;
8713 	case SCSI_CAP_QFULL_RETRY_INTERVAL:
8714 		((mptsas_tgt_private_t *)(ap->a_hba_tran->tran_tgt_private))->
8715 		    t_private->m_qfull_retry_interval =
8716 		    drv_usectohz(value * 1000);
8717 		rval = TRUE;
8718 		break;
8719 	default:
8720 		rval = UNDEFINED;
8721 		break;
8722 	}
8723 	mutex_exit(&mpt->m_mutex);
8724 	return (rval);
8725 }
8726 
8727 /*
8728  * Utility routine for mptsas_ifsetcap/ifgetcap
8729  */
8730 /*ARGSUSED*/
8731 static int
8732 mptsas_capchk(char *cap, int tgtonly, int *cidxp)
8733 {
8734 	NDBG24(("mptsas_capchk: cap=%s", cap));
8735 
8736 	if (!cap)
8737 		return (FALSE);
8738 
8739 	*cidxp = scsi_hba_lookup_capstr(cap);
8740 	return (TRUE);
8741 }
8742 
8743 static int
8744 mptsas_alloc_active_slots(mptsas_t *mpt, int flag)
8745 {
8746 	mptsas_slots_t	*old_active = mpt->m_active;
8747 	mptsas_slots_t	*new_active;
8748 	size_t		size;
8749 	int		rval = -1;
8750 
8751 	if (mpt->m_ncmds) {
8752 		NDBG9(("cannot change size of active slots array"));
8753 		return (rval);
8754 	}
8755 
8756 	size = MPTSAS_SLOTS_SIZE(mpt);
8757 	new_active = kmem_zalloc(size, flag);
8758 	if (new_active == NULL) {
8759 		NDBG1(("new active alloc failed"));
8760 	} else {
8761 		/*
8762 		 * Since SMID 0 is reserved and the TM slot is reserved, the
8763 		 * number of slots that can be used at any one time is
8764 		 * m_max_requests - 2.
8765 		 */
8766 		mpt->m_active = new_active;
8767 		mpt->m_active->m_n_slots = (mpt->m_max_requests - 2);
8768 		mpt->m_active->m_size = size;
8769 		mpt->m_active->m_tags = 1;
8770 		if (old_active) {
8771 			kmem_free(old_active, old_active->m_size);
8772 		}
8773 		rval = 0;
8774 	}
8775 
8776 	return (rval);
8777 }
8778 
8779 /*
8780  * Error logging, printing, and debug print routines.
8781  */
8782 static char *mptsas_label = "mpt_sas";
8783 
8784 /*PRINTFLIKE3*/
8785 void
8786 mptsas_log(mptsas_t *mpt, int level, char *fmt, ...)
8787 {
8788 	dev_info_t	*dev;
8789 	va_list		ap;
8790 
8791 	if (mpt) {
8792 		dev = mpt->m_dip;
8793 	} else {
8794 		dev = 0;
8795 	}
8796 
8797 	mutex_enter(&mptsas_log_mutex);
8798 
8799 	va_start(ap, fmt);
8800 	(void) vsprintf(mptsas_log_buf, fmt, ap);
8801 	va_end(ap);
8802 
8803 	if (level == CE_CONT) {
8804 		scsi_log(dev, mptsas_label, level, "%s\n", mptsas_log_buf);
8805 	} else {
8806 		scsi_log(dev, mptsas_label, level, "%s", mptsas_log_buf);
8807 	}
8808 
8809 	mutex_exit(&mptsas_log_mutex);
8810 }
8811 
8812 #ifdef MPTSAS_DEBUG
8813 /*PRINTFLIKE1*/
8814 void
8815 mptsas_printf(char *fmt, ...)
8816 {
8817 	dev_info_t	*dev = 0;
8818 	va_list		ap;
8819 
8820 	mutex_enter(&mptsas_log_mutex);
8821 
8822 	va_start(ap, fmt);
8823 	(void) vsprintf(mptsas_log_buf, fmt, ap);
8824 	va_end(ap);
8825 
8826 #ifdef PROM_PRINTF
8827 	prom_printf("%s:\t%s\n", mptsas_label, mptsas_log_buf);
8828 #else
8829 	scsi_log(dev, mptsas_label, SCSI_DEBUG, "%s\n", mptsas_log_buf);
8830 #endif
8831 	mutex_exit(&mptsas_log_mutex);
8832 }
8833 #endif
8834 
8835 /*
8836  * timeout handling
8837  */
8838 static void
8839 mptsas_watch(void *arg)
8840 {
8841 #ifndef __lock_lint
8842 	_NOTE(ARGUNUSED(arg))
8843 #endif
8844 
8845 	mptsas_t	*mpt;
8846 
8847 	NDBG30(("mptsas_watch"));
8848 
8849 	rw_enter(&mptsas_global_rwlock, RW_READER);
8850 	for (mpt = mptsas_head; mpt != (mptsas_t *)NULL; mpt = mpt->m_next) {
8851 
8852 		mutex_enter(&mpt->m_mutex);
8853 
8854 		/* Skip device if not powered on */
8855 		if (mpt->m_options & MPTSAS_OPT_PM) {
8856 			if (mpt->m_power_level == PM_LEVEL_D0) {
8857 				(void) pm_busy_component(mpt->m_dip, 0);
8858 				mpt->m_busy = 1;
8859 			} else {
8860 				mutex_exit(&mpt->m_mutex);
8861 				continue;
8862 			}
8863 		}
8864 
8865 		/*
8866 		 * For now, always call mptsas_watchsubr.
8867 		 */
8868 		mptsas_watchsubr(mpt);
8869 
8870 		if (mpt->m_options & MPTSAS_OPT_PM) {
8871 			mpt->m_busy = 0;
8872 			(void) pm_idle_component(mpt->m_dip, 0);
8873 		}
8874 
8875 		mutex_exit(&mpt->m_mutex);
8876 	}
8877 	rw_exit(&mptsas_global_rwlock);
8878 
8879 	mutex_enter(&mptsas_global_mutex);
8880 	if (mptsas_timeouts_enabled)
8881 		mptsas_timeout_id = timeout(mptsas_watch, NULL, mptsas_tick);
8882 	mutex_exit(&mptsas_global_mutex);
8883 }
8884 
8885 static void
8886 mptsas_watchsubr(mptsas_t *mpt)
8887 {
8888 	int		i;
8889 	mptsas_cmd_t	*cmd;
8890 	mptsas_target_t	*ptgt = NULL;
8891 
8892 	NDBG30(("mptsas_watchsubr: mpt=0x%p", (void *)mpt));
8893 
8894 #ifdef MPTSAS_TEST
8895 	if (mptsas_enable_untagged) {
8896 		mptsas_test_untagged++;
8897 	}
8898 #endif
8899 
8900 	/*
8901 	 * Check for commands stuck in active slot
8902 	 * Account for TM requests, which use the last SMID.
8903 	 */
8904 	for (i = 0; i <= mpt->m_active->m_n_slots; i++) {
8905 		if ((cmd = mpt->m_active->m_slot[i]) != NULL) {
8906 			if ((cmd->cmd_flags & CFLAG_CMDIOC) == 0) {
8907 				cmd->cmd_active_timeout -=
8908 				    mptsas_scsi_watchdog_tick;
8909 				if (cmd->cmd_active_timeout <= 0) {
8910 					/*
8911 					 * There seems to be a command stuck
8912 					 * in the active slot.  Drain throttle.
8913 					 */
8914 					mptsas_set_throttle(mpt,
8915 					    cmd->cmd_tgt_addr,
8916 					    DRAIN_THROTTLE);
8917 				}
8918 			}
8919 			if ((cmd->cmd_flags & CFLAG_PASSTHRU) ||
8920 			    (cmd->cmd_flags & CFLAG_CONFIG)) {
8921 				cmd->cmd_active_timeout -=
8922 				    mptsas_scsi_watchdog_tick;
8923 				if (cmd->cmd_active_timeout <= 0) {
8924 					/*
8925 					 * passthrough command timeout
8926 					 */
8927 					cmd->cmd_flags |= (CFLAG_FINISHED |
8928 					    CFLAG_TIMEOUT);
8929 					cv_broadcast(&mpt->m_passthru_cv);
8930 					cv_broadcast(&mpt->m_config_cv);
8931 				}
8932 			}
8933 		}
8934 	}
8935 
8936 	ptgt = (mptsas_target_t *)mptsas_hash_traverse(&mpt->m_active->m_tgttbl,
8937 	    MPTSAS_HASH_FIRST);
8938 	while (ptgt != NULL) {
8939 		/*
8940 		 * If we were draining due to a qfull condition,
8941 		 * go back to full throttle.
8942 		 */
8943 		if ((ptgt->m_t_throttle < MAX_THROTTLE) &&
8944 		    (ptgt->m_t_throttle > HOLD_THROTTLE) &&
8945 		    (ptgt->m_t_ncmds < ptgt->m_t_throttle)) {
8946 			mptsas_set_throttle(mpt, ptgt, MAX_THROTTLE);
8947 			mptsas_restart_hba(mpt);
8948 		}
8949 
8950 		if ((ptgt->m_t_ncmds > 0) &&
8951 		    (ptgt->m_timebase)) {
8952 
8953 			if (ptgt->m_timebase <=
8954 			    mptsas_scsi_watchdog_tick) {
8955 				ptgt->m_timebase +=
8956 				    mptsas_scsi_watchdog_tick;
8957 				ptgt = (mptsas_target_t *)mptsas_hash_traverse(
8958 				    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
8959 				continue;
8960 			}
8961 
8962 			ptgt->m_timeout -= mptsas_scsi_watchdog_tick;
8963 
8964 			if (ptgt->m_timeout < 0) {
8965 				mptsas_cmd_timeout(mpt, ptgt->m_devhdl);
8966 				ptgt = (mptsas_target_t *)mptsas_hash_traverse(
8967 				    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
8968 				continue;
8969 			}
8970 
8971 			if ((ptgt->m_timeout) <=
8972 			    mptsas_scsi_watchdog_tick) {
8973 				NDBG23(("pending timeout"));
8974 				mptsas_set_throttle(mpt, ptgt,
8975 				    DRAIN_THROTTLE);
8976 			}
8977 		}
8978 
8979 		ptgt = (mptsas_target_t *)mptsas_hash_traverse(
8980 		    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
8981 	}
8982 }
8983 
8984 /*
8985  * timeout recovery
8986  */
8987 static void
8988 mptsas_cmd_timeout(mptsas_t *mpt, uint16_t devhdl)
8989 {
8990 
8991 	NDBG29(("mptsas_cmd_timeout: target=%d", devhdl));
8992 	mptsas_log(mpt, CE_WARN, "Disconnected command timeout for "
8993 	    "Target %d", devhdl);
8994 
8995 	/*
8996 	 * If the current target is not the target passed in,
8997 	 * try to reset that target.
8998 	 */
8999 	NDBG29(("mptsas_cmd_timeout: device reset"));
9000 	if (mptsas_do_scsi_reset(mpt, devhdl) != TRUE) {
9001 		mptsas_log(mpt, CE_WARN, "Target %d reset for command timeout "
9002 		    "recovery failed!", devhdl);
9003 	}
9004 }
9005 
9006 /*
9007  * Device / Hotplug control
9008  */
9009 static int
9010 mptsas_scsi_quiesce(dev_info_t *dip)
9011 {
9012 	mptsas_t	*mpt;
9013 	scsi_hba_tran_t	*tran;
9014 
9015 	tran = ddi_get_driver_private(dip);
9016 	if (tran == NULL || (mpt = TRAN2MPT(tran)) == NULL)
9017 		return (-1);
9018 
9019 	return (mptsas_quiesce_bus(mpt));
9020 }
9021 
9022 static int
9023 mptsas_scsi_unquiesce(dev_info_t *dip)
9024 {
9025 	mptsas_t		*mpt;
9026 	scsi_hba_tran_t	*tran;
9027 
9028 	tran = ddi_get_driver_private(dip);
9029 	if (tran == NULL || (mpt = TRAN2MPT(tran)) == NULL)
9030 		return (-1);
9031 
9032 	return (mptsas_unquiesce_bus(mpt));
9033 }
9034 
9035 static int
9036 mptsas_quiesce_bus(mptsas_t *mpt)
9037 {
9038 	mptsas_target_t	*ptgt = NULL;
9039 
9040 	NDBG28(("mptsas_quiesce_bus"));
9041 	mutex_enter(&mpt->m_mutex);
9042 
9043 	/* Set all the throttles to zero */
9044 	ptgt = (mptsas_target_t *)mptsas_hash_traverse(&mpt->m_active->m_tgttbl,
9045 	    MPTSAS_HASH_FIRST);
9046 	while (ptgt != NULL) {
9047 		mptsas_set_throttle(mpt, ptgt, HOLD_THROTTLE);
9048 
9049 		ptgt = (mptsas_target_t *)mptsas_hash_traverse(
9050 		    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
9051 	}
9052 
9053 	/* If there are any outstanding commands in the queue */
9054 	if (mpt->m_ncmds) {
9055 		mpt->m_softstate |= MPTSAS_SS_DRAINING;
9056 		mpt->m_quiesce_timeid = timeout(mptsas_ncmds_checkdrain,
9057 		    mpt, (MPTSAS_QUIESCE_TIMEOUT * drv_usectohz(1000000)));
9058 		if (cv_wait_sig(&mpt->m_cv, &mpt->m_mutex) == 0) {
9059 			/*
9060 			 * Quiesce has been interrupted
9061 			 */
9062 			mpt->m_softstate &= ~MPTSAS_SS_DRAINING;
9063 			ptgt = (mptsas_target_t *)mptsas_hash_traverse(
9064 			    &mpt->m_active->m_tgttbl, MPTSAS_HASH_FIRST);
9065 			while (ptgt != NULL) {
9066 				mptsas_set_throttle(mpt, ptgt, MAX_THROTTLE);
9067 
9068 				ptgt = (mptsas_target_t *)mptsas_hash_traverse(
9069 				    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
9070 			}
9071 			mptsas_restart_hba(mpt);
9072 			if (mpt->m_quiesce_timeid != 0) {
9073 				timeout_id_t tid = mpt->m_quiesce_timeid;
9074 				mpt->m_quiesce_timeid = 0;
9075 				mutex_exit(&mpt->m_mutex);
9076 				(void) untimeout(tid);
9077 				return (-1);
9078 			}
9079 			mutex_exit(&mpt->m_mutex);
9080 			return (-1);
9081 		} else {
9082 			/* Bus has been quiesced */
9083 			ASSERT(mpt->m_quiesce_timeid == 0);
9084 			mpt->m_softstate &= ~MPTSAS_SS_DRAINING;
9085 			mpt->m_softstate |= MPTSAS_SS_QUIESCED;
9086 			mutex_exit(&mpt->m_mutex);
9087 			return (0);
9088 		}
9089 	}
9090 	/* Bus was not busy - QUIESCED */
9091 	mutex_exit(&mpt->m_mutex);
9092 
9093 	return (0);
9094 }
9095 
9096 static int
9097 mptsas_unquiesce_bus(mptsas_t *mpt)
9098 {
9099 	mptsas_target_t	*ptgt = NULL;
9100 
9101 	NDBG28(("mptsas_unquiesce_bus"));
9102 	mutex_enter(&mpt->m_mutex);
9103 	mpt->m_softstate &= ~MPTSAS_SS_QUIESCED;
9104 	ptgt = (mptsas_target_t *)mptsas_hash_traverse(&mpt->m_active->m_tgttbl,
9105 	    MPTSAS_HASH_FIRST);
9106 	while (ptgt != NULL) {
9107 		mptsas_set_throttle(mpt, ptgt, MAX_THROTTLE);
9108 
9109 		ptgt = (mptsas_target_t *)mptsas_hash_traverse(
9110 		    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
9111 	}
9112 	mptsas_restart_hba(mpt);
9113 	mutex_exit(&mpt->m_mutex);
9114 	return (0);
9115 }
9116 
9117 static void
9118 mptsas_ncmds_checkdrain(void *arg)
9119 {
9120 	mptsas_t	*mpt = arg;
9121 	mptsas_target_t	*ptgt = NULL;
9122 
9123 	mutex_enter(&mpt->m_mutex);
9124 	if (mpt->m_softstate & MPTSAS_SS_DRAINING) {
9125 		mpt->m_quiesce_timeid = 0;
9126 		if (mpt->m_ncmds == 0) {
9127 			/* Command queue has been drained */
9128 			cv_signal(&mpt->m_cv);
9129 		} else {
9130 			/*
9131 			 * The throttle may have been reset because
9132 			 * of a SCSI bus reset
9133 			 */
9134 			ptgt = (mptsas_target_t *)mptsas_hash_traverse(
9135 			    &mpt->m_active->m_tgttbl, MPTSAS_HASH_FIRST);
9136 			while (ptgt != NULL) {
9137 				mptsas_set_throttle(mpt, ptgt, HOLD_THROTTLE);
9138 
9139 				ptgt = (mptsas_target_t *)mptsas_hash_traverse(
9140 				    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
9141 			}
9142 
9143 			mpt->m_quiesce_timeid = timeout(mptsas_ncmds_checkdrain,
9144 			    mpt, (MPTSAS_QUIESCE_TIMEOUT *
9145 			    drv_usectohz(1000000)));
9146 		}
9147 	}
9148 	mutex_exit(&mpt->m_mutex);
9149 }
9150 
9151 static void
9152 mptsas_dump_cmd(mptsas_t *mpt, mptsas_cmd_t *cmd)
9153 {
9154 	int	i;
9155 	uint8_t	*cp = (uchar_t *)cmd->cmd_pkt->pkt_cdbp;
9156 	char	buf[128];
9157 
9158 	buf[0] = '\0';
9159 	mptsas_log(mpt, CE_NOTE, "?Cmd (0x%p) dump for Target %d Lun %d:\n",
9160 	    (void *)cmd, Tgt(cmd), Lun(cmd));
9161 	(void) sprintf(&buf[0], "\tcdb=[");
9162 	for (i = 0; i < (int)cmd->cmd_cdblen; i++) {
9163 		(void) sprintf(&buf[strlen(buf)], " 0x%x", *cp++);
9164 	}
9165 	(void) sprintf(&buf[strlen(buf)], " ]");
9166 	mptsas_log(mpt, CE_NOTE, "?%s\n", buf);
9167 	mptsas_log(mpt, CE_NOTE,
9168 	    "?pkt_flags=0x%x pkt_statistics=0x%x pkt_state=0x%x\n",
9169 	    cmd->cmd_pkt->pkt_flags, cmd->cmd_pkt->pkt_statistics,
9170 	    cmd->cmd_pkt->pkt_state);
9171 	mptsas_log(mpt, CE_NOTE, "?pkt_scbp=0x%x cmd_flags=0x%x\n",
9172 	    *(cmd->cmd_pkt->pkt_scbp), cmd->cmd_flags);
9173 }
9174 
9175 static void
9176 mptsas_start_passthru(mptsas_t *mpt, mptsas_cmd_t *cmd)
9177 {
9178 	caddr_t			memp;
9179 	pMPI2RequestHeader_t	request_hdrp;
9180 	struct scsi_pkt		*pkt = cmd->cmd_pkt;
9181 	mptsas_pt_request_t	*pt = pkt->pkt_ha_private;
9182 	uint32_t		request_size, data_size, dataout_size;
9183 	uint32_t		direction;
9184 	ddi_dma_cookie_t	data_cookie;
9185 	ddi_dma_cookie_t	dataout_cookie;
9186 	uint32_t		request_desc_low, request_desc_high = 0;
9187 	uint32_t		i, sense_bufp;
9188 	uint8_t			desc_type;
9189 	uint8_t			*request, function;
9190 	ddi_dma_handle_t	dma_hdl = mpt->m_dma_req_frame_hdl;
9191 	ddi_acc_handle_t	acc_hdl = mpt->m_acc_req_frame_hdl;
9192 
9193 	desc_type = MPI2_REQ_DESCRIPT_FLAGS_DEFAULT_TYPE;
9194 
9195 	request = pt->request;
9196 	direction = pt->direction;
9197 	request_size = pt->request_size;
9198 	data_size = pt->data_size;
9199 	dataout_size = pt->dataout_size;
9200 	data_cookie = pt->data_cookie;
9201 	dataout_cookie = pt->dataout_cookie;
9202 
9203 	/*
9204 	 * Store the passthrough message in memory location
9205 	 * corresponding to our slot number
9206 	 */
9207 	memp = mpt->m_req_frame + (mpt->m_req_frame_size * cmd->cmd_slot);
9208 	request_hdrp = (pMPI2RequestHeader_t)memp;
9209 	bzero(memp, mpt->m_req_frame_size);
9210 
9211 	for (i = 0; i < request_size; i++) {
9212 		bcopy(request + i, memp + i, 1);
9213 	}
9214 
9215 	if (data_size || dataout_size) {
9216 		pMpi2SGESimple64_t	sgep;
9217 		uint32_t		sge_flags;
9218 
9219 		sgep = (pMpi2SGESimple64_t)((uint8_t *)request_hdrp +
9220 		    request_size);
9221 		if (dataout_size) {
9222 
9223 			sge_flags = dataout_size |
9224 			    ((uint32_t)(MPI2_SGE_FLAGS_SIMPLE_ELEMENT |
9225 			    MPI2_SGE_FLAGS_END_OF_BUFFER |
9226 			    MPI2_SGE_FLAGS_HOST_TO_IOC |
9227 			    MPI2_SGE_FLAGS_64_BIT_ADDRESSING) <<
9228 			    MPI2_SGE_FLAGS_SHIFT);
9229 			ddi_put32(acc_hdl, &sgep->FlagsLength, sge_flags);
9230 			ddi_put32(acc_hdl, &sgep->Address.Low,
9231 			    (uint32_t)(dataout_cookie.dmac_laddress &
9232 			    0xffffffffull));
9233 			ddi_put32(acc_hdl, &sgep->Address.High,
9234 			    (uint32_t)(dataout_cookie.dmac_laddress
9235 			    >> 32));
9236 			sgep++;
9237 		}
9238 		sge_flags = data_size;
9239 		sge_flags |= ((uint32_t)(MPI2_SGE_FLAGS_SIMPLE_ELEMENT |
9240 		    MPI2_SGE_FLAGS_LAST_ELEMENT |
9241 		    MPI2_SGE_FLAGS_END_OF_BUFFER |
9242 		    MPI2_SGE_FLAGS_END_OF_LIST |
9243 		    MPI2_SGE_FLAGS_64_BIT_ADDRESSING) <<
9244 		    MPI2_SGE_FLAGS_SHIFT);
9245 		if (direction == MPTSAS_PASS_THRU_DIRECTION_WRITE) {
9246 			sge_flags |= ((uint32_t)(MPI2_SGE_FLAGS_HOST_TO_IOC) <<
9247 			    MPI2_SGE_FLAGS_SHIFT);
9248 		} else {
9249 			sge_flags |= ((uint32_t)(MPI2_SGE_FLAGS_IOC_TO_HOST) <<
9250 			    MPI2_SGE_FLAGS_SHIFT);
9251 		}
9252 		ddi_put32(acc_hdl, &sgep->FlagsLength,
9253 		    sge_flags);
9254 		ddi_put32(acc_hdl, &sgep->Address.Low,
9255 		    (uint32_t)(data_cookie.dmac_laddress &
9256 		    0xffffffffull));
9257 		ddi_put32(acc_hdl, &sgep->Address.High,
9258 		    (uint32_t)(data_cookie.dmac_laddress >> 32));
9259 	}
9260 
9261 	function = request_hdrp->Function;
9262 	if ((function == MPI2_FUNCTION_SCSI_IO_REQUEST) ||
9263 	    (function == MPI2_FUNCTION_RAID_SCSI_IO_PASSTHROUGH)) {
9264 		pMpi2SCSIIORequest_t	scsi_io_req;
9265 
9266 		scsi_io_req = (pMpi2SCSIIORequest_t)request_hdrp;
9267 		/*
9268 		 * Put SGE for data and data_out buffer at the end of
9269 		 * scsi_io_request message header.(64 bytes in total)
9270 		 * Following above SGEs, the residual space will be
9271 		 * used by sense data.
9272 		 */
9273 		ddi_put8(acc_hdl,
9274 		    &scsi_io_req->SenseBufferLength,
9275 		    (uint8_t)(request_size - 64));
9276 
9277 		sense_bufp = mpt->m_req_frame_dma_addr +
9278 		    (mpt->m_req_frame_size * cmd->cmd_slot);
9279 		sense_bufp += 64;
9280 		ddi_put32(acc_hdl,
9281 		    &scsi_io_req->SenseBufferLowAddress, sense_bufp);
9282 
9283 		/*
9284 		 * Set SGLOffset0 value
9285 		 */
9286 		ddi_put8(acc_hdl, &scsi_io_req->SGLOffset0,
9287 		    offsetof(MPI2_SCSI_IO_REQUEST, SGL) / 4);
9288 
9289 		/*
9290 		 * Setup descriptor info
9291 		 */
9292 		desc_type = MPI2_REQ_DESCRIPT_FLAGS_SCSI_IO;
9293 		request_desc_high = (ddi_get16(acc_hdl,
9294 		    &scsi_io_req->DevHandle) << 16);
9295 	}
9296 
9297 	/*
9298 	 * We must wait till the message has been completed before
9299 	 * beginning the next message so we wait for this one to
9300 	 * finish.
9301 	 */
9302 	(void) ddi_dma_sync(dma_hdl, 0, 0, DDI_DMA_SYNC_FORDEV);
9303 	request_desc_low = (cmd->cmd_slot << 16) + desc_type;
9304 	cmd->cmd_rfm = NULL;
9305 	MPTSAS_START_CMD(mpt, request_desc_low, request_desc_high);
9306 	if ((mptsas_check_dma_handle(dma_hdl) != DDI_SUCCESS) ||
9307 	    (mptsas_check_acc_handle(acc_hdl) != DDI_SUCCESS)) {
9308 		ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_UNAFFECTED);
9309 	}
9310 }
9311 
9312 
9313 
9314 static int
9315 mptsas_do_passthru(mptsas_t *mpt, uint8_t *request, uint8_t *reply,
9316     uint8_t *data, uint32_t request_size, uint32_t reply_size,
9317     uint32_t data_size, uint32_t direction, uint8_t *dataout,
9318     uint32_t dataout_size, short timeout, int mode)
9319 {
9320 	mptsas_pt_request_t		pt;
9321 	mptsas_dma_alloc_state_t	data_dma_state;
9322 	mptsas_dma_alloc_state_t	dataout_dma_state;
9323 	caddr_t				memp;
9324 	mptsas_cmd_t			*cmd = NULL;
9325 	struct scsi_pkt			*pkt;
9326 	uint32_t			reply_len = 0, sense_len = 0;
9327 	pMPI2RequestHeader_t		request_hdrp;
9328 	pMPI2RequestHeader_t		request_msg;
9329 	pMPI2DefaultReply_t		reply_msg;
9330 	Mpi2SCSIIOReply_t		rep_msg;
9331 	int				i, status = 0, pt_flags = 0, rv = 0;
9332 	int				rvalue;
9333 	uint8_t				function;
9334 
9335 	ASSERT(mutex_owned(&mpt->m_mutex));
9336 
9337 	reply_msg = (pMPI2DefaultReply_t)(&rep_msg);
9338 	bzero(reply_msg, sizeof (MPI2_DEFAULT_REPLY));
9339 	request_msg = kmem_zalloc(request_size, KM_SLEEP);
9340 
9341 	mutex_exit(&mpt->m_mutex);
9342 	/*
9343 	 * copy in the request buffer since it could be used by
9344 	 * another thread when the pt request into waitq
9345 	 */
9346 	if (ddi_copyin(request, request_msg, request_size, mode)) {
9347 		mutex_enter(&mpt->m_mutex);
9348 		status = EFAULT;
9349 		mptsas_log(mpt, CE_WARN, "failed to copy request data");
9350 		goto out;
9351 	}
9352 	mutex_enter(&mpt->m_mutex);
9353 
9354 	function = request_msg->Function;
9355 	if (function == MPI2_FUNCTION_SCSI_TASK_MGMT) {
9356 		pMpi2SCSITaskManagementRequest_t	task;
9357 		task = (pMpi2SCSITaskManagementRequest_t)request_msg;
9358 		mptsas_setup_bus_reset_delay(mpt);
9359 		rv = mptsas_ioc_task_management(mpt, task->TaskType,
9360 		    task->DevHandle, (int)task->LUN[1]);
9361 
9362 		if (rv != TRUE) {
9363 			status = EIO;
9364 			mptsas_log(mpt, CE_WARN, "task management failed");
9365 		}
9366 		goto out;
9367 	}
9368 
9369 	if (data_size != 0) {
9370 		data_dma_state.size = data_size;
9371 		if (mptsas_passthru_dma_alloc(mpt, &data_dma_state) !=
9372 		    DDI_SUCCESS) {
9373 			status = ENOMEM;
9374 			mptsas_log(mpt, CE_WARN, "failed to alloc DMA "
9375 			    "resource");
9376 			goto out;
9377 		}
9378 		pt_flags |= MPTSAS_DATA_ALLOCATED;
9379 		if (direction == MPTSAS_PASS_THRU_DIRECTION_WRITE) {
9380 			mutex_exit(&mpt->m_mutex);
9381 			for (i = 0; i < data_size; i++) {
9382 				if (ddi_copyin(data + i, (uint8_t *)
9383 				    data_dma_state.memp + i, 1, mode)) {
9384 					mutex_enter(&mpt->m_mutex);
9385 					status = EFAULT;
9386 					mptsas_log(mpt, CE_WARN, "failed to "
9387 					    "copy read data");
9388 					goto out;
9389 				}
9390 			}
9391 			mutex_enter(&mpt->m_mutex);
9392 		}
9393 	}
9394 
9395 	if (dataout_size != 0) {
9396 		dataout_dma_state.size = dataout_size;
9397 		if (mptsas_passthru_dma_alloc(mpt, &dataout_dma_state) !=
9398 		    DDI_SUCCESS) {
9399 			status = ENOMEM;
9400 			mptsas_log(mpt, CE_WARN, "failed to alloc DMA "
9401 			    "resource");
9402 			goto out;
9403 		}
9404 		pt_flags |= MPTSAS_DATAOUT_ALLOCATED;
9405 		mutex_exit(&mpt->m_mutex);
9406 		for (i = 0; i < dataout_size; i++) {
9407 			if (ddi_copyin(dataout + i, (uint8_t *)
9408 			    dataout_dma_state.memp + i, 1, mode)) {
9409 				mutex_enter(&mpt->m_mutex);
9410 				mptsas_log(mpt, CE_WARN, "failed to copy out"
9411 				    " data");
9412 				status = EFAULT;
9413 				goto out;
9414 			}
9415 		}
9416 		mutex_enter(&mpt->m_mutex);
9417 	}
9418 
9419 	if ((rvalue = (mptsas_request_from_pool(mpt, &cmd, &pkt))) == -1) {
9420 		status = EAGAIN;
9421 		mptsas_log(mpt, CE_NOTE, "event ack command pool is full");
9422 		goto out;
9423 	}
9424 	pt_flags |= MPTSAS_REQUEST_POOL_CMD;
9425 
9426 	bzero((caddr_t)cmd, sizeof (*cmd));
9427 	bzero((caddr_t)pkt, scsi_pkt_size());
9428 	bzero((caddr_t)&pt, sizeof (pt));
9429 
9430 	cmd->ioc_cmd_slot = (uint32_t)(rvalue);
9431 
9432 	pt.request = (uint8_t *)request_msg;
9433 	pt.direction = direction;
9434 	pt.request_size = request_size;
9435 	pt.data_size = data_size;
9436 	pt.dataout_size = dataout_size;
9437 	pt.data_cookie = data_dma_state.cookie;
9438 	pt.dataout_cookie = dataout_dma_state.cookie;
9439 
9440 	/*
9441 	 * Form a blank cmd/pkt to store the acknowledgement message
9442 	 */
9443 	pkt->pkt_cdbp		= (opaque_t)&cmd->cmd_cdb[0];
9444 	pkt->pkt_scbp		= (opaque_t)&cmd->cmd_scb;
9445 	pkt->pkt_ha_private	= (opaque_t)&pt;
9446 	pkt->pkt_flags		= FLAG_HEAD;
9447 	pkt->pkt_time		= timeout;
9448 	cmd->cmd_pkt		= pkt;
9449 	cmd->cmd_flags		= CFLAG_CMDIOC | CFLAG_PASSTHRU;
9450 
9451 	/*
9452 	 * Save the command in a slot
9453 	 */
9454 	if (mptsas_save_cmd(mpt, cmd) == TRUE) {
9455 		/*
9456 		 * Once passthru command get slot, set cmd_flags
9457 		 * CFLAG_PREPARED.
9458 		 */
9459 		cmd->cmd_flags |= CFLAG_PREPARED;
9460 		mptsas_start_passthru(mpt, cmd);
9461 	} else {
9462 		mptsas_waitq_add(mpt, cmd);
9463 	}
9464 
9465 	while ((cmd->cmd_flags & CFLAG_FINISHED) == 0) {
9466 		cv_wait(&mpt->m_passthru_cv, &mpt->m_mutex);
9467 	}
9468 
9469 	if (cmd->cmd_flags & CFLAG_PREPARED) {
9470 		memp = mpt->m_req_frame + (mpt->m_req_frame_size *
9471 		    cmd->cmd_slot);
9472 		request_hdrp = (pMPI2RequestHeader_t)memp;
9473 	}
9474 
9475 	if (cmd->cmd_flags & CFLAG_TIMEOUT) {
9476 		status = ETIMEDOUT;
9477 		mptsas_log(mpt, CE_WARN, "passthrough command timeout");
9478 		pt_flags |= MPTSAS_CMD_TIMEOUT;
9479 		goto out;
9480 	}
9481 
9482 	if (cmd->cmd_rfm) {
9483 		/*
9484 		 * cmd_rfm is zero means the command reply is a CONTEXT
9485 		 * reply and no PCI Write to post the free reply SMFA
9486 		 * because no reply message frame is used.
9487 		 * cmd_rfm is non-zero means the reply is a ADDRESS
9488 		 * reply and reply message frame is used.
9489 		 */
9490 		pt_flags |= MPTSAS_ADDRESS_REPLY;
9491 		(void) ddi_dma_sync(mpt->m_dma_reply_frame_hdl, 0, 0,
9492 		    DDI_DMA_SYNC_FORCPU);
9493 		reply_msg = (pMPI2DefaultReply_t)
9494 		    (mpt->m_reply_frame + (cmd->cmd_rfm -
9495 		    mpt->m_reply_frame_dma_addr));
9496 	}
9497 
9498 	mptsas_fma_check(mpt, cmd);
9499 	if (pkt->pkt_reason == CMD_TRAN_ERR) {
9500 		status = EAGAIN;
9501 		mptsas_log(mpt, CE_WARN, "passthru fma error");
9502 		goto out;
9503 	}
9504 	if (pkt->pkt_reason == CMD_RESET) {
9505 		status = EAGAIN;
9506 		mptsas_log(mpt, CE_WARN, "ioc reset abort passthru");
9507 		goto out;
9508 	}
9509 
9510 	if (pkt->pkt_reason == CMD_INCOMPLETE) {
9511 		status = EIO;
9512 		mptsas_log(mpt, CE_WARN, "passthrough command incomplete");
9513 		goto out;
9514 	}
9515 
9516 	mutex_exit(&mpt->m_mutex);
9517 	if (cmd->cmd_flags & CFLAG_PREPARED) {
9518 		function = request_hdrp->Function;
9519 		if ((function == MPI2_FUNCTION_SCSI_IO_REQUEST) ||
9520 		    (function == MPI2_FUNCTION_RAID_SCSI_IO_PASSTHROUGH)) {
9521 			reply_len = sizeof (MPI2_SCSI_IO_REPLY);
9522 			sense_len = reply_size - reply_len;
9523 		} else {
9524 			reply_len = reply_size;
9525 			sense_len = 0;
9526 		}
9527 
9528 		for (i = 0; i < reply_len; i++) {
9529 			if (ddi_copyout((uint8_t *)reply_msg + i, reply + i, 1,
9530 			    mode)) {
9531 				mutex_enter(&mpt->m_mutex);
9532 				status = EFAULT;
9533 				mptsas_log(mpt, CE_WARN, "failed to copy out "
9534 				    "reply data");
9535 				goto out;
9536 			}
9537 		}
9538 		for (i = 0; i < sense_len; i++) {
9539 			if (ddi_copyout((uint8_t *)request_hdrp + 64 + i,
9540 			    reply + reply_len + i, 1, mode)) {
9541 				mutex_enter(&mpt->m_mutex);
9542 				status = EFAULT;
9543 				mptsas_log(mpt, CE_WARN, "failed to copy out "
9544 				    "sense data");
9545 				goto out;
9546 			}
9547 		}
9548 	}
9549 
9550 	if (data_size) {
9551 		if (direction != MPTSAS_PASS_THRU_DIRECTION_WRITE) {
9552 			(void) ddi_dma_sync(data_dma_state.handle, 0, 0,
9553 			    DDI_DMA_SYNC_FORCPU);
9554 			for (i = 0; i < data_size; i++) {
9555 				if (ddi_copyout((uint8_t *)(
9556 				    data_dma_state.memp + i), data + i,  1,
9557 				    mode)) {
9558 					mutex_enter(&mpt->m_mutex);
9559 					status = EFAULT;
9560 					mptsas_log(mpt, CE_WARN, "failed to "
9561 					    "copy out the reply data");
9562 					goto out;
9563 				}
9564 			}
9565 		}
9566 	}
9567 	mutex_enter(&mpt->m_mutex);
9568 out:
9569 	/*
9570 	 * Put the reply frame back on the free queue, increment the free
9571 	 * index, and write the new index to the free index register.  But only
9572 	 * if this reply is an ADDRESS reply.
9573 	 */
9574 	if (pt_flags & MPTSAS_ADDRESS_REPLY) {
9575 		ddi_put32(mpt->m_acc_free_queue_hdl,
9576 		    &((uint32_t *)(void *)mpt->m_free_queue)[mpt->m_free_index],
9577 		    cmd->cmd_rfm);
9578 		(void) ddi_dma_sync(mpt->m_dma_free_queue_hdl, 0, 0,
9579 		    DDI_DMA_SYNC_FORDEV);
9580 		if (++mpt->m_free_index == mpt->m_free_queue_depth) {
9581 			mpt->m_free_index = 0;
9582 		}
9583 		ddi_put32(mpt->m_datap, &mpt->m_reg->ReplyFreeHostIndex,
9584 		    mpt->m_free_index);
9585 	}
9586 	if (cmd && (cmd->cmd_flags & CFLAG_PREPARED)) {
9587 		mptsas_remove_cmd(mpt, cmd);
9588 		pt_flags &= (~MPTSAS_REQUEST_POOL_CMD);
9589 	}
9590 	if (pt_flags & MPTSAS_REQUEST_POOL_CMD)
9591 		mptsas_return_to_pool(mpt, cmd);
9592 	if (pt_flags & MPTSAS_DATA_ALLOCATED) {
9593 		if (mptsas_check_dma_handle(data_dma_state.handle) !=
9594 		    DDI_SUCCESS) {
9595 			ddi_fm_service_impact(mpt->m_dip,
9596 			    DDI_SERVICE_UNAFFECTED);
9597 			status = EFAULT;
9598 		}
9599 		mptsas_passthru_dma_free(&data_dma_state);
9600 	}
9601 	if (pt_flags & MPTSAS_DATAOUT_ALLOCATED) {
9602 		if (mptsas_check_dma_handle(dataout_dma_state.handle) !=
9603 		    DDI_SUCCESS) {
9604 			ddi_fm_service_impact(mpt->m_dip,
9605 			    DDI_SERVICE_UNAFFECTED);
9606 			status = EFAULT;
9607 		}
9608 		mptsas_passthru_dma_free(&dataout_dma_state);
9609 	}
9610 	if (pt_flags & MPTSAS_CMD_TIMEOUT) {
9611 		if ((mptsas_restart_ioc(mpt)) == DDI_FAILURE) {
9612 			mptsas_log(mpt, CE_WARN, "mptsas_restart_ioc failed");
9613 		}
9614 	}
9615 	if (request_msg)
9616 		kmem_free(request_msg, request_size);
9617 
9618 	return (status);
9619 }
9620 
9621 static int
9622 mptsas_pass_thru(mptsas_t *mpt, mptsas_pass_thru_t *data, int mode)
9623 {
9624 	/*
9625 	 * If timeout is 0, set timeout to default of 60 seconds.
9626 	 */
9627 	if (data->Timeout == 0) {
9628 		data->Timeout = MPTSAS_PASS_THRU_TIME_DEFAULT;
9629 	}
9630 
9631 	if (((data->DataSize == 0) &&
9632 	    (data->DataDirection == MPTSAS_PASS_THRU_DIRECTION_NONE)) ||
9633 	    ((data->DataSize != 0) &&
9634 	    ((data->DataDirection == MPTSAS_PASS_THRU_DIRECTION_READ) ||
9635 	    (data->DataDirection == MPTSAS_PASS_THRU_DIRECTION_WRITE) ||
9636 	    ((data->DataDirection == MPTSAS_PASS_THRU_DIRECTION_BOTH) &&
9637 	    (data->DataOutSize != 0))))) {
9638 		if (data->DataDirection == MPTSAS_PASS_THRU_DIRECTION_BOTH) {
9639 			data->DataDirection = MPTSAS_PASS_THRU_DIRECTION_READ;
9640 		} else {
9641 			data->DataOutSize = 0;
9642 		}
9643 		/*
9644 		 * Send passthru request messages
9645 		 */
9646 		return (mptsas_do_passthru(mpt,
9647 		    (uint8_t *)((uintptr_t)data->PtrRequest),
9648 		    (uint8_t *)((uintptr_t)data->PtrReply),
9649 		    (uint8_t *)((uintptr_t)data->PtrData),
9650 		    data->RequestSize, data->ReplySize,
9651 		    data->DataSize, data->DataDirection,
9652 		    (uint8_t *)((uintptr_t)data->PtrDataOut),
9653 		    data->DataOutSize, data->Timeout, mode));
9654 	} else {
9655 		return (EINVAL);
9656 	}
9657 }
9658 
9659 /*
9660  * This routine handles the "event query" ioctl.
9661  */
9662 static int
9663 mptsas_event_query(mptsas_t *mpt, mptsas_event_query_t *data, int mode,
9664     int *rval)
9665 {
9666 	int			status;
9667 	mptsas_event_query_t	driverdata;
9668 	uint8_t			i;
9669 
9670 	driverdata.Entries = MPTSAS_EVENT_QUEUE_SIZE;
9671 
9672 	mutex_enter(&mpt->m_mutex);
9673 	for (i = 0; i < 4; i++) {
9674 		driverdata.Types[i] = mpt->m_event_mask[i];
9675 	}
9676 	mutex_exit(&mpt->m_mutex);
9677 
9678 	if (ddi_copyout(&driverdata, data, sizeof (driverdata), mode) != 0) {
9679 		status = EFAULT;
9680 	} else {
9681 		*rval = MPTIOCTL_STATUS_GOOD;
9682 		status = 0;
9683 	}
9684 
9685 	return (status);
9686 }
9687 
9688 /*
9689  * This routine handles the "event enable" ioctl.
9690  */
9691 static int
9692 mptsas_event_enable(mptsas_t *mpt, mptsas_event_enable_t *data, int mode,
9693     int *rval)
9694 {
9695 	int			status;
9696 	mptsas_event_enable_t	driverdata;
9697 	uint8_t			i;
9698 
9699 	if (ddi_copyin(data, &driverdata, sizeof (driverdata), mode) == 0) {
9700 		mutex_enter(&mpt->m_mutex);
9701 		for (i = 0; i < 4; i++) {
9702 			mpt->m_event_mask[i] = driverdata.Types[i];
9703 		}
9704 		mutex_exit(&mpt->m_mutex);
9705 
9706 		*rval = MPTIOCTL_STATUS_GOOD;
9707 		status = 0;
9708 	} else {
9709 		status = EFAULT;
9710 	}
9711 	return (status);
9712 }
9713 
9714 /*
9715  * This routine handles the "event report" ioctl.
9716  */
9717 static int
9718 mptsas_event_report(mptsas_t *mpt, mptsas_event_report_t *data, int mode,
9719     int *rval)
9720 {
9721 	int			status;
9722 	mptsas_event_report_t	driverdata;
9723 
9724 	mutex_enter(&mpt->m_mutex);
9725 
9726 	if (ddi_copyin(&data->Size, &driverdata.Size, sizeof (driverdata.Size),
9727 	    mode) == 0) {
9728 		if (driverdata.Size >= sizeof (mpt->m_events)) {
9729 			if (ddi_copyout(mpt->m_events, data->Events,
9730 			    sizeof (mpt->m_events), mode) != 0) {
9731 				status = EFAULT;
9732 			} else {
9733 				if (driverdata.Size > sizeof (mpt->m_events)) {
9734 					driverdata.Size =
9735 					    sizeof (mpt->m_events);
9736 					if (ddi_copyout(&driverdata.Size,
9737 					    &data->Size,
9738 					    sizeof (driverdata.Size),
9739 					    mode) != 0) {
9740 						status = EFAULT;
9741 					} else {
9742 						*rval = MPTIOCTL_STATUS_GOOD;
9743 						status = 0;
9744 					}
9745 				} else {
9746 					*rval = MPTIOCTL_STATUS_GOOD;
9747 					status = 0;
9748 				}
9749 			}
9750 		} else {
9751 			*rval = MPTIOCTL_STATUS_LEN_TOO_SHORT;
9752 			status = 0;
9753 		}
9754 	} else {
9755 		status = EFAULT;
9756 	}
9757 
9758 	mutex_exit(&mpt->m_mutex);
9759 	return (status);
9760 }
9761 
9762 static void
9763 mptsas_lookup_pci_data(mptsas_t *mpt, mptsas_adapter_data_t *adapter_data)
9764 {
9765 	int	*reg_data;
9766 	uint_t	reglen;
9767 
9768 	/*
9769 	 * Lookup the 'reg' property and extract the other data
9770 	 */
9771 	if (ddi_prop_lookup_int_array(DDI_DEV_T_ANY, mpt->m_dip,
9772 	    DDI_PROP_DONTPASS, "reg", &reg_data, &reglen) ==
9773 	    DDI_PROP_SUCCESS) {
9774 		/*
9775 		 * Extract the PCI data from the 'reg' property first DWORD.
9776 		 * The entry looks like the following:
9777 		 * First DWORD:
9778 		 * Bits 0 - 7 8-bit Register number
9779 		 * Bits 8 - 10 3-bit Function number
9780 		 * Bits 11 - 15 5-bit Device number
9781 		 * Bits 16 - 23 8-bit Bus number
9782 		 * Bits 24 - 25 2-bit Address Space type identifier
9783 		 *
9784 		 * Store the device number in PCIDeviceHwId.
9785 		 * Store the function number in MpiPortNumber.
9786 		 * PciInformation stores bus, device, and function together
9787 		 */
9788 		adapter_data->PCIDeviceHwId = (reg_data[0] & 0x0000F800) >> 11;
9789 		adapter_data->MpiPortNumber = (reg_data[0] & 0x00000700) >> 8;
9790 		adapter_data->PciInformation = (reg_data[0] & 0x00FFFF00) >> 8;
9791 		ddi_prop_free((void *)reg_data);
9792 	} else {
9793 		/*
9794 		 * If we can't determine the PCI data then we fill in FF's for
9795 		 * the data to indicate this.
9796 		 */
9797 		adapter_data->PCIDeviceHwId = 0xFFFFFFFF;
9798 		adapter_data->MpiPortNumber = 0xFFFFFFFF;
9799 		adapter_data->PciInformation = 0xFFFFFFFF;
9800 	}
9801 
9802 	/*
9803 	 * Saved in the mpt->m_fwversion
9804 	 */
9805 	adapter_data->MpiFirmwareVersion = mpt->m_fwversion;
9806 }
9807 
9808 static void
9809 mptsas_read_adapter_data(mptsas_t *mpt, mptsas_adapter_data_t *adapter_data)
9810 {
9811 	char	*driver_verstr = MPTSAS_MOD_STRING;
9812 
9813 	mptsas_lookup_pci_data(mpt, adapter_data);
9814 	adapter_data->AdapterType = MPTIOCTL_ADAPTER_TYPE_SAS2;
9815 	adapter_data->PCIDeviceHwId = (uint32_t)mpt->m_devid;
9816 	adapter_data->PCIDeviceHwRev = (uint32_t)mpt->m_revid;
9817 	adapter_data->SubSystemId = (uint32_t)mpt->m_ssid;
9818 	adapter_data->SubsystemVendorId = (uint32_t)mpt->m_svid;
9819 	(void) strcpy((char *)&adapter_data->DriverVersion[0], driver_verstr);
9820 	adapter_data->BiosVersion = 0;
9821 	(void) mptsas_get_bios_page3(mpt, &adapter_data->BiosVersion);
9822 }
9823 
9824 static void
9825 mptsas_read_pci_info(mptsas_t *mpt, mptsas_pci_info_t *pci_info)
9826 {
9827 	int	*reg_data, i;
9828 	uint_t	reglen;
9829 
9830 	/*
9831 	 * Lookup the 'reg' property and extract the other data
9832 	 */
9833 	if (ddi_prop_lookup_int_array(DDI_DEV_T_ANY, mpt->m_dip,
9834 	    DDI_PROP_DONTPASS, "reg", &reg_data, &reglen) ==
9835 	    DDI_PROP_SUCCESS) {
9836 		/*
9837 		 * Extract the PCI data from the 'reg' property first DWORD.
9838 		 * The entry looks like the following:
9839 		 * First DWORD:
9840 		 * Bits 8 - 10 3-bit Function number
9841 		 * Bits 11 - 15 5-bit Device number
9842 		 * Bits 16 - 23 8-bit Bus number
9843 		 */
9844 		pci_info->BusNumber = (reg_data[0] & 0x00FF0000) >> 16;
9845 		pci_info->DeviceNumber = (reg_data[0] & 0x0000F800) >> 11;
9846 		pci_info->FunctionNumber = (reg_data[0] & 0x00000700) >> 8;
9847 		ddi_prop_free((void *)reg_data);
9848 	} else {
9849 		/*
9850 		 * If we can't determine the PCI info then we fill in FF's for
9851 		 * the data to indicate this.
9852 		 */
9853 		pci_info->BusNumber = 0xFFFFFFFF;
9854 		pci_info->DeviceNumber = 0xFF;
9855 		pci_info->FunctionNumber = 0xFF;
9856 	}
9857 
9858 	/*
9859 	 * Now get the interrupt vector and the pci header.  The vector can
9860 	 * only be 0 right now.  The header is the first 256 bytes of config
9861 	 * space.
9862 	 */
9863 	pci_info->InterruptVector = 0;
9864 	for (i = 0; i < sizeof (pci_info->PciHeader); i++) {
9865 		pci_info->PciHeader[i] = pci_config_get8(mpt->m_config_handle,
9866 		    i);
9867 	}
9868 }
9869 
9870 static int
9871 mptsas_ioctl(dev_t dev, int cmd, intptr_t data, int mode, cred_t *credp,
9872     int *rval)
9873 {
9874 	int			status = 0;
9875 	mptsas_t		*mpt;
9876 	mptsas_update_flash_t	flashdata;
9877 	mptsas_pass_thru_t	passthru_data;
9878 	mptsas_adapter_data_t   adapter_data;
9879 	mptsas_pci_info_t	pci_info;
9880 	int			copylen;
9881 
9882 	*rval = MPTIOCTL_STATUS_GOOD;
9883 	mpt = ddi_get_soft_state(mptsas_state, MINOR2INST(getminor(dev)));
9884 	if (mpt == NULL) {
9885 		return (scsi_hba_ioctl(dev, cmd, data, mode, credp, rval));
9886 	}
9887 	if (secpolicy_sys_config(credp, B_FALSE) != 0) {
9888 		return (EPERM);
9889 	}
9890 
9891 	/* Make sure power level is D0 before accessing registers */
9892 	mutex_enter(&mpt->m_mutex);
9893 	if (mpt->m_options & MPTSAS_OPT_PM) {
9894 		(void) pm_busy_component(mpt->m_dip, 0);
9895 		if (mpt->m_power_level != PM_LEVEL_D0) {
9896 			mutex_exit(&mpt->m_mutex);
9897 			if (pm_raise_power(mpt->m_dip, 0, PM_LEVEL_D0) !=
9898 			    DDI_SUCCESS) {
9899 				mptsas_log(mpt, CE_WARN,
9900 				    "mptsas%d: mptsas_ioctl: Raise power "
9901 				    "request failed.", mpt->m_instance);
9902 				(void) pm_idle_component(mpt->m_dip, 0);
9903 				return (ENXIO);
9904 			}
9905 		} else {
9906 			mutex_exit(&mpt->m_mutex);
9907 		}
9908 	} else {
9909 		mutex_exit(&mpt->m_mutex);
9910 	}
9911 
9912 	switch (cmd) {
9913 		case MPTIOCTL_UPDATE_FLASH:
9914 			if (ddi_copyin((void *)data, &flashdata,
9915 				sizeof (struct mptsas_update_flash), mode)) {
9916 				status = EFAULT;
9917 				break;
9918 			}
9919 
9920 			mutex_enter(&mpt->m_mutex);
9921 			if (mptsas_update_flash(mpt,
9922 			    (caddr_t)(long)flashdata.PtrBuffer,
9923 			    flashdata.ImageSize, flashdata.ImageType, mode)) {
9924 				status = EFAULT;
9925 			}
9926 
9927 			/*
9928 			 * Reset the chip to start using the new
9929 			 * firmware.  Reset if failed also.
9930 			 */
9931 			if (mptsas_restart_ioc(mpt) == DDI_FAILURE) {
9932 				status = EFAULT;
9933 			}
9934 			mutex_exit(&mpt->m_mutex);
9935 			break;
9936 		case MPTIOCTL_PASS_THRU:
9937 			/*
9938 			 * The user has requested to pass through a command to
9939 			 * be executed by the MPT firmware.  Call our routine
9940 			 * which does this.  Only allow one passthru IOCTL at
9941 			 * one time.
9942 			 */
9943 			if (ddi_copyin((void *)data, &passthru_data,
9944 			    sizeof (mptsas_pass_thru_t), mode)) {
9945 				status = EFAULT;
9946 				break;
9947 			}
9948 			mutex_enter(&mpt->m_mutex);
9949 			if (mpt->m_passthru_in_progress) {
9950 				mutex_exit(&mpt->m_mutex);
9951 				return (EBUSY);
9952 			}
9953 			mpt->m_passthru_in_progress = 1;
9954 			status = mptsas_pass_thru(mpt, &passthru_data, mode);
9955 			mpt->m_passthru_in_progress = 0;
9956 			mutex_exit(&mpt->m_mutex);
9957 
9958 			break;
9959 		case MPTIOCTL_GET_ADAPTER_DATA:
9960 			/*
9961 			 * The user has requested to read adapter data.  Call
9962 			 * our routine which does this.
9963 			 */
9964 			bzero(&adapter_data, sizeof (mptsas_adapter_data_t));
9965 			if (ddi_copyin((void *)data, (void *)&adapter_data,
9966 			    sizeof (mptsas_adapter_data_t), mode)) {
9967 				status = EFAULT;
9968 				break;
9969 			}
9970 			if (adapter_data.StructureLength >=
9971 			    sizeof (mptsas_adapter_data_t)) {
9972 				adapter_data.StructureLength = (uint32_t)
9973 				    sizeof (mptsas_adapter_data_t);
9974 				copylen = sizeof (mptsas_adapter_data_t);
9975 				mutex_enter(&mpt->m_mutex);
9976 				mptsas_read_adapter_data(mpt, &adapter_data);
9977 				mutex_exit(&mpt->m_mutex);
9978 			} else {
9979 				adapter_data.StructureLength = (uint32_t)
9980 				    sizeof (mptsas_adapter_data_t);
9981 				copylen = sizeof (adapter_data.StructureLength);
9982 				*rval = MPTIOCTL_STATUS_LEN_TOO_SHORT;
9983 			}
9984 			if (ddi_copyout((void *)(&adapter_data), (void *)data,
9985 			    copylen, mode) != 0) {
9986 				status = EFAULT;
9987 			}
9988 			break;
9989 		case MPTIOCTL_GET_PCI_INFO:
9990 			/*
9991 			 * The user has requested to read pci info.  Call
9992 			 * our routine which does this.
9993 			 */
9994 			bzero(&pci_info, sizeof (mptsas_pci_info_t));
9995 			mutex_enter(&mpt->m_mutex);
9996 			mptsas_read_pci_info(mpt, &pci_info);
9997 			mutex_exit(&mpt->m_mutex);
9998 			if (ddi_copyout((void *)(&pci_info), (void *)data,
9999 			    sizeof (mptsas_pci_info_t), mode) != 0) {
10000 				status = EFAULT;
10001 			}
10002 			break;
10003 		case MPTIOCTL_RESET_ADAPTER:
10004 			mutex_enter(&mpt->m_mutex);
10005 			if ((mptsas_restart_ioc(mpt)) == DDI_FAILURE) {
10006 				mptsas_log(mpt, CE_WARN, "reset adapter IOCTL "
10007 				    "failed");
10008 				status = EFAULT;
10009 			}
10010 			mutex_exit(&mpt->m_mutex);
10011 			break;
10012 		case MPTIOCTL_EVENT_QUERY:
10013 			/*
10014 			 * The user has done an event query. Call our routine
10015 			 * which does this.
10016 			 */
10017 			status = mptsas_event_query(mpt,
10018 			    (mptsas_event_query_t *)data, mode, rval);
10019 			break;
10020 		case MPTIOCTL_EVENT_ENABLE:
10021 			/*
10022 			 * The user has done an event enable. Call our routine
10023 			 * which does this.
10024 			 */
10025 			status = mptsas_event_enable(mpt,
10026 			    (mptsas_event_enable_t *)data, mode, rval);
10027 			break;
10028 		case MPTIOCTL_EVENT_REPORT:
10029 			/*
10030 			 * The user has done an event report. Call our routine
10031 			 * which does this.
10032 			 */
10033 			status = mptsas_event_report(mpt,
10034 			    (mptsas_event_report_t *)data, mode, rval);
10035 			break;
10036 		default:
10037 			status = scsi_hba_ioctl(dev, cmd, data, mode, credp,
10038 			    rval);
10039 			break;
10040 	}
10041 
10042 	/*
10043 	 * Report idle status to pm after grace period because
10044 	 * multiple ioctls may be queued and raising power
10045 	 * for every ioctl is time consuming.  If a timeout is
10046 	 * pending for the previous ioctl, cancel the timeout and
10047 	 * report idle status to pm because calls to pm_busy_component(9F)
10048 	 * are stacked.
10049 	 */
10050 	mutex_enter(&mpt->m_mutex);
10051 	if (mpt->m_options & MPTSAS_OPT_PM) {
10052 		if (mpt->m_pm_timeid != 0) {
10053 			timeout_id_t tid = mpt->m_pm_timeid;
10054 			mpt->m_pm_timeid = 0;
10055 			mutex_exit(&mpt->m_mutex);
10056 			(void) untimeout(tid);
10057 			/*
10058 			 * Report idle status for previous ioctl since
10059 			 * calls to pm_busy_component(9F) are stacked.
10060 			 */
10061 			(void) pm_idle_component(mpt->m_dip, 0);
10062 			mutex_enter(&mpt->m_mutex);
10063 		}
10064 		mpt->m_pm_timeid = timeout(mptsas_idle_pm, mpt,
10065 		    drv_usectohz((clock_t)mpt->m_pm_idle_delay * 1000000));
10066 	}
10067 	mutex_exit(&mpt->m_mutex);
10068 
10069 	return (status);
10070 }
10071 
10072 int
10073 mptsas_restart_ioc(mptsas_t *mpt) {
10074 	int		rval = DDI_SUCCESS;
10075 	mptsas_target_t	*ptgt = NULL;
10076 
10077 	ASSERT(mutex_owned(&mpt->m_mutex));
10078 
10079 	/*
10080 	 * Set all throttles to HOLD
10081 	 */
10082 	ptgt = (mptsas_target_t *)mptsas_hash_traverse(&mpt->m_active->m_tgttbl,
10083 	    MPTSAS_HASH_FIRST);
10084 	while (ptgt != NULL) {
10085 		mptsas_set_throttle(mpt, ptgt, HOLD_THROTTLE);
10086 
10087 		ptgt = (mptsas_target_t *)mptsas_hash_traverse(
10088 		    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
10089 	}
10090 
10091 	/*
10092 	 * Disable interrupts
10093 	 */
10094 	MPTSAS_DISABLE_INTR(mpt);
10095 
10096 	/*
10097 	 * Abort all commands: outstanding commands, commands in waitq and
10098 	 * tx_waitq.
10099 	 */
10100 	mptsas_flush_hba(mpt);
10101 
10102 	/*
10103 	 * Reinitialize the chip.
10104 	 */
10105 	if (mptsas_init_chip(mpt, FALSE) == DDI_FAILURE) {
10106 		rval = DDI_FAILURE;
10107 	}
10108 
10109 	/*
10110 	 * Enable interrupts again
10111 	 */
10112 	MPTSAS_ENABLE_INTR(mpt);
10113 
10114 	/*
10115 	 * If mptsas_init_chip was successful, update the driver data.
10116 	 */
10117 	if (rval == DDI_SUCCESS) {
10118 		mptsas_update_driver_data(mpt);
10119 	}
10120 
10121 	/*
10122 	 * Reset the throttles
10123 	 */
10124 	ptgt = (mptsas_target_t *)mptsas_hash_traverse(&mpt->m_active->m_tgttbl,
10125 	    MPTSAS_HASH_FIRST);
10126 	while (ptgt != NULL) {
10127 		mptsas_set_throttle(mpt, ptgt, MAX_THROTTLE);
10128 
10129 		ptgt = (mptsas_target_t *)mptsas_hash_traverse(
10130 		    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
10131 	}
10132 
10133 	mptsas_doneq_empty(mpt);
10134 
10135 	if (rval != DDI_SUCCESS) {
10136 		mptsas_fm_ereport(mpt, DDI_FM_DEVICE_NO_RESPONSE);
10137 		ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_LOST);
10138 	}
10139 	return (rval);
10140 }
10141 
10142 int
10143 mptsas_init_chip(mptsas_t *mpt, int first_time)
10144 {
10145 	ddi_dma_cookie_t	cookie;
10146 	uint32_t		i;
10147 	mptsas_slots_t		*new_active;
10148 
10149 	if (first_time == FALSE) {
10150 		/*
10151 		 * De-allocate buffers before re-allocating them using the
10152 		 * latest IOC facts.
10153 		 */
10154 		mptsas_hba_fini(mpt);
10155 
10156 		/*
10157 		 * Setup configuration space
10158 		 */
10159 		if (mptsas_config_space_init(mpt) == FALSE) {
10160 			mptsas_log(mpt, CE_WARN, "mptsas_config_space_init "
10161 			    "failed!");
10162 			goto fail;
10163 		}
10164 	}
10165 
10166 	/*
10167 	 * Check to see if the firmware image is valid
10168 	 */
10169 	if (ddi_get32(mpt->m_datap, &mpt->m_reg->HostDiagnostic) &
10170 	    MPI2_DIAG_FLASH_BAD_SIG) {
10171 		mptsas_log(mpt, CE_WARN, "mptsas bad flash signature!");
10172 		goto fail;
10173 	}
10174 
10175 	/*
10176 	 * Reset the chip
10177 	 */
10178 	if (mptsas_ioc_reset(mpt) == MPTSAS_RESET_FAIL) {
10179 		mptsas_log(mpt, CE_WARN, "hard reset failed!");
10180 		goto fail;
10181 	}
10182 	/*
10183 	 * IOC facts can change after a diag reset so all buffers that are
10184 	 * based on these numbers must be de-allocated and re-allocated.  Get
10185 	 * new IOC facts each time chip is initialized.
10186 	 */
10187 	if (mptsas_ioc_get_facts(mpt) == DDI_FAILURE) {
10188 		mptsas_log(mpt, CE_WARN, "mptsas_ioc_get_facts "
10189 		    "failed");
10190 		goto fail;
10191 	}
10192 	/*
10193 	 * Re-allocate active slots here if not the first reset.  Since
10194 	 * m_active could have a different number of slots allocated after a
10195 	 * reset, just de-allocate the old m_active structure and re-allocate a
10196 	 * new one.  Save the tables and IR info from the old m_active.
10197 	 */
10198 	if (first_time == FALSE) {
10199 		new_active = kmem_zalloc(MPTSAS_SLOTS_SIZE(mpt), KM_SLEEP);
10200 		if (new_active == NULL) {
10201 			mptsas_log(mpt, CE_WARN, "Re-alloc of active slots "
10202 			    "failed!");
10203 			goto fail;
10204 		} else {
10205 			new_active->m_n_slots = (mpt->m_max_requests - 2);
10206 			new_active->m_size = MPTSAS_SLOTS_SIZE(mpt);
10207 			new_active->m_tags = 1;
10208 			new_active->m_tgttbl = mpt->m_active->m_tgttbl;
10209 			new_active->m_smptbl = mpt->m_active->m_smptbl;
10210 			new_active->m_num_raid_configs =
10211 			    mpt->m_active->m_num_raid_configs;
10212 			for (i = 0; i < new_active->m_num_raid_configs; i++) {
10213 				new_active->m_raidconfig[i] =
10214 				    mpt->m_active->m_raidconfig[i];
10215 			}
10216 			kmem_free(mpt->m_active, mpt->m_active->m_size);
10217 			mpt->m_active = new_active;
10218 		}
10219 	}
10220 
10221 	/*
10222 	 * Allocate request message frames
10223 	 */
10224 	if (mptsas_alloc_request_frames(mpt) == DDI_FAILURE) {
10225 		mptsas_log(mpt, CE_WARN, "mptsas_alloc_request_frames "
10226 		    "failed");
10227 		goto fail;
10228 	}
10229 	/*
10230 	 * Allocate reply free queue
10231 	 */
10232 	if (mptsas_alloc_free_queue(mpt) == DDI_FAILURE) {
10233 		mptsas_log(mpt, CE_WARN, "mptsas_alloc_free_queue "
10234 		    "failed!");
10235 		goto fail;
10236 	}
10237 	/*
10238 	 * Allocate reply descriptor post queue
10239 	 */
10240 	if (mptsas_alloc_post_queue(mpt) == DDI_FAILURE) {
10241 		mptsas_log(mpt, CE_WARN, "mptsas_alloc_post_queue "
10242 		    "failed!");
10243 		goto fail;
10244 	}
10245 	/*
10246 	 * Allocate reply message frames
10247 	 */
10248 	if (mptsas_alloc_reply_frames(mpt) == DDI_FAILURE) {
10249 		mptsas_log(mpt, CE_WARN, "mptsas_alloc_reply_frames "
10250 		    "failed!");
10251 		goto fail;
10252 	}
10253 
10254 	/*
10255 	 * Re-Initialize ioc to operational state
10256 	 */
10257 	if (mptsas_ioc_init(mpt) == DDI_FAILURE) {
10258 		mptsas_log(mpt, CE_WARN, "mptsas_ioc_init failed");
10259 		goto fail;
10260 	}
10261 
10262 	mpt->m_replyh_args = kmem_zalloc(sizeof (m_replyh_arg_t) *
10263 	    mpt->m_max_replies, KM_SLEEP);
10264 
10265 	/*
10266 	 * Initialize reply post index and request index.  Reply free index is
10267 	 * initialized after the next loop.
10268 	 */
10269 	mpt->m_post_index = 0;
10270 
10271 	/*
10272 	 * Initialize the Reply Free Queue with the physical addresses of our
10273 	 * reply frames.
10274 	 */
10275 	cookie.dmac_address = mpt->m_reply_frame_dma_addr;
10276 	for (i = 0; i < mpt->m_free_queue_depth - 1; i++) {
10277 		ddi_put32(mpt->m_acc_free_queue_hdl,
10278 		    &((uint32_t *)(void *)mpt->m_free_queue)[i],
10279 		    cookie.dmac_address);
10280 		cookie.dmac_address += mpt->m_reply_frame_size;
10281 	}
10282 	(void) ddi_dma_sync(mpt->m_dma_free_queue_hdl, 0, 0,
10283 	    DDI_DMA_SYNC_FORDEV);
10284 
10285 	/*
10286 	 * Initialize the reply free index to one past the last frame on the
10287 	 * queue.  This will signify that the queue is empty to start with.
10288 	 */
10289 	mpt->m_free_index = i;
10290 	ddi_put32(mpt->m_datap, &mpt->m_reg->ReplyFreeHostIndex, i);
10291 
10292 	/*
10293 	 * Initialize the reply post queue to 0xFFFFFFFF,0xFFFFFFFF's.
10294 	 */
10295 	for (i = 0; i < mpt->m_post_queue_depth; i++) {
10296 		ddi_put64(mpt->m_acc_post_queue_hdl,
10297 		    &((uint64_t *)(void *)mpt->m_post_queue)[i],
10298 		    0xFFFFFFFFFFFFFFFF);
10299 	}
10300 	(void) ddi_dma_sync(mpt->m_dma_post_queue_hdl, 0, 0,
10301 	    DDI_DMA_SYNC_FORDEV);
10302 
10303 	/*
10304 	 * Enable ports
10305 	 */
10306 	if (mptsas_ioc_enable_port(mpt) == DDI_FAILURE) {
10307 		mptsas_log(mpt, CE_WARN, "mptsas_ioc_enable_port failed");
10308 		goto fail;
10309 	}
10310 
10311 	/*
10312 	 * First, make sure the HBA is set in "initiator" mode.  Once that
10313 	 * is complete, get the base WWID.
10314 	 */
10315 
10316 	if (first_time == TRUE) {
10317 		if (mptsas_set_initiator_mode(mpt)) {
10318 			mptsas_log(mpt, CE_WARN, "mptsas_set_initiator_mode "
10319 			    "failed!");
10320 			goto fail;
10321 		}
10322 
10323 		if (mptsas_get_manufacture_page5(mpt) == DDI_FAILURE) {
10324 			mptsas_log(mpt, CE_WARN,
10325 			    "mptsas_get_manufacture_page5 failed!");
10326 			goto fail;
10327 		}
10328 	}
10329 
10330 	/*
10331 	 * enable events
10332 	 */
10333 	if (first_time == FALSE) {
10334 		if (mptsas_ioc_enable_event_notification(mpt)) {
10335 			goto fail;
10336 		}
10337 	}
10338 
10339 	/*
10340 	 * We need checks in attach and these.
10341 	 * chip_init is called in mult. places
10342 	 */
10343 
10344 	if ((mptsas_check_dma_handle(mpt->m_dma_req_frame_hdl) !=
10345 	    DDI_SUCCESS) ||
10346 	    (mptsas_check_dma_handle(mpt->m_dma_reply_frame_hdl) !=
10347 	    DDI_SUCCESS) ||
10348 	    (mptsas_check_dma_handle(mpt->m_dma_free_queue_hdl) !=
10349 	    DDI_SUCCESS) ||
10350 	    (mptsas_check_dma_handle(mpt->m_dma_post_queue_hdl) !=
10351 	    DDI_SUCCESS) ||
10352 	    (mptsas_check_dma_handle(mpt->m_hshk_dma_hdl) !=
10353 	    DDI_SUCCESS)) {
10354 		ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_UNAFFECTED);
10355 		goto fail;
10356 	}
10357 
10358 	/* Check all acc handles */
10359 	if ((mptsas_check_acc_handle(mpt->m_datap) != DDI_SUCCESS) ||
10360 	    (mptsas_check_acc_handle(mpt->m_acc_req_frame_hdl) !=
10361 	    DDI_SUCCESS) ||
10362 	    (mptsas_check_acc_handle(mpt->m_acc_reply_frame_hdl) !=
10363 	    DDI_SUCCESS) ||
10364 	    (mptsas_check_acc_handle(mpt->m_acc_free_queue_hdl) !=
10365 	    DDI_SUCCESS) ||
10366 	    (mptsas_check_acc_handle(mpt->m_acc_post_queue_hdl) !=
10367 	    DDI_SUCCESS) ||
10368 	    (mptsas_check_acc_handle(mpt->m_hshk_acc_hdl) !=
10369 	    DDI_SUCCESS) ||
10370 	    (mptsas_check_acc_handle(mpt->m_config_handle) !=
10371 	    DDI_SUCCESS)) {
10372 		ddi_fm_service_impact(mpt->m_dip, DDI_SERVICE_UNAFFECTED);
10373 		goto fail;
10374 	}
10375 
10376 	return (DDI_SUCCESS);
10377 
10378 fail:
10379 	return (DDI_FAILURE);
10380 }
10381 
10382 static int
10383 mptsas_init_pm(mptsas_t *mpt)
10384 {
10385 	char		pmc_name[16];
10386 	char		*pmc[] = {
10387 				NULL,
10388 				"0=Off (PCI D3 State)",
10389 				"3=On (PCI D0 State)",
10390 				NULL
10391 			};
10392 	uint16_t	pmcsr_stat;
10393 
10394 	/*
10395 	 * If power management is supported by this chip, create
10396 	 * pm-components property for the power management framework
10397 	 */
10398 	(void) sprintf(pmc_name, "NAME=mptsas%d", mpt->m_instance);
10399 	pmc[0] = pmc_name;
10400 	if (ddi_prop_update_string_array(DDI_DEV_T_NONE, mpt->m_dip,
10401 	    "pm-components", pmc, 3) != DDI_PROP_SUCCESS) {
10402 		mpt->m_options &= ~MPTSAS_OPT_PM;
10403 		mptsas_log(mpt, CE_WARN,
10404 		    "mptsas%d: pm-component property creation failed.",
10405 		    mpt->m_instance);
10406 		return (DDI_FAILURE);
10407 	}
10408 
10409 	/*
10410 	 * Power on device.
10411 	 */
10412 	(void) pm_busy_component(mpt->m_dip, 0);
10413 	pmcsr_stat = pci_config_get16(mpt->m_config_handle,
10414 	    mpt->m_pmcsr_offset);
10415 	if ((pmcsr_stat & PCI_PMCSR_STATE_MASK) != PCI_PMCSR_D0) {
10416 		mptsas_log(mpt, CE_WARN, "mptsas%d: Power up the device",
10417 		    mpt->m_instance);
10418 		pci_config_put16(mpt->m_config_handle, mpt->m_pmcsr_offset,
10419 		    PCI_PMCSR_D0);
10420 	}
10421 	if (pm_power_has_changed(mpt->m_dip, 0, PM_LEVEL_D0) != DDI_SUCCESS) {
10422 		mptsas_log(mpt, CE_WARN, "pm_power_has_changed failed");
10423 		return (DDI_FAILURE);
10424 	}
10425 	mpt->m_power_level = PM_LEVEL_D0;
10426 	/*
10427 	 * Set pm idle delay.
10428 	 */
10429 	mpt->m_pm_idle_delay = ddi_prop_get_int(DDI_DEV_T_ANY,
10430 	    mpt->m_dip, 0, "mptsas-pm-idle-delay", MPTSAS_PM_IDLE_TIMEOUT);
10431 
10432 	return (DDI_SUCCESS);
10433 }
10434 
10435 /*
10436  * mptsas_add_intrs:
10437  *
10438  * Register FIXED or MSI interrupts.
10439  */
10440 static int
10441 mptsas_add_intrs(mptsas_t *mpt, int intr_type)
10442 {
10443 	dev_info_t	*dip = mpt->m_dip;
10444 	int		avail, actual, count = 0;
10445 	int		i, flag, ret;
10446 
10447 	NDBG6(("mptsas_add_intrs:interrupt type 0x%x", intr_type));
10448 
10449 	/* Get number of interrupts */
10450 	ret = ddi_intr_get_nintrs(dip, intr_type, &count);
10451 	if ((ret != DDI_SUCCESS) || (count <= 0)) {
10452 		mptsas_log(mpt, CE_WARN, "ddi_intr_get_nintrs() failed, "
10453 		    "ret %d count %d\n", ret, count);
10454 
10455 		return (DDI_FAILURE);
10456 	}
10457 
10458 	/* Get number of available interrupts */
10459 	ret = ddi_intr_get_navail(dip, intr_type, &avail);
10460 	if ((ret != DDI_SUCCESS) || (avail == 0)) {
10461 		mptsas_log(mpt, CE_WARN, "ddi_intr_get_navail() failed, "
10462 		    "ret %d avail %d\n", ret, avail);
10463 
10464 		return (DDI_FAILURE);
10465 	}
10466 
10467 	if (avail < count) {
10468 		mptsas_log(mpt, CE_NOTE, "ddi_intr_get_nvail returned %d, "
10469 		    "navail() returned %d", count, avail);
10470 	}
10471 
10472 	/* Mpt only have one interrupt routine */
10473 	if ((intr_type == DDI_INTR_TYPE_MSI) && (count > 1)) {
10474 		count = 1;
10475 	}
10476 
10477 	/* Allocate an array of interrupt handles */
10478 	mpt->m_intr_size = count * sizeof (ddi_intr_handle_t);
10479 	mpt->m_htable = kmem_alloc(mpt->m_intr_size, KM_SLEEP);
10480 
10481 	flag = DDI_INTR_ALLOC_NORMAL;
10482 
10483 	/* call ddi_intr_alloc() */
10484 	ret = ddi_intr_alloc(dip, mpt->m_htable, intr_type, 0,
10485 	    count, &actual, flag);
10486 
10487 	if ((ret != DDI_SUCCESS) || (actual == 0)) {
10488 		mptsas_log(mpt, CE_WARN, "ddi_intr_alloc() failed, ret %d\n",
10489 		    ret);
10490 		kmem_free(mpt->m_htable, mpt->m_intr_size);
10491 		return (DDI_FAILURE);
10492 	}
10493 
10494 	/* use interrupt count returned or abort? */
10495 	if (actual < count) {
10496 		mptsas_log(mpt, CE_NOTE, "Requested: %d, Received: %d\n",
10497 		    count, actual);
10498 	}
10499 
10500 	mpt->m_intr_cnt = actual;
10501 
10502 	/*
10503 	 * Get priority for first msi, assume remaining are all the same
10504 	 */
10505 	if ((ret = ddi_intr_get_pri(mpt->m_htable[0],
10506 	    &mpt->m_intr_pri)) != DDI_SUCCESS) {
10507 		mptsas_log(mpt, CE_WARN, "ddi_intr_get_pri() failed %d\n", ret);
10508 
10509 		/* Free already allocated intr */
10510 		for (i = 0; i < actual; i++) {
10511 			(void) ddi_intr_free(mpt->m_htable[i]);
10512 		}
10513 
10514 		kmem_free(mpt->m_htable, mpt->m_intr_size);
10515 		return (DDI_FAILURE);
10516 	}
10517 
10518 	/* Test for high level mutex */
10519 	if (mpt->m_intr_pri >= ddi_intr_get_hilevel_pri()) {
10520 		mptsas_log(mpt, CE_WARN, "mptsas_add_intrs: "
10521 		    "Hi level interrupt not supported\n");
10522 
10523 		/* Free already allocated intr */
10524 		for (i = 0; i < actual; i++) {
10525 			(void) ddi_intr_free(mpt->m_htable[i]);
10526 		}
10527 
10528 		kmem_free(mpt->m_htable, mpt->m_intr_size);
10529 		return (DDI_FAILURE);
10530 	}
10531 
10532 	/* Call ddi_intr_add_handler() */
10533 	for (i = 0; i < actual; i++) {
10534 		if ((ret = ddi_intr_add_handler(mpt->m_htable[i], mptsas_intr,
10535 		    (caddr_t)mpt, (caddr_t)(uintptr_t)i)) != DDI_SUCCESS) {
10536 			mptsas_log(mpt, CE_WARN, "ddi_intr_add_handler() "
10537 			    "failed %d\n", ret);
10538 
10539 			/* Free already allocated intr */
10540 			for (i = 0; i < actual; i++) {
10541 				(void) ddi_intr_free(mpt->m_htable[i]);
10542 			}
10543 
10544 			kmem_free(mpt->m_htable, mpt->m_intr_size);
10545 			return (DDI_FAILURE);
10546 		}
10547 	}
10548 
10549 	if ((ret = ddi_intr_get_cap(mpt->m_htable[0], &mpt->m_intr_cap))
10550 	    != DDI_SUCCESS) {
10551 		mptsas_log(mpt, CE_WARN, "ddi_intr_get_cap() failed %d\n", ret);
10552 
10553 		/* Free already allocated intr */
10554 		for (i = 0; i < actual; i++) {
10555 			(void) ddi_intr_free(mpt->m_htable[i]);
10556 		}
10557 
10558 		kmem_free(mpt->m_htable, mpt->m_intr_size);
10559 		return (DDI_FAILURE);
10560 	}
10561 
10562 	return (DDI_SUCCESS);
10563 }
10564 
10565 /*
10566  * mptsas_rem_intrs:
10567  *
10568  * Unregister FIXED or MSI interrupts
10569  */
10570 static void
10571 mptsas_rem_intrs(mptsas_t *mpt)
10572 {
10573 	int	i;
10574 
10575 	NDBG6(("mptsas_rem_intrs"));
10576 
10577 	/* Disable all interrupts */
10578 	if (mpt->m_intr_cap & DDI_INTR_FLAG_BLOCK) {
10579 		/* Call ddi_intr_block_disable() */
10580 		(void) ddi_intr_block_disable(mpt->m_htable, mpt->m_intr_cnt);
10581 	} else {
10582 		for (i = 0; i < mpt->m_intr_cnt; i++) {
10583 			(void) ddi_intr_disable(mpt->m_htable[i]);
10584 		}
10585 	}
10586 
10587 	/* Call ddi_intr_remove_handler() */
10588 	for (i = 0; i < mpt->m_intr_cnt; i++) {
10589 		(void) ddi_intr_remove_handler(mpt->m_htable[i]);
10590 		(void) ddi_intr_free(mpt->m_htable[i]);
10591 	}
10592 
10593 	kmem_free(mpt->m_htable, mpt->m_intr_size);
10594 }
10595 
10596 /*
10597  * The IO fault service error handling callback function
10598  */
10599 /*ARGSUSED*/
10600 static int
10601 mptsas_fm_error_cb(dev_info_t *dip, ddi_fm_error_t *err, const void *impl_data)
10602 {
10603 	/*
10604 	 * as the driver can always deal with an error in any dma or
10605 	 * access handle, we can just return the fme_status value.
10606 	 */
10607 	pci_ereport_post(dip, err, NULL);
10608 	return (err->fme_status);
10609 }
10610 
10611 /*
10612  * mptsas_fm_init - initialize fma capabilities and register with IO
10613  *               fault services.
10614  */
10615 static void
10616 mptsas_fm_init(mptsas_t *mpt)
10617 {
10618 	/*
10619 	 * Need to change iblock to priority for new MSI intr
10620 	 */
10621 	ddi_iblock_cookie_t	fm_ibc;
10622 
10623 	/* Only register with IO Fault Services if we have some capability */
10624 	if (mpt->m_fm_capabilities) {
10625 		/* Adjust access and dma attributes for FMA */
10626 		mpt->m_dev_acc_attr.devacc_attr_access |= DDI_FLAGERR_ACC;
10627 		mpt->m_msg_dma_attr.dma_attr_flags |= DDI_DMA_FLAGERR;
10628 		mpt->m_io_dma_attr.dma_attr_flags |= DDI_DMA_FLAGERR;
10629 
10630 		/*
10631 		 * Register capabilities with IO Fault Services.
10632 		 * mpt->m_fm_capabilities will be updated to indicate
10633 		 * capabilities actually supported (not requested.)
10634 		 */
10635 		ddi_fm_init(mpt->m_dip, &mpt->m_fm_capabilities, &fm_ibc);
10636 
10637 		/*
10638 		 * Initialize pci ereport capabilities if ereport
10639 		 * capable (should always be.)
10640 		 */
10641 		if (DDI_FM_EREPORT_CAP(mpt->m_fm_capabilities) ||
10642 		    DDI_FM_ERRCB_CAP(mpt->m_fm_capabilities)) {
10643 			pci_ereport_setup(mpt->m_dip);
10644 		}
10645 
10646 		/*
10647 		 * Register error callback if error callback capable.
10648 		 */
10649 		if (DDI_FM_ERRCB_CAP(mpt->m_fm_capabilities)) {
10650 			ddi_fm_handler_register(mpt->m_dip,
10651 			    mptsas_fm_error_cb, (void *) mpt);
10652 		}
10653 	}
10654 }
10655 
10656 /*
10657  * mptsas_fm_fini - Releases fma capabilities and un-registers with IO
10658  *               fault services.
10659  *
10660  */
10661 static void
10662 mptsas_fm_fini(mptsas_t *mpt)
10663 {
10664 	/* Only unregister FMA capabilities if registered */
10665 	if (mpt->m_fm_capabilities) {
10666 
10667 		/*
10668 		 * Un-register error callback if error callback capable.
10669 		 */
10670 
10671 		if (DDI_FM_ERRCB_CAP(mpt->m_fm_capabilities)) {
10672 			ddi_fm_handler_unregister(mpt->m_dip);
10673 		}
10674 
10675 		/*
10676 		 * Release any resources allocated by pci_ereport_setup()
10677 		 */
10678 
10679 		if (DDI_FM_EREPORT_CAP(mpt->m_fm_capabilities) ||
10680 		    DDI_FM_ERRCB_CAP(mpt->m_fm_capabilities)) {
10681 			pci_ereport_teardown(mpt->m_dip);
10682 		}
10683 
10684 		/* Unregister from IO Fault Services */
10685 		ddi_fm_fini(mpt->m_dip);
10686 
10687 		/* Adjust access and dma attributes for FMA */
10688 		mpt->m_dev_acc_attr.devacc_attr_access &= ~DDI_FLAGERR_ACC;
10689 		mpt->m_msg_dma_attr.dma_attr_flags &= ~DDI_DMA_FLAGERR;
10690 		mpt->m_io_dma_attr.dma_attr_flags &= ~DDI_DMA_FLAGERR;
10691 
10692 	}
10693 }
10694 
10695 int
10696 mptsas_check_acc_handle(ddi_acc_handle_t handle)
10697 {
10698 	ddi_fm_error_t	de;
10699 
10700 	if (handle == NULL)
10701 		return (DDI_FAILURE);
10702 	ddi_fm_acc_err_get(handle, &de, DDI_FME_VER0);
10703 	return (de.fme_status);
10704 }
10705 
10706 int
10707 mptsas_check_dma_handle(ddi_dma_handle_t handle)
10708 {
10709 	ddi_fm_error_t	de;
10710 
10711 	if (handle == NULL)
10712 		return (DDI_FAILURE);
10713 	ddi_fm_dma_err_get(handle, &de, DDI_FME_VER0);
10714 	return (de.fme_status);
10715 }
10716 
10717 void
10718 mptsas_fm_ereport(mptsas_t *mpt, char *detail)
10719 {
10720 	uint64_t	ena;
10721 	char		buf[FM_MAX_CLASS];
10722 
10723 	(void) snprintf(buf, FM_MAX_CLASS, "%s.%s", DDI_FM_DEVICE, detail);
10724 	ena = fm_ena_generate(0, FM_ENA_FMT1);
10725 	if (DDI_FM_EREPORT_CAP(mpt->m_fm_capabilities)) {
10726 		ddi_fm_ereport_post(mpt->m_dip, buf, ena, DDI_NOSLEEP,
10727 		    FM_VERSION, DATA_TYPE_UINT8, FM_EREPORT_VERS0, NULL);
10728 	}
10729 }
10730 
10731 static int
10732 mptsas_get_target_device_info(mptsas_t *mpt, uint32_t page_address,
10733     uint16_t *dev_handle, mptsas_target_t **pptgt)
10734 {
10735 	int		rval;
10736 	uint32_t	dev_info;
10737 	uint64_t	sas_wwn;
10738 	uint8_t		physport, phymask;
10739 	uint8_t		phynum, config, disk;
10740 	mptsas_slots_t	*slots = mpt->m_active;
10741 	uint64_t		devicename;
10742 	mptsas_target_t		*tmp_tgt = NULL;
10743 
10744 	ASSERT(*pptgt == NULL);
10745 
10746 	rval = mptsas_get_sas_device_page0(mpt, page_address, dev_handle,
10747 	    &sas_wwn, &dev_info, &physport, &phynum);
10748 	if (rval != DDI_SUCCESS) {
10749 		rval = DEV_INFO_FAIL_PAGE0;
10750 		return (rval);
10751 	}
10752 
10753 	if ((dev_info & (MPI2_SAS_DEVICE_INFO_SSP_TARGET |
10754 	    MPI2_SAS_DEVICE_INFO_SATA_DEVICE |
10755 	    MPI2_SAS_DEVICE_INFO_ATAPI_DEVICE)) == NULL) {
10756 		rval = DEV_INFO_WRONG_DEVICE_TYPE;
10757 		return (rval);
10758 	}
10759 
10760 	/*
10761 	 * Get SATA Device Name from SAS device page0 for
10762 	 * sata device, if device name doesn't exist, set m_sas_wwn to
10763 	 * 0 for direct attached SATA. For the device behind the expander
10764 	 * we still can use STP address assigned by expander.
10765 	 */
10766 	if (dev_info & (MPI2_SAS_DEVICE_INFO_SATA_DEVICE |
10767 	    MPI2_SAS_DEVICE_INFO_ATAPI_DEVICE)) {
10768 		mutex_exit(&mpt->m_mutex);
10769 		/* alloc a tmp_tgt to send the cmd */
10770 		tmp_tgt = kmem_zalloc(sizeof (struct mptsas_target),
10771 		    KM_SLEEP);
10772 		tmp_tgt->m_devhdl = *dev_handle;
10773 		tmp_tgt->m_deviceinfo = dev_info;
10774 		tmp_tgt->m_qfull_retries = QFULL_RETRIES;
10775 		tmp_tgt->m_qfull_retry_interval =
10776 		    drv_usectohz(QFULL_RETRY_INTERVAL * 1000);
10777 		tmp_tgt->m_t_throttle = MAX_THROTTLE;
10778 		devicename = mptsas_get_sata_guid(mpt, tmp_tgt, 0);
10779 		kmem_free(tmp_tgt, sizeof (struct mptsas_target));
10780 		mutex_enter(&mpt->m_mutex);
10781 		if (devicename != 0 && (((devicename >> 56) & 0xf0) == 0x50)) {
10782 			sas_wwn = devicename;
10783 		} else if (dev_info & MPI2_SAS_DEVICE_INFO_DIRECT_ATTACH) {
10784 			sas_wwn = 0;
10785 		}
10786 	}
10787 
10788 	/*
10789 	 * Check if the dev handle is for a Phys Disk. If so, set return value
10790 	 * and exit.  Don't add Phys Disks to hash.
10791 	 */
10792 	for (config = 0; config < slots->m_num_raid_configs; config++) {
10793 		for (disk = 0; disk < MPTSAS_MAX_DISKS_IN_CONFIG; disk++) {
10794 			if (*dev_handle == slots->m_raidconfig[config].
10795 			    m_physdisk_devhdl[disk]) {
10796 				rval = DEV_INFO_PHYS_DISK;
10797 				return (rval);
10798 			}
10799 		}
10800 	}
10801 
10802 	phymask = mptsas_physport_to_phymask(mpt, physport);
10803 	*pptgt = mptsas_tgt_alloc(&slots->m_tgttbl, *dev_handle, sas_wwn,
10804 	    dev_info, phymask, phynum);
10805 	if (*pptgt == NULL) {
10806 		mptsas_log(mpt, CE_WARN, "Failed to allocated target"
10807 		    "structure!");
10808 		rval = DEV_INFO_FAIL_ALLOC;
10809 		return (rval);
10810 	}
10811 	return (DEV_INFO_SUCCESS);
10812 }
10813 
10814 uint64_t
10815 mptsas_get_sata_guid(mptsas_t *mpt, mptsas_target_t *ptgt, int lun)
10816 {
10817 	uint64_t	sata_guid = 0, *pwwn = NULL;
10818 	int		target = ptgt->m_devhdl;
10819 	uchar_t		*inq83 = NULL;
10820 	int		inq83_len = 0xFF;
10821 	uchar_t		*dblk = NULL;
10822 	int		inq83_retry = 3;
10823 	int		rval = DDI_FAILURE;
10824 
10825 	inq83	= kmem_zalloc(inq83_len, KM_SLEEP);
10826 
10827 inq83_retry:
10828 	rval = mptsas_inquiry(mpt, ptgt, lun, 0x83, inq83,
10829 	    inq83_len, NULL, 1);
10830 	if (rval != DDI_SUCCESS) {
10831 		mptsas_log(mpt, CE_WARN, "!mptsas request inquiry page "
10832 		    "0x83 for target:%x, lun:%x failed!", target, lun);
10833 		goto out;
10834 	}
10835 	/* According to SAT2, the first descriptor is logic unit name */
10836 	dblk = &inq83[4];
10837 	if ((dblk[1] & 0x30) != 0) {
10838 		mptsas_log(mpt, CE_WARN, "!Descriptor is not lun associated.");
10839 		goto out;
10840 	}
10841 	pwwn = (uint64_t *)(void *)(&dblk[4]);
10842 	if ((dblk[4] & 0xf0) == 0x50) {
10843 		sata_guid = BE_64(*pwwn);
10844 		goto out;
10845 	} else if (dblk[4] == 'A') {
10846 		NDBG20(("SATA drive has no NAA format GUID."));
10847 		goto out;
10848 	} else {
10849 		/* The data is not ready, wait and retry */
10850 		inq83_retry--;
10851 		if (inq83_retry <= 0) {
10852 			goto out;
10853 		}
10854 		NDBG20(("The GUID is not ready, retry..."));
10855 		delay(1 * drv_usectohz(1000000));
10856 		goto inq83_retry;
10857 	}
10858 out:
10859 	kmem_free(inq83, inq83_len);
10860 	return (sata_guid);
10861 }
10862 static int
10863 mptsas_inquiry(mptsas_t *mpt, mptsas_target_t *ptgt, int lun, uchar_t page,
10864     unsigned char *buf, int len, int *reallen, uchar_t evpd)
10865 {
10866 	uchar_t			cdb[CDB_GROUP0];
10867 	struct scsi_address	ap;
10868 	struct buf		*data_bp = NULL;
10869 	int			resid = 0;
10870 	int			ret = DDI_FAILURE;
10871 
10872 	ASSERT(len <= 0xffff);
10873 
10874 	ap.a_target = MPTSAS_INVALID_DEVHDL;
10875 	ap.a_lun = (uchar_t)(lun);
10876 	ap.a_hba_tran = mpt->m_tran;
10877 
10878 	data_bp = scsi_alloc_consistent_buf(&ap,
10879 	    (struct buf *)NULL, len, B_READ, NULL_FUNC, NULL);
10880 	if (data_bp == NULL) {
10881 		return (ret);
10882 	}
10883 	bzero(cdb, CDB_GROUP0);
10884 	cdb[0] = SCMD_INQUIRY;
10885 	cdb[1] = evpd;
10886 	cdb[2] = page;
10887 	cdb[3] = (len & 0xff00) >> 8;
10888 	cdb[4] = (len & 0x00ff);
10889 	cdb[5] = 0;
10890 
10891 	ret = mptsas_send_scsi_cmd(mpt, &ap, ptgt, &cdb[0], CDB_GROUP0, data_bp,
10892 	    &resid);
10893 	if (ret == DDI_SUCCESS) {
10894 		if (reallen) {
10895 			*reallen = len - resid;
10896 		}
10897 		bcopy((caddr_t)data_bp->b_un.b_addr, buf, len);
10898 	}
10899 	if (data_bp) {
10900 		scsi_free_consistent_buf(data_bp);
10901 	}
10902 	return (ret);
10903 }
10904 
10905 static int
10906 mptsas_send_scsi_cmd(mptsas_t *mpt, struct scsi_address *ap,
10907     mptsas_target_t *ptgt, uchar_t *cdb, int cdblen, struct buf *data_bp,
10908     int *resid)
10909 {
10910 	struct scsi_pkt		*pktp = NULL;
10911 	scsi_hba_tran_t		*tran_clone = NULL;
10912 	mptsas_tgt_private_t	*tgt_private = NULL;
10913 	int			ret = DDI_FAILURE;
10914 
10915 	/*
10916 	 * scsi_hba_tran_t->tran_tgt_private is used to pass the address
10917 	 * information to scsi_init_pkt, allocate a scsi_hba_tran structure
10918 	 * to simulate the cmds from sd
10919 	 */
10920 	tran_clone = kmem_alloc(
10921 	    sizeof (scsi_hba_tran_t), KM_SLEEP);
10922 	if (tran_clone == NULL) {
10923 		goto out;
10924 	}
10925 	bcopy((caddr_t)mpt->m_tran,
10926 	    (caddr_t)tran_clone, sizeof (scsi_hba_tran_t));
10927 	tgt_private = kmem_alloc(
10928 	    sizeof (mptsas_tgt_private_t), KM_SLEEP);
10929 	if (tgt_private == NULL) {
10930 		goto out;
10931 	}
10932 	tgt_private->t_lun = ap->a_lun;
10933 	tgt_private->t_private = ptgt;
10934 	tran_clone->tran_tgt_private = tgt_private;
10935 	ap->a_hba_tran = tran_clone;
10936 
10937 	pktp = scsi_init_pkt(ap, (struct scsi_pkt *)NULL,
10938 	    data_bp, cdblen, sizeof (struct scsi_arq_status),
10939 	    0, PKT_CONSISTENT, NULL, NULL);
10940 	if (pktp == NULL) {
10941 		goto out;
10942 	}
10943 	bcopy(cdb, pktp->pkt_cdbp, cdblen);
10944 	pktp->pkt_flags = FLAG_NOPARITY;
10945 	if (scsi_poll(pktp) < 0) {
10946 		goto out;
10947 	}
10948 	if (((struct scsi_status *)pktp->pkt_scbp)->sts_chk) {
10949 		goto out;
10950 	}
10951 	if (resid != NULL) {
10952 		*resid = pktp->pkt_resid;
10953 	}
10954 
10955 	ret = DDI_SUCCESS;
10956 out:
10957 	if (pktp) {
10958 		scsi_destroy_pkt(pktp);
10959 	}
10960 	if (tran_clone) {
10961 		kmem_free(tran_clone, sizeof (scsi_hba_tran_t));
10962 	}
10963 	if (tgt_private) {
10964 		kmem_free(tgt_private, sizeof (mptsas_tgt_private_t));
10965 	}
10966 	return (ret);
10967 }
10968 static int
10969 mptsas_parse_address(char *name, uint64_t *wwid, uint8_t *phy, int *lun)
10970 {
10971 	char	*cp = NULL;
10972 	char	*ptr = NULL;
10973 	size_t	s = 0;
10974 	char	*wwid_str = NULL;
10975 	char	*lun_str = NULL;
10976 	long	lunnum;
10977 	long	phyid = -1;
10978 	int	rc = DDI_FAILURE;
10979 
10980 	ptr = name;
10981 	ASSERT(ptr[0] == 'w' || ptr[0] == 'p');
10982 	ptr++;
10983 	if ((cp = strchr(ptr, ',')) == NULL) {
10984 		return (DDI_FAILURE);
10985 	}
10986 
10987 	wwid_str = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP);
10988 	s = (uintptr_t)cp - (uintptr_t)ptr;
10989 
10990 	bcopy(ptr, wwid_str, s);
10991 	wwid_str[s] = '\0';
10992 
10993 	ptr = ++cp;
10994 
10995 	if ((cp = strchr(ptr, '\0')) == NULL) {
10996 		goto out;
10997 	}
10998 	lun_str =  kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP);
10999 	s = (uintptr_t)cp - (uintptr_t)ptr;
11000 
11001 	bcopy(ptr, lun_str, s);
11002 	lun_str[s] = '\0';
11003 
11004 	if (name[0] == 'p') {
11005 		rc = ddi_strtol(wwid_str, NULL, 0x10, &phyid);
11006 	} else {
11007 		rc = scsi_wwnstr_to_wwn(wwid_str, wwid);
11008 	}
11009 	if (rc != DDI_SUCCESS)
11010 		goto out;
11011 
11012 	if (phyid != -1) {
11013 		ASSERT(phyid < 8);
11014 		*phy = (uint8_t)phyid;
11015 	}
11016 	rc = ddi_strtol(lun_str, NULL, 0x10, &lunnum);
11017 	if (rc != 0)
11018 		goto out;
11019 
11020 	*lun = (int)lunnum;
11021 	rc = DDI_SUCCESS;
11022 out:
11023 	if (wwid_str)
11024 		kmem_free(wwid_str, SCSI_MAXNAMELEN);
11025 	if (lun_str)
11026 		kmem_free(lun_str, SCSI_MAXNAMELEN);
11027 
11028 	return (rc);
11029 }
11030 
11031 /*
11032  * mptsas_parse_smp_name() is to parse sas wwn string
11033  * which format is "wWWN"
11034  */
11035 static int
11036 mptsas_parse_smp_name(char *name, uint64_t *wwn)
11037 {
11038 	char	*ptr = name;
11039 
11040 	if (*ptr != 'w') {
11041 		return (DDI_FAILURE);
11042 	}
11043 
11044 	ptr++;
11045 	if (scsi_wwnstr_to_wwn(ptr, wwn)) {
11046 		return (DDI_FAILURE);
11047 	}
11048 	return (DDI_SUCCESS);
11049 }
11050 
11051 static int
11052 mptsas_bus_config(dev_info_t *pdip, uint_t flag,
11053     ddi_bus_config_op_t op, void *arg, dev_info_t **childp)
11054 {
11055 	int		ret = NDI_FAILURE;
11056 	int		circ = 0;
11057 	int		circ1 = 0;
11058 	mptsas_t	*mpt;
11059 	char		*ptr = NULL;
11060 	char		*devnm = NULL;
11061 	uint64_t	wwid = 0;
11062 	uint8_t		phy = 0xFF;
11063 	int		lun = 0;
11064 	uint_t		mflags = flag;
11065 
11066 	if (scsi_hba_iport_unit_address(pdip) == 0) {
11067 		return (DDI_FAILURE);
11068 	}
11069 
11070 	mpt = DIP2MPT(pdip);
11071 	if (!mpt) {
11072 		return (DDI_FAILURE);
11073 	}
11074 
11075 	/*
11076 	 * Hold the nexus across the bus_config
11077 	 */
11078 	ndi_devi_enter(scsi_vhci_dip, &circ);
11079 	ndi_devi_enter(pdip, &circ1);
11080 	switch (op) {
11081 	case BUS_CONFIG_ONE:
11082 		/* parse wwid/target name out of name given */
11083 		if ((ptr = strchr((char *)arg, '@')) == NULL) {
11084 			ret = NDI_FAILURE;
11085 			break;
11086 		}
11087 		ptr++;
11088 		if (strncmp((char *)arg, "smp", 3) == 0) {
11089 			/*
11090 			 * This is a SMP target device
11091 			 */
11092 			ret = mptsas_parse_smp_name(ptr, &wwid);
11093 			if (ret != DDI_SUCCESS) {
11094 				ret = NDI_FAILURE;
11095 				break;
11096 			}
11097 			ret = mptsas_config_smp(pdip, wwid, childp);
11098 		} else if ((ptr[0] == 'w') || (ptr[0] == 'p')) {
11099 			/*
11100 			 * OBP could pass down a non-canonical form
11101 			 * bootpath without LUN part when LUN is 0.
11102 			 * So driver need adjust the string.
11103 			 */
11104 			if (strchr(ptr, ',') == NULL) {
11105 				devnm = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP);
11106 				(void) sprintf(devnm, "%s,0", (char *)arg);
11107 				ptr = strchr(devnm, '@');
11108 				ptr++;
11109 			}
11110 
11111 			/*
11112 			 * The device path is wWWID format and the device
11113 			 * is not SMP target device.
11114 			 */
11115 			ret = mptsas_parse_address(ptr, &wwid, &phy, &lun);
11116 			if (ret != DDI_SUCCESS) {
11117 				ret = NDI_FAILURE;
11118 				break;
11119 			}
11120 			if (ptr[0] == 'w') {
11121 				ret = mptsas_config_one_addr(pdip, wwid,
11122 				    lun, childp);
11123 			} else if (ptr[0] == 'p') {
11124 				ret = mptsas_config_one_phy(pdip, phy, lun,
11125 				    childp);
11126 			}
11127 		} else {
11128 			ret = NDI_FAILURE;
11129 			break;
11130 		}
11131 
11132 		/*
11133 		 * DDI group instructed us to use this flag.
11134 		 */
11135 		mflags |= NDI_MDI_FALLBACK;
11136 		break;
11137 	case BUS_CONFIG_DRIVER:
11138 	case BUS_CONFIG_ALL:
11139 		mptsas_config_all(pdip);
11140 		ret = NDI_SUCCESS;
11141 		break;
11142 	}
11143 
11144 	if (ret == NDI_SUCCESS) {
11145 		ret = ndi_busop_bus_config(pdip, mflags, op,
11146 		    (devnm == NULL) ? arg : devnm, childp, 0);
11147 	}
11148 
11149 	ndi_devi_exit(pdip, circ1);
11150 	ndi_devi_exit(scsi_vhci_dip, circ);
11151 	if (devnm != NULL)
11152 		kmem_free(devnm, SCSI_MAXNAMELEN);
11153 	return (ret);
11154 }
11155 
11156 static int
11157 mptsas_probe_lun(dev_info_t *pdip, int lun, dev_info_t **dip,
11158     mptsas_target_t *ptgt)
11159 {
11160 	int			rval = DDI_FAILURE;
11161 	struct scsi_inquiry	*sd_inq = NULL;
11162 	mptsas_t		*mpt = DIP2MPT(pdip);
11163 
11164 	sd_inq = (struct scsi_inquiry *)kmem_alloc(SUN_INQSIZE, KM_SLEEP);
11165 
11166 	rval = mptsas_inquiry(mpt, ptgt, lun, 0, (uchar_t *)sd_inq,
11167 	    SUN_INQSIZE, 0, (uchar_t)0);
11168 
11169 	if ((rval == DDI_SUCCESS) && MPTSAS_VALID_LUN(sd_inq)) {
11170 		rval = mptsas_create_lun(pdip, sd_inq, dip, ptgt, lun);
11171 	} else {
11172 		rval = DDI_FAILURE;
11173 	}
11174 out:
11175 	kmem_free(sd_inq, SUN_INQSIZE);
11176 	return (rval);
11177 }
11178 
11179 static int
11180 mptsas_config_one_addr(dev_info_t *pdip, uint64_t sasaddr, int lun,
11181     dev_info_t **lundip)
11182 {
11183 	int		rval;
11184 	mptsas_t		*mpt = DIP2MPT(pdip);
11185 	int		phymask;
11186 	mptsas_target_t	*ptgt = NULL;
11187 
11188 	/*
11189 	 * Get the physical port associated to the iport
11190 	 */
11191 	phymask = ddi_prop_get_int(DDI_DEV_T_ANY, pdip, 0,
11192 	    "phymask", 0);
11193 
11194 	ptgt = mptsas_wwid_to_ptgt(mpt, phymask, sasaddr);
11195 	if (ptgt == NULL) {
11196 		/*
11197 		 * didn't match any device by searching
11198 		 */
11199 		return (DDI_FAILURE);
11200 	}
11201 	/*
11202 	 * If the LUN already exists and the status is online,
11203 	 * we just return the pointer to dev_info_t directly.
11204 	 * For the mdi_pathinfo node, we'll handle it in
11205 	 * mptsas_create_virt_lun()
11206 	 * TODO should be also in mptsas_handle_dr
11207 	 */
11208 
11209 	*lundip = mptsas_find_child_addr(pdip, sasaddr, lun);
11210 	if (*lundip != NULL) {
11211 		/*
11212 		 * TODO Another senario is, we hotplug the same disk
11213 		 * on the same slot, the devhdl changed, is this
11214 		 * possible?
11215 		 * tgt_private->t_private != ptgt
11216 		 */
11217 		if (sasaddr != ptgt->m_sas_wwn) {
11218 			/*
11219 			 * The device has changed although the devhdl is the
11220 			 * same (Enclosure mapping mode, change drive on the
11221 			 * same slot)
11222 			 */
11223 			return (DDI_FAILURE);
11224 		}
11225 		return (DDI_SUCCESS);
11226 	}
11227 
11228 	if (phymask == 0) {
11229 		/*
11230 		 * Configure IR volume
11231 		 */
11232 		rval =  mptsas_config_raid(pdip, ptgt->m_devhdl, lundip);
11233 		return (rval);
11234 	}
11235 	rval = mptsas_probe_lun(pdip, lun, lundip, ptgt);
11236 
11237 	return (rval);
11238 }
11239 
11240 static int
11241 mptsas_config_one_phy(dev_info_t *pdip, uint8_t phy, int lun,
11242     dev_info_t **lundip)
11243 {
11244 	int		rval;
11245 	mptsas_target_t	*ptgt = NULL;
11246 
11247 	ptgt = mptsas_phy_to_tgt(pdip, phy);
11248 	if (ptgt == NULL) {
11249 		/*
11250 		 * didn't match any device by searching
11251 		 */
11252 		return (DDI_FAILURE);
11253 	}
11254 
11255 	/*
11256 	 * If the LUN already exists and the status is online,
11257 	 * we just return the pointer to dev_info_t directly.
11258 	 * For the mdi_pathinfo node, we'll handle it in
11259 	 * mptsas_create_virt_lun().
11260 	 */
11261 
11262 	*lundip = mptsas_find_child_phy(pdip, phy);
11263 	if (*lundip != NULL) {
11264 		return (DDI_SUCCESS);
11265 	}
11266 
11267 	rval = mptsas_probe_lun(pdip, lun, lundip, ptgt);
11268 
11269 	return (rval);
11270 }
11271 
11272 static int
11273 mptsas_retrieve_lundata(int lun_cnt, uint8_t *buf, uint16_t *lun_num,
11274     uint8_t *lun_addr_type)
11275 {
11276 	uint32_t	lun_idx = 0;
11277 
11278 	ASSERT(lun_num != NULL);
11279 	ASSERT(lun_addr_type != NULL);
11280 
11281 	lun_idx = (lun_cnt + 1) * MPTSAS_SCSI_REPORTLUNS_ADDRESS_SIZE;
11282 	/* determine report luns addressing type */
11283 	switch (buf[lun_idx] & MPTSAS_SCSI_REPORTLUNS_ADDRESS_MASK) {
11284 		/*
11285 		 * Vendors in the field have been found to be concatenating
11286 		 * bus/target/lun to equal the complete lun value instead
11287 		 * of switching to flat space addressing
11288 		 */
11289 		/* 00b - peripheral device addressing method */
11290 	case MPTSAS_SCSI_REPORTLUNS_ADDRESS_PERIPHERAL:
11291 		/* FALLTHRU */
11292 		/* 10b - logical unit addressing method */
11293 	case MPTSAS_SCSI_REPORTLUNS_ADDRESS_LOGICAL_UNIT:
11294 		/* FALLTHRU */
11295 		/* 01b - flat space addressing method */
11296 	case MPTSAS_SCSI_REPORTLUNS_ADDRESS_FLAT_SPACE:
11297 		/* byte0 bit0-5=msb lun byte1 bit0-7=lsb lun */
11298 		*lun_addr_type = (buf[lun_idx] &
11299 		    MPTSAS_SCSI_REPORTLUNS_ADDRESS_MASK) >> 6;
11300 		*lun_num = (buf[lun_idx] & 0x3F) << 8;
11301 		*lun_num |= buf[lun_idx + 1];
11302 		return (DDI_SUCCESS);
11303 	default:
11304 		return (DDI_FAILURE);
11305 	}
11306 }
11307 
11308 static int
11309 mptsas_config_luns(dev_info_t *pdip, mptsas_target_t *ptgt)
11310 {
11311 	struct buf		*repluns_bp = NULL;
11312 	struct scsi_address	ap;
11313 	uchar_t			cdb[CDB_GROUP5];
11314 	int			ret = DDI_FAILURE;
11315 	int			retry = 0;
11316 	int			lun_list_len = 0;
11317 	uint16_t		lun_num = 0;
11318 	uint8_t			lun_addr_type = 0;
11319 	uint32_t		lun_cnt = 0;
11320 	uint32_t		lun_total = 0;
11321 	dev_info_t		*cdip = NULL;
11322 	uint16_t		*saved_repluns = NULL;
11323 	char			*buffer = NULL;
11324 	int			buf_len = 128;
11325 	mptsas_t		*mpt = DIP2MPT(pdip);
11326 	uint64_t		sas_wwn = 0;
11327 	uint8_t			phy = 0xFF;
11328 	uint32_t		dev_info = 0;
11329 
11330 	mutex_enter(&mpt->m_mutex);
11331 	sas_wwn = ptgt->m_sas_wwn;
11332 	phy = ptgt->m_phynum;
11333 	dev_info = ptgt->m_deviceinfo;
11334 	mutex_exit(&mpt->m_mutex);
11335 
11336 	if (sas_wwn == 0) {
11337 		/*
11338 		 * It's a SATA without Device Name
11339 		 * So don't try multi-LUNs
11340 		 */
11341 		if (mptsas_find_child_phy(pdip, phy)) {
11342 			return (DDI_SUCCESS);
11343 		} else {
11344 			/*
11345 			 * need configure and create node
11346 			 */
11347 			return (DDI_FAILURE);
11348 		}
11349 	}
11350 
11351 	/*
11352 	 * WWN (SAS address or Device Name exist)
11353 	 */
11354 	if (dev_info & (MPI2_SAS_DEVICE_INFO_SATA_DEVICE |
11355 	    MPI2_SAS_DEVICE_INFO_ATAPI_DEVICE)) {
11356 		/*
11357 		 * SATA device with Device Name
11358 		 * So don't try multi-LUNs
11359 		 */
11360 		if (mptsas_find_child_addr(pdip, sas_wwn, 0)) {
11361 			return (DDI_SUCCESS);
11362 		} else {
11363 			return (DDI_FAILURE);
11364 		}
11365 	}
11366 
11367 	do {
11368 		ap.a_target = MPTSAS_INVALID_DEVHDL;
11369 		ap.a_lun = 0;
11370 		ap.a_hba_tran = mpt->m_tran;
11371 		repluns_bp = scsi_alloc_consistent_buf(&ap,
11372 		    (struct buf *)NULL, buf_len, B_READ, NULL_FUNC, NULL);
11373 		if (repluns_bp == NULL) {
11374 			retry++;
11375 			continue;
11376 		}
11377 		bzero(cdb, CDB_GROUP5);
11378 		cdb[0] = SCMD_REPORT_LUNS;
11379 		cdb[6] = (buf_len & 0xff000000) >> 24;
11380 		cdb[7] = (buf_len & 0x00ff0000) >> 16;
11381 		cdb[8] = (buf_len & 0x0000ff00) >> 8;
11382 		cdb[9] = (buf_len & 0x000000ff);
11383 
11384 		ret = mptsas_send_scsi_cmd(mpt, &ap, ptgt, &cdb[0], CDB_GROUP5,
11385 		    repluns_bp, NULL);
11386 		if (ret != DDI_SUCCESS) {
11387 			scsi_free_consistent_buf(repluns_bp);
11388 			retry++;
11389 			continue;
11390 		}
11391 		lun_list_len = BE_32(*(int *)((void *)(
11392 		    repluns_bp->b_un.b_addr)));
11393 		if (buf_len >= lun_list_len + 8) {
11394 			ret = DDI_SUCCESS;
11395 			break;
11396 		}
11397 		scsi_free_consistent_buf(repluns_bp);
11398 		buf_len = lun_list_len + 8;
11399 
11400 	} while (retry < 3);
11401 
11402 	if (ret != DDI_SUCCESS)
11403 		return (ret);
11404 	buffer = (char *)repluns_bp->b_un.b_addr;
11405 	/*
11406 	 * find out the number of luns returned by the SCSI ReportLun call
11407 	 * and allocate buffer space
11408 	 */
11409 	lun_total = lun_list_len / MPTSAS_SCSI_REPORTLUNS_ADDRESS_SIZE;
11410 	saved_repluns = kmem_zalloc(sizeof (uint16_t) * lun_total, KM_SLEEP);
11411 	if (saved_repluns == NULL) {
11412 		scsi_free_consistent_buf(repluns_bp);
11413 		return (DDI_FAILURE);
11414 	}
11415 	for (lun_cnt = 0; lun_cnt < lun_total; lun_cnt++) {
11416 		if (mptsas_retrieve_lundata(lun_cnt, (uint8_t *)(buffer),
11417 		    &lun_num, &lun_addr_type) != DDI_SUCCESS) {
11418 			continue;
11419 		}
11420 		saved_repluns[lun_cnt] = lun_num;
11421 		if (cdip = mptsas_find_child_addr(pdip, sas_wwn, lun_num))
11422 			ret = DDI_SUCCESS;
11423 		else
11424 			ret = mptsas_probe_lun(pdip, lun_num, &cdip,
11425 			    ptgt);
11426 		if ((ret == DDI_SUCCESS) && (cdip != NULL)) {
11427 			(void) ndi_prop_remove(DDI_DEV_T_NONE, cdip,
11428 			    MPTSAS_DEV_GONE);
11429 		}
11430 	}
11431 	mptsas_offline_missed_luns(pdip, saved_repluns, lun_total, ptgt);
11432 	kmem_free(saved_repluns, sizeof (uint16_t) * lun_total);
11433 	scsi_free_consistent_buf(repluns_bp);
11434 	return (DDI_SUCCESS);
11435 }
11436 
11437 static int
11438 mptsas_config_raid(dev_info_t *pdip, uint16_t target, dev_info_t **dip)
11439 {
11440 	int			rval = DDI_FAILURE;
11441 	struct scsi_inquiry	*sd_inq = NULL;
11442 	mptsas_t		*mpt = DIP2MPT(pdip);
11443 	mptsas_target_t		*ptgt = NULL;
11444 
11445 	mutex_enter(&mpt->m_mutex);
11446 	ptgt = mptsas_search_by_devhdl(&mpt->m_active->m_tgttbl, target);
11447 	mutex_exit(&mpt->m_mutex);
11448 	if (ptgt == NULL) {
11449 		mptsas_log(mpt, CE_WARN, "Volume with VolDevHandle of 0x%x "
11450 		    "not found.", target);
11451 		return (rval);
11452 	}
11453 
11454 	sd_inq = (struct scsi_inquiry *)kmem_alloc(SUN_INQSIZE, KM_SLEEP);
11455 	rval = mptsas_inquiry(mpt, ptgt, 0, 0, (uchar_t *)sd_inq,
11456 	    SUN_INQSIZE, 0, (uchar_t)0);
11457 
11458 	if ((rval == DDI_SUCCESS) && MPTSAS_VALID_LUN(sd_inq)) {
11459 		rval = mptsas_create_phys_lun(pdip, sd_inq, NULL, dip, ptgt,
11460 		    0);
11461 	} else {
11462 		rval = DDI_FAILURE;
11463 	}
11464 
11465 out:
11466 	kmem_free(sd_inq, SUN_INQSIZE);
11467 	return (rval);
11468 }
11469 
11470 /*
11471  * configure all RAID volumes for virtual iport
11472  */
11473 static void
11474 mptsas_config_all_viport(dev_info_t *pdip)
11475 {
11476 	mptsas_t	*mpt = DIP2MPT(pdip);
11477 	int		config, vol;
11478 	int		target;
11479 	dev_info_t	*lundip = NULL;
11480 	mptsas_slots_t	*slots = mpt->m_active;
11481 
11482 	/*
11483 	 * Get latest RAID info and search for any Volume DevHandles.  If any
11484 	 * are found, configure the volume.
11485 	 */
11486 	mutex_enter(&mpt->m_mutex);
11487 	for (config = 0; config < slots->m_num_raid_configs; config++) {
11488 		for (vol = 0; vol < MPTSAS_MAX_RAIDVOLS; vol++) {
11489 			if (slots->m_raidconfig[config].m_raidvol[vol].m_israid
11490 			    == 1) {
11491 				target = slots->m_raidconfig[config].
11492 				    m_raidvol[vol].m_raidhandle;
11493 				mutex_exit(&mpt->m_mutex);
11494 				(void) mptsas_config_raid(pdip, target,
11495 				    &lundip);
11496 				mutex_enter(&mpt->m_mutex);
11497 			}
11498 		}
11499 	}
11500 	mutex_exit(&mpt->m_mutex);
11501 }
11502 
11503 static void
11504 mptsas_offline_missed_luns(dev_info_t *pdip, uint16_t *repluns,
11505     int lun_cnt, mptsas_target_t *ptgt)
11506 {
11507 	dev_info_t	*child = NULL, *savechild = NULL;
11508 	mdi_pathinfo_t	*pip = NULL, *savepip = NULL;
11509 	uint64_t	sas_wwn, wwid;
11510 	uint8_t		phy;
11511 	int		lun;
11512 	int		i;
11513 	int		find;
11514 	char		*addr;
11515 	char		*nodename;
11516 	mptsas_t	*mpt = DIP2MPT(pdip);
11517 
11518 	mutex_enter(&mpt->m_mutex);
11519 	wwid = ptgt->m_sas_wwn;
11520 	mutex_exit(&mpt->m_mutex);
11521 
11522 	child = ddi_get_child(pdip);
11523 	while (child) {
11524 		find = 0;
11525 		savechild = child;
11526 		child = ddi_get_next_sibling(child);
11527 
11528 		nodename = ddi_node_name(savechild);
11529 		if (strcmp(nodename, "smp") == 0) {
11530 			continue;
11531 		}
11532 
11533 		addr = ddi_get_name_addr(savechild);
11534 		if (addr == NULL) {
11535 			continue;
11536 		}
11537 
11538 		if (mptsas_parse_address(addr, &sas_wwn, &phy, &lun) !=
11539 		    DDI_SUCCESS) {
11540 			continue;
11541 		}
11542 
11543 		if (wwid == sas_wwn) {
11544 			for (i = 0; i < lun_cnt; i++) {
11545 				if (repluns[i] == lun) {
11546 					find = 1;
11547 					break;
11548 				}
11549 			}
11550 		} else {
11551 			continue;
11552 		}
11553 		if (find == 0) {
11554 			/*
11555 			 * The lun has not been there already
11556 			 */
11557 			(void) mptsas_offline_lun(pdip, savechild, NULL,
11558 			    NDI_DEVI_REMOVE);
11559 		}
11560 	}
11561 
11562 	pip = mdi_get_next_client_path(pdip, NULL);
11563 	while (pip) {
11564 		find = 0;
11565 		savepip = pip;
11566 		addr = MDI_PI(pip)->pi_addr;
11567 
11568 		pip = mdi_get_next_client_path(pdip, pip);
11569 
11570 		if (addr == NULL) {
11571 			continue;
11572 		}
11573 
11574 		if (mptsas_parse_address(addr, &sas_wwn, &phy,
11575 		    &lun) != DDI_SUCCESS) {
11576 			continue;
11577 		}
11578 
11579 		if (sas_wwn == wwid) {
11580 			for (i = 0; i < lun_cnt; i++) {
11581 				if (repluns[i] == lun) {
11582 					find = 1;
11583 					break;
11584 				}
11585 			}
11586 		} else {
11587 			continue;
11588 		}
11589 
11590 		if (find == 0) {
11591 			/*
11592 			 * The lun has not been there already
11593 			 */
11594 			(void) mptsas_offline_lun(pdip, NULL, savepip,
11595 			    NDI_DEVI_REMOVE);
11596 		}
11597 	}
11598 }
11599 
11600 void
11601 mptsas_update_hashtab(struct mptsas *mpt)
11602 {
11603 	uint32_t	page_address;
11604 	int		rval = 0;
11605 	uint16_t	dev_handle;
11606 	mptsas_target_t	*ptgt = NULL;
11607 	mptsas_smp_t	smp_node;
11608 
11609 	/*
11610 	 * Get latest RAID info.
11611 	 */
11612 	(void) mptsas_get_raid_info(mpt);
11613 
11614 	dev_handle = mpt->m_smp_devhdl;
11615 	for (; mpt->m_done_traverse_smp == 0; ) {
11616 		page_address = (MPI2_SAS_EXPAND_PGAD_FORM_GET_NEXT_HNDL &
11617 		    MPI2_SAS_EXPAND_PGAD_FORM_MASK) | (uint32_t)dev_handle;
11618 		if (mptsas_get_sas_expander_page0(mpt, page_address, &smp_node)
11619 		    != DDI_SUCCESS) {
11620 			break;
11621 		}
11622 		mpt->m_smp_devhdl = dev_handle = smp_node.m_devhdl;
11623 		(void) mptsas_smp_alloc(&mpt->m_active->m_smptbl, &smp_node);
11624 	}
11625 
11626 	/*
11627 	 * Config target devices
11628 	 */
11629 	dev_handle = mpt->m_dev_handle;
11630 
11631 	/*
11632 	 * Do loop to get sas device page 0 by GetNextHandle till the
11633 	 * the last handle. If the sas device is a SATA/SSP target,
11634 	 * we try to config it.
11635 	 */
11636 	for (; mpt->m_done_traverse_dev == 0; ) {
11637 		ptgt = NULL;
11638 		page_address =
11639 		    (MPI2_SAS_DEVICE_PGAD_FORM_GET_NEXT_HANDLE &
11640 		    MPI2_SAS_DEVICE_PGAD_FORM_MASK) |
11641 		    (uint32_t)dev_handle;
11642 		rval = mptsas_get_target_device_info(mpt, page_address,
11643 		    &dev_handle, &ptgt);
11644 		if ((rval == DEV_INFO_FAIL_PAGE0) ||
11645 		    (rval == DEV_INFO_FAIL_ALLOC)) {
11646 			break;
11647 		}
11648 
11649 		mpt->m_dev_handle = dev_handle;
11650 	}
11651 
11652 }
11653 
11654 void
11655 mptsas_invalid_hashtab(mptsas_hash_table_t *hashtab)
11656 {
11657 	mptsas_hash_data_t *data;
11658 	data = mptsas_hash_traverse(hashtab, MPTSAS_HASH_FIRST);
11659 	while (data != NULL) {
11660 		data->devhdl = MPTSAS_INVALID_DEVHDL;
11661 		data->device_info = 0;
11662 		/*
11663 		 * For tgttbl, clear dr_flag.
11664 		 */
11665 		data->dr_flag = MPTSAS_DR_INACTIVE;
11666 		data = mptsas_hash_traverse(hashtab, MPTSAS_HASH_NEXT);
11667 	}
11668 }
11669 
11670 void
11671 mptsas_update_driver_data(struct mptsas *mpt)
11672 {
11673 	/*
11674 	 * TODO after hard reset, update the driver data structures
11675 	 * 1. update port/phymask mapping table mpt->m_phy_info
11676 	 * 2. invalid all the entries in hash table
11677 	 *    m_devhdl = 0xffff and m_deviceinfo = 0
11678 	 * 3. call sas_device_page/expander_page to update hash table
11679 	 */
11680 	mptsas_update_phymask(mpt);
11681 	/*
11682 	 * Invalid the existing entries
11683 	 */
11684 	mptsas_invalid_hashtab(&mpt->m_active->m_tgttbl);
11685 	mptsas_invalid_hashtab(&mpt->m_active->m_smptbl);
11686 	mpt->m_done_traverse_dev = 0;
11687 	mpt->m_done_traverse_smp = 0;
11688 	mpt->m_dev_handle = mpt->m_smp_devhdl = MPTSAS_INVALID_DEVHDL;
11689 	mptsas_update_hashtab(mpt);
11690 }
11691 
11692 static void
11693 mptsas_config_all(dev_info_t *pdip)
11694 {
11695 	dev_info_t	*smpdip = NULL;
11696 	mptsas_t	*mpt = DIP2MPT(pdip);
11697 	int		phymask = 0;
11698 	uint8_t		phy_mask;
11699 	mptsas_target_t	*ptgt = NULL;
11700 	mptsas_smp_t	*psmp;
11701 
11702 	/*
11703 	 * Get the phymask associated to the iport
11704 	 */
11705 	phymask = ddi_prop_get_int(DDI_DEV_T_ANY, pdip, 0,
11706 	    "phymask", 0);
11707 
11708 	/*
11709 	 * Enumerate RAID volumes here (phymask == 0).
11710 	 */
11711 	if (phymask == 0) {
11712 		mptsas_config_all_viport(pdip);
11713 		return;
11714 	}
11715 
11716 	mutex_enter(&mpt->m_mutex);
11717 
11718 	if (!mpt->m_done_traverse_dev || !mpt->m_done_traverse_smp) {
11719 		mptsas_update_hashtab(mpt);
11720 	}
11721 
11722 	psmp = (mptsas_smp_t *)mptsas_hash_traverse(&mpt->m_active->m_smptbl,
11723 	    MPTSAS_HASH_FIRST);
11724 	while (psmp != NULL) {
11725 		phy_mask = psmp->m_phymask;
11726 		if (phy_mask == phymask) {
11727 			smpdip = NULL;
11728 			mutex_exit(&mpt->m_mutex);
11729 			(void) mptsas_online_smp(pdip, psmp, &smpdip);
11730 			mutex_enter(&mpt->m_mutex);
11731 		}
11732 		psmp = (mptsas_smp_t *)mptsas_hash_traverse(
11733 		    &mpt->m_active->m_smptbl, MPTSAS_HASH_NEXT);
11734 	}
11735 
11736 	ptgt = (mptsas_target_t *)mptsas_hash_traverse(&mpt->m_active->m_tgttbl,
11737 	    MPTSAS_HASH_FIRST);
11738 	while (ptgt != NULL) {
11739 		phy_mask = ptgt->m_phymask;
11740 		if (phy_mask == phymask) {
11741 			mutex_exit(&mpt->m_mutex);
11742 			(void) mptsas_config_target(pdip, ptgt);
11743 			mutex_enter(&mpt->m_mutex);
11744 		}
11745 
11746 		ptgt = (mptsas_target_t *)mptsas_hash_traverse(
11747 		    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
11748 	}
11749 	mutex_exit(&mpt->m_mutex);
11750 }
11751 
11752 static int
11753 mptsas_config_target(dev_info_t *pdip, mptsas_target_t *ptgt)
11754 {
11755 	int		rval = DDI_FAILURE;
11756 	dev_info_t	*tdip;
11757 
11758 	rval = mptsas_config_luns(pdip, ptgt);
11759 	if (rval != DDI_SUCCESS) {
11760 		/*
11761 		 * The return value means the SCMD_REPORT_LUNS
11762 		 * did not execute successfully. The target maybe
11763 		 * doesn't support such command.
11764 		 */
11765 		rval = mptsas_probe_lun(pdip, 0, &tdip, ptgt);
11766 	}
11767 	return (rval);
11768 }
11769 
11770 /*
11771  * Return fail if not all the childs/paths are freed.
11772  * if there is any path under the HBA, the return value will be always fail
11773  * because we didn't call mdi_pi_free for path
11774  */
11775 static int
11776 mptsas_offline_target(dev_info_t *pdip, char *name)
11777 {
11778 	dev_info_t		*child = NULL, *prechild = NULL;
11779 	mdi_pathinfo_t		*pip = NULL, *savepip = NULL;
11780 	int			tmp_rval, rval = DDI_SUCCESS;
11781 	char			*addr, *cp;
11782 	size_t			s;
11783 	mptsas_t		*mpt = DIP2MPT(pdip);
11784 
11785 	child = ddi_get_child(pdip);
11786 	while (child) {
11787 		addr = ddi_get_name_addr(child);
11788 		prechild = child;
11789 		child = ddi_get_next_sibling(child);
11790 
11791 		if (addr == NULL) {
11792 			continue;
11793 		}
11794 		if ((cp = strchr(addr, ',')) == NULL) {
11795 			continue;
11796 		}
11797 
11798 		s = (uintptr_t)cp - (uintptr_t)addr;
11799 
11800 		if (strncmp(addr, name, s) != 0) {
11801 			continue;
11802 		}
11803 
11804 		tmp_rval = mptsas_offline_lun(pdip, prechild, NULL,
11805 		    NDI_DEVI_REMOVE);
11806 		if (tmp_rval != DDI_SUCCESS) {
11807 			rval = DDI_FAILURE;
11808 			if (ndi_prop_create_boolean(DDI_DEV_T_NONE,
11809 			    prechild, MPTSAS_DEV_GONE) !=
11810 			    DDI_PROP_SUCCESS) {
11811 				mptsas_log(mpt, CE_WARN, "mptsas driver "
11812 				    "unable to create property for "
11813 				    "SAS %s (MPTSAS_DEV_GONE)", addr);
11814 			}
11815 		}
11816 	}
11817 
11818 	pip = mdi_get_next_client_path(pdip, NULL);
11819 	while (pip) {
11820 		addr = MDI_PI(pip)->pi_addr;
11821 		savepip = pip;
11822 		pip = mdi_get_next_client_path(pdip, pip);
11823 		if (addr == NULL) {
11824 			continue;
11825 		}
11826 
11827 		if ((cp = strchr(addr, ',')) == NULL) {
11828 			continue;
11829 		}
11830 
11831 		s = (uintptr_t)cp - (uintptr_t)addr;
11832 
11833 		if (strncmp(addr, name, s) != 0) {
11834 			continue;
11835 		}
11836 
11837 		(void) mptsas_offline_lun(pdip, NULL, savepip,
11838 		    NDI_DEVI_REMOVE);
11839 		/*
11840 		 * driver will not invoke mdi_pi_free, so path will not
11841 		 * be freed forever, return DDI_FAILURE.
11842 		 */
11843 		rval = DDI_FAILURE;
11844 	}
11845 	return (rval);
11846 }
11847 
11848 static int
11849 mptsas_offline_lun(dev_info_t *pdip, dev_info_t *rdip,
11850     mdi_pathinfo_t *rpip, uint_t flags)
11851 {
11852 	int		rval = DDI_FAILURE;
11853 	char		*devname;
11854 	dev_info_t	*cdip, *parent;
11855 
11856 	if (rpip != NULL) {
11857 		parent = scsi_vhci_dip;
11858 		cdip = mdi_pi_get_client(rpip);
11859 	} else if (rdip != NULL) {
11860 		parent = pdip;
11861 		cdip = rdip;
11862 	} else {
11863 		return (DDI_FAILURE);
11864 	}
11865 
11866 	/*
11867 	 * Make sure node is attached otherwise
11868 	 * it won't have related cache nodes to
11869 	 * clean up.  i_ddi_devi_attached is
11870 	 * similiar to i_ddi_node_state(cdip) >=
11871 	 * DS_ATTACHED.
11872 	 */
11873 	if (i_ddi_devi_attached(cdip)) {
11874 
11875 		/* Get full devname */
11876 		devname = kmem_alloc(MAXNAMELEN + 1, KM_SLEEP);
11877 		(void) ddi_deviname(cdip, devname);
11878 		/* Clean cache */
11879 		(void) devfs_clean(parent, devname + 1,
11880 		    DV_CLEAN_FORCE);
11881 		kmem_free(devname, MAXNAMELEN + 1);
11882 	}
11883 	if (rpip != NULL) {
11884 		if (MDI_PI_IS_OFFLINE(rpip)) {
11885 			rval = DDI_SUCCESS;
11886 		} else {
11887 			rval = mdi_pi_offline(rpip, 0);
11888 		}
11889 	} else {
11890 		rval = ndi_devi_offline(cdip, flags);
11891 	}
11892 
11893 	return (rval);
11894 }
11895 
11896 static dev_info_t *
11897 mptsas_find_smp_child(dev_info_t *parent, char *str_wwn)
11898 {
11899 	dev_info_t	*child = NULL;
11900 	char		*smp_wwn = NULL;
11901 
11902 	child = ddi_get_child(parent);
11903 	while (child) {
11904 		if (ddi_prop_lookup_string(DDI_DEV_T_ANY, child,
11905 		    DDI_PROP_DONTPASS, SMP_WWN, &smp_wwn)
11906 		    != DDI_SUCCESS) {
11907 			child = ddi_get_next_sibling(child);
11908 			continue;
11909 		}
11910 
11911 		if (strcmp(smp_wwn, str_wwn) == 0) {
11912 			ddi_prop_free(smp_wwn);
11913 			break;
11914 		}
11915 		child = ddi_get_next_sibling(child);
11916 		ddi_prop_free(smp_wwn);
11917 	}
11918 	return (child);
11919 }
11920 
11921 static int
11922 mptsas_offline_smp(dev_info_t *pdip, mptsas_smp_t *smp_node, uint_t flags)
11923 {
11924 	int		rval = DDI_FAILURE;
11925 	char		*devname;
11926 	char		wwn_str[MPTSAS_WWN_STRLEN];
11927 	dev_info_t	*cdip;
11928 
11929 	(void) sprintf(wwn_str, "%"PRIx64, smp_node->m_sasaddr);
11930 
11931 	cdip = mptsas_find_smp_child(pdip, wwn_str);
11932 
11933 	if (cdip == NULL)
11934 		return (DDI_SUCCESS);
11935 
11936 	/*
11937 	 * Make sure node is attached otherwise
11938 	 * it won't have related cache nodes to
11939 	 * clean up.  i_ddi_devi_attached is
11940 	 * similiar to i_ddi_node_state(cdip) >=
11941 	 * DS_ATTACHED.
11942 	 */
11943 	if (i_ddi_devi_attached(cdip)) {
11944 
11945 		/* Get full devname */
11946 		devname = kmem_alloc(MAXNAMELEN + 1, KM_SLEEP);
11947 		(void) ddi_deviname(cdip, devname);
11948 		/* Clean cache */
11949 		(void) devfs_clean(pdip, devname + 1,
11950 		    DV_CLEAN_FORCE);
11951 		kmem_free(devname, MAXNAMELEN + 1);
11952 	}
11953 
11954 	rval = ndi_devi_offline(cdip, flags);
11955 
11956 	return (rval);
11957 }
11958 
11959 static dev_info_t *
11960 mptsas_find_child(dev_info_t *pdip, char *name)
11961 {
11962 	dev_info_t	*child = NULL;
11963 	char		*rname = NULL;
11964 	int		rval = DDI_FAILURE;
11965 
11966 	rname = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP);
11967 
11968 	child = ddi_get_child(pdip);
11969 	while (child) {
11970 		rval = mptsas_name_child(child, rname, SCSI_MAXNAMELEN);
11971 		if (rval != DDI_SUCCESS) {
11972 			child = ddi_get_next_sibling(child);
11973 			bzero(rname, SCSI_MAXNAMELEN);
11974 			continue;
11975 		}
11976 
11977 		if (strcmp(rname, name) == 0) {
11978 			break;
11979 		}
11980 		child = ddi_get_next_sibling(child);
11981 		bzero(rname, SCSI_MAXNAMELEN);
11982 	}
11983 
11984 	kmem_free(rname, SCSI_MAXNAMELEN);
11985 
11986 	return (child);
11987 }
11988 
11989 
11990 static dev_info_t *
11991 mptsas_find_child_addr(dev_info_t *pdip, uint64_t sasaddr, int lun)
11992 {
11993 	dev_info_t	*child = NULL;
11994 	char		*name = NULL;
11995 	char		*addr = NULL;
11996 
11997 	name = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP);
11998 	addr = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP);
11999 	(void) sprintf(name, "%016"PRIx64, sasaddr);
12000 	(void) sprintf(addr, "w%s,%x", name, lun);
12001 	child = mptsas_find_child(pdip, addr);
12002 	kmem_free(name, SCSI_MAXNAMELEN);
12003 	kmem_free(addr, SCSI_MAXNAMELEN);
12004 	return (child);
12005 }
12006 
12007 static dev_info_t *
12008 mptsas_find_child_phy(dev_info_t *pdip, uint8_t phy)
12009 {
12010 	dev_info_t	*child;
12011 	char		*addr;
12012 
12013 	addr = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP);
12014 	(void) sprintf(addr, "p%x,0", phy);
12015 	child = mptsas_find_child(pdip, addr);
12016 	kmem_free(addr, SCSI_MAXNAMELEN);
12017 	return (child);
12018 }
12019 
12020 static mdi_pathinfo_t *
12021 mptsas_find_path_phy(dev_info_t *pdip, uint8_t phy)
12022 {
12023 	mdi_pathinfo_t	*path;
12024 	char		*addr = NULL;
12025 
12026 	addr = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP);
12027 	(void) sprintf(addr, "p%x,0", phy);
12028 	path = mdi_pi_find(pdip, NULL, addr);
12029 	kmem_free(addr, SCSI_MAXNAMELEN);
12030 	return (path);
12031 }
12032 
12033 static mdi_pathinfo_t *
12034 mptsas_find_path_addr(dev_info_t *parent, uint64_t sasaddr, int lun)
12035 {
12036 	mdi_pathinfo_t	*path;
12037 	char		*name = NULL;
12038 	char		*addr = NULL;
12039 
12040 	name = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP);
12041 	addr = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP);
12042 	(void) sprintf(name, "%016"PRIx64, sasaddr);
12043 	(void) sprintf(addr, "w%s,%x", name, lun);
12044 	path = mdi_pi_find(parent, NULL, addr);
12045 	kmem_free(name, SCSI_MAXNAMELEN);
12046 	kmem_free(addr, SCSI_MAXNAMELEN);
12047 
12048 	return (path);
12049 }
12050 
12051 static int
12052 mptsas_create_lun(dev_info_t *pdip, struct scsi_inquiry *sd_inq,
12053     dev_info_t **lun_dip, mptsas_target_t *ptgt, int lun)
12054 {
12055 	int			i = 0;
12056 	uchar_t			*inq83 = NULL;
12057 	int			inq83_len1 = 0xFF;
12058 	int			inq83_len = 0;
12059 	int			rval = DDI_FAILURE;
12060 	ddi_devid_t		devid;
12061 	char			*guid = NULL;
12062 	int			target = ptgt->m_devhdl;
12063 	mdi_pathinfo_t		*pip = NULL;
12064 	mptsas_t		*mpt = DIP2MPT(pdip);
12065 
12066 	/*
12067 	 * For DVD/CD ROM and tape devices and optical
12068 	 * devices, we won't try to enumerate them under
12069 	 * scsi_vhci, so no need to try page83
12070 	 */
12071 	if (sd_inq && (sd_inq->inq_dtype == DTYPE_RODIRECT ||
12072 	    sd_inq->inq_dtype == DTYPE_OPTICAL))
12073 		goto create_lun;
12074 
12075 	/*
12076 	 * The LCA returns good SCSI status, but corrupt page 83 data the first
12077 	 * time it is queried. The solution is to keep trying to request page83
12078 	 * and verify the GUID is not (DDI_NOT_WELL_FORMED) in
12079 	 * mptsas_inq83_retry_timeout seconds. If the timeout expires, driver
12080 	 * give up to get VPD page at this stage and fail the enumeration.
12081 	 */
12082 
12083 	inq83	= kmem_zalloc(inq83_len1, KM_SLEEP);
12084 
12085 	for (i = 0; i < mptsas_inq83_retry_timeout; i++) {
12086 		rval = mptsas_inquiry(mpt, ptgt, lun, 0x83, inq83,
12087 		    inq83_len1, &inq83_len, 1);
12088 		if (rval != 0) {
12089 			mptsas_log(mpt, CE_WARN, "!mptsas request inquiry page "
12090 			    "0x83 for target:%x, lun:%x failed!", target, lun);
12091 			goto out;
12092 		}
12093 		/*
12094 		 * create DEVID from inquiry data
12095 		 */
12096 		if ((rval = ddi_devid_scsi_encode(
12097 		    DEVID_SCSI_ENCODE_VERSION_LATEST, NULL, (uchar_t *)sd_inq,
12098 		    sizeof (struct scsi_inquiry), NULL, 0, inq83,
12099 		    (size_t)inq83_len, &devid)) == DDI_SUCCESS) {
12100 			/*
12101 			 * extract GUID from DEVID
12102 			 */
12103 			guid = ddi_devid_to_guid(devid);
12104 
12105 			/*
12106 			 * Do not enable MPXIO if the strlen(guid) is greater
12107 			 * than MPTSAS_MAX_GUID_LEN, this constrain would be
12108 			 * handled by framework later.
12109 			 */
12110 			if (guid && (strlen(guid) > MPTSAS_MAX_GUID_LEN)) {
12111 				ddi_devid_free_guid(guid);
12112 				guid = NULL;
12113 				if (mpt->m_mpxio_enable == TRUE) {
12114 					mptsas_log(mpt, CE_NOTE, "!Target:%x, "
12115 					    "lun:%x doesn't have a valid GUID, "
12116 					    "multipathing for this drive is "
12117 					    "not enabled", target, lun);
12118 				}
12119 			}
12120 
12121 			/*
12122 			 * devid no longer needed
12123 			 */
12124 			ddi_devid_free(devid);
12125 			break;
12126 		} else if (rval == DDI_NOT_WELL_FORMED) {
12127 			/*
12128 			 * return value of ddi_devid_scsi_encode equal to
12129 			 * DDI_NOT_WELL_FORMED means DEVID_RETRY, it worth
12130 			 * to retry inquiry page 0x83 and get GUID.
12131 			 */
12132 			NDBG20(("Not well formed devid, retry..."));
12133 			delay(1 * drv_usectohz(1000000));
12134 			continue;
12135 		} else {
12136 			mptsas_log(mpt, CE_WARN, "!Encode devid failed for "
12137 			    "path target:%x, lun:%x", target, lun);
12138 			rval = DDI_FAILURE;
12139 			goto create_lun;
12140 		}
12141 	}
12142 
12143 	if (i == mptsas_inq83_retry_timeout) {
12144 		mptsas_log(mpt, CE_WARN, "!Repeated page83 requests timeout "
12145 		    "for path target:%x, lun:%x", target, lun);
12146 	}
12147 
12148 	rval = DDI_FAILURE;
12149 
12150 create_lun:
12151 	if ((guid != NULL) && (mpt->m_mpxio_enable == TRUE)) {
12152 		rval = mptsas_create_virt_lun(pdip, sd_inq, guid, lun_dip, &pip,
12153 		    ptgt, lun);
12154 	}
12155 	if (rval != DDI_SUCCESS) {
12156 		rval = mptsas_create_phys_lun(pdip, sd_inq, guid, lun_dip,
12157 		    ptgt, lun);
12158 	}
12159 out:
12160 	if (guid != NULL) {
12161 		/*
12162 		 * guid no longer needed
12163 		 */
12164 		ddi_devid_free_guid(guid);
12165 	}
12166 	if (inq83 != NULL)
12167 		kmem_free(inq83, inq83_len1);
12168 	return (rval);
12169 }
12170 
12171 static int
12172 mptsas_create_virt_lun(dev_info_t *pdip, struct scsi_inquiry *inq, char *guid,
12173     dev_info_t **lun_dip, mdi_pathinfo_t **pip, mptsas_target_t *ptgt, int lun)
12174 {
12175 	int			target;
12176 	char			*nodename = NULL;
12177 	char			**compatible = NULL;
12178 	int			ncompatible	= 0;
12179 	int			mdi_rtn = MDI_FAILURE;
12180 	int			rval = DDI_FAILURE;
12181 	char			*old_guid = NULL;
12182 	mptsas_t		*mpt = DIP2MPT(pdip);
12183 	char			*lun_addr = NULL;
12184 	char			*wwn_str = NULL;
12185 	char			*component = NULL;
12186 	uint8_t			phy = 0xFF;
12187 	uint64_t		sas_wwn;
12188 	uint32_t		devinfo;
12189 
12190 	mutex_enter(&mpt->m_mutex);
12191 	target = ptgt->m_devhdl;
12192 	sas_wwn = ptgt->m_sas_wwn;
12193 	devinfo = ptgt->m_deviceinfo;
12194 	phy = ptgt->m_phynum;
12195 	mutex_exit(&mpt->m_mutex);
12196 
12197 	if (sas_wwn) {
12198 		*pip = mptsas_find_path_addr(pdip, sas_wwn, lun);
12199 	} else {
12200 		*pip = mptsas_find_path_phy(pdip, phy);
12201 	}
12202 
12203 	if (*pip != NULL) {
12204 		*lun_dip = MDI_PI(*pip)->pi_client->ct_dip;
12205 		ASSERT(*lun_dip != NULL);
12206 		if (ddi_prop_lookup_string(DDI_DEV_T_ANY, *lun_dip,
12207 		    (DDI_PROP_DONTPASS | DDI_PROP_NOTPROM),
12208 		    MDI_CLIENT_GUID_PROP, &old_guid) == DDI_SUCCESS) {
12209 			if (strncmp(guid, old_guid, strlen(guid)) == 0) {
12210 				/*
12211 				 * Same path back online again.
12212 				 */
12213 				(void) ddi_prop_free(old_guid);
12214 				if (!MDI_PI_IS_ONLINE(*pip) &&
12215 				    !MDI_PI_IS_STANDBY(*pip)) {
12216 					rval = mdi_pi_online(*pip, 0);
12217 				} else {
12218 					rval = DDI_SUCCESS;
12219 				}
12220 				if (rval != DDI_SUCCESS) {
12221 					mptsas_log(mpt, CE_WARN, "path:target: "
12222 					    "%x, lun:%x online failed!", target,
12223 					    lun);
12224 					*pip = NULL;
12225 					*lun_dip = NULL;
12226 				}
12227 				return (rval);
12228 			} else {
12229 				/*
12230 				 * The GUID of the LUN has changed which maybe
12231 				 * because customer mapped another volume to the
12232 				 * same LUN.
12233 				 */
12234 				mptsas_log(mpt, CE_WARN, "The GUID of the "
12235 				    "target:%x, lun:%x was changed, maybe "
12236 				    "because someone mapped another volume "
12237 				    "to the same LUN", target, lun);
12238 				(void) ddi_prop_free(old_guid);
12239 				if (!MDI_PI_IS_OFFLINE(*pip)) {
12240 					rval = mdi_pi_offline(*pip, 0);
12241 					if (rval != MDI_SUCCESS) {
12242 						mptsas_log(mpt, CE_WARN, "path:"
12243 						    "target:%x, lun:%x offline "
12244 						    "failed!", target, lun);
12245 						*pip = NULL;
12246 						*lun_dip = NULL;
12247 						return (DDI_FAILURE);
12248 					}
12249 				}
12250 				if (mdi_pi_free(*pip, 0) != MDI_SUCCESS) {
12251 					mptsas_log(mpt, CE_WARN, "path:target:"
12252 					    "%x, lun:%x free failed!", target,
12253 					    lun);
12254 					*pip = NULL;
12255 					*lun_dip = NULL;
12256 					return (DDI_FAILURE);
12257 				}
12258 			}
12259 		} else {
12260 			mptsas_log(mpt, CE_WARN, "Can't get client-guid "
12261 			    "property for path:target:%x, lun:%x", target, lun);
12262 			*pip = NULL;
12263 			*lun_dip = NULL;
12264 			return (DDI_FAILURE);
12265 		}
12266 	}
12267 	scsi_hba_nodename_compatible_get(inq, NULL,
12268 	    inq->inq_dtype, NULL, &nodename, &compatible, &ncompatible);
12269 
12270 	/*
12271 	 * if nodename can't be determined then print a message and skip it
12272 	 */
12273 	if (nodename == NULL) {
12274 		mptsas_log(mpt, CE_WARN, "mptsas driver found no compatible "
12275 		    "driver for target%d lun %d dtype:0x%02x", target, lun,
12276 		    inq->inq_dtype);
12277 		return (DDI_FAILURE);
12278 	}
12279 
12280 	wwn_str = kmem_zalloc(MPTSAS_WWN_STRLEN, KM_SLEEP);
12281 	/* The property is needed by MPAPI */
12282 	(void) sprintf(wwn_str, "%016"PRIx64, sas_wwn);
12283 
12284 	lun_addr = kmem_zalloc(SCSI_MAXNAMELEN, KM_SLEEP);
12285 	if (sas_wwn)
12286 		(void) sprintf(lun_addr, "w%s,%x", wwn_str, lun);
12287 	else
12288 		(void) sprintf(lun_addr, "p%x,%x", phy, lun);
12289 
12290 	mdi_rtn = mdi_pi_alloc_compatible(pdip, nodename,
12291 	    guid, lun_addr, compatible, ncompatible,
12292 	    0, pip);
12293 	if (mdi_rtn == MDI_SUCCESS) {
12294 
12295 		if (mdi_prop_update_string(*pip, MDI_GUID,
12296 		    guid) != DDI_SUCCESS) {
12297 			mptsas_log(mpt, CE_WARN, "mptsas driver unable to "
12298 			    "create property for target %d lun %d (MDI_GUID)",
12299 			    target, lun);
12300 			mdi_rtn = MDI_FAILURE;
12301 			goto virt_create_done;
12302 		}
12303 
12304 		if (mdi_prop_update_int(*pip, LUN_PROP,
12305 		    lun) != DDI_SUCCESS) {
12306 			mptsas_log(mpt, CE_WARN, "mptsas driver unable to "
12307 			    "create property for target %d lun %d (LUN_PROP)",
12308 			    target, lun);
12309 			mdi_rtn = MDI_FAILURE;
12310 			goto virt_create_done;
12311 		}
12312 		if (mdi_prop_update_string_array(*pip, "compatible",
12313 		    compatible, ncompatible) !=
12314 		    DDI_PROP_SUCCESS) {
12315 			mptsas_log(mpt, CE_WARN, "mptsas driver unable to "
12316 			    "create property for target %d lun %d (COMPATIBLE)",
12317 			    target, lun);
12318 			mdi_rtn = MDI_FAILURE;
12319 			goto virt_create_done;
12320 		}
12321 		if (sas_wwn && (mdi_prop_update_string(*pip,
12322 		    SCSI_ADDR_PROP_TARGET_PORT, wwn_str) != DDI_PROP_SUCCESS)) {
12323 			mptsas_log(mpt, CE_WARN, "mptsas driver unable to "
12324 			    "create property for target %d lun %d "
12325 			    "(target-port)", target, lun);
12326 			mdi_rtn = MDI_FAILURE;
12327 			goto virt_create_done;
12328 		} else if ((sas_wwn == 0) && (mdi_prop_update_int(*pip,
12329 		    "sata-phy", phy) != DDI_PROP_SUCCESS)) {
12330 			/*
12331 			 * Direct attached SATA device without DeviceName
12332 			 */
12333 			mptsas_log(mpt, CE_WARN, "mptsas driver unable to "
12334 			    "create property for SAS target %d lun %d "
12335 			    "(sata-phy)", target, lun);
12336 			mdi_rtn = NDI_FAILURE;
12337 			goto virt_create_done;
12338 		}
12339 
12340 		if (inq->inq_dtype == 0) {
12341 			component = kmem_zalloc(MAXPATHLEN, KM_SLEEP);
12342 			/*
12343 			 * set obp path for pathinfo
12344 			 */
12345 			(void) snprintf(component, MAXPATHLEN,
12346 			    "disk@%s", lun_addr);
12347 
12348 			if (mdi_pi_pathname_obp_set(*pip, component) !=
12349 			    DDI_SUCCESS) {
12350 				mptsas_log(mpt, CE_WARN, "mpt_sas driver "
12351 				    "unable to set obp-path for object %s",
12352 				    component);
12353 				mdi_rtn = MDI_FAILURE;
12354 				goto virt_create_done;
12355 			}
12356 		}
12357 
12358 		*lun_dip = MDI_PI(*pip)->pi_client->ct_dip;
12359 		if (devinfo & (MPI2_SAS_DEVICE_INFO_SATA_DEVICE |
12360 		    MPI2_SAS_DEVICE_INFO_ATAPI_DEVICE)) {
12361 			if ((ndi_prop_update_int(DDI_DEV_T_NONE, *lun_dip,
12362 			    "pm-capable", 1)) !=
12363 			    DDI_PROP_SUCCESS) {
12364 				mptsas_log(mpt, CE_WARN, "mptsas driver"
12365 				    "failed to create pm-capable "
12366 				    "property, target %d", target);
12367 				mdi_rtn = MDI_FAILURE;
12368 				goto virt_create_done;
12369 			}
12370 		}
12371 		NDBG20(("new path:%s onlining,", MDI_PI(*pip)->pi_addr));
12372 		mdi_rtn = mdi_pi_online(*pip, 0);
12373 		if (mdi_rtn == MDI_NOT_SUPPORTED) {
12374 			mdi_rtn = MDI_FAILURE;
12375 		}
12376 virt_create_done:
12377 		if (*pip && mdi_rtn != MDI_SUCCESS) {
12378 			(void) mdi_pi_free(*pip, 0);
12379 			*pip = NULL;
12380 			*lun_dip = NULL;
12381 		}
12382 	}
12383 
12384 	scsi_hba_nodename_compatible_free(nodename, compatible);
12385 	if (lun_addr != NULL) {
12386 		kmem_free(lun_addr, SCSI_MAXNAMELEN);
12387 	}
12388 	if (wwn_str != NULL) {
12389 		kmem_free(wwn_str, MPTSAS_WWN_STRLEN);
12390 	}
12391 	if (component != NULL) {
12392 		kmem_free(component, MAXPATHLEN);
12393 	}
12394 
12395 	return ((mdi_rtn == MDI_SUCCESS) ? DDI_SUCCESS : DDI_FAILURE);
12396 }
12397 
12398 static int
12399 mptsas_create_phys_lun(dev_info_t *pdip, struct scsi_inquiry *inq,
12400     char *guid, dev_info_t **lun_dip, mptsas_target_t *ptgt, int lun)
12401 {
12402 	int			target;
12403 	int			ndi_rtn = NDI_FAILURE;
12404 	uint64_t		be_sas_wwn;
12405 	char			*nodename = NULL;
12406 	char			**compatible = NULL;
12407 	int			ncompatible = 0;
12408 	int			instance = 0;
12409 	mptsas_t		*mpt = DIP2MPT(pdip);
12410 	char			*wwn_str = NULL;
12411 	char			*component = NULL;
12412 	uint8_t			phy = 0xFF;
12413 	uint64_t		sas_wwn;
12414 	uint32_t		devinfo;
12415 
12416 	mutex_enter(&mpt->m_mutex);
12417 	target = ptgt->m_devhdl;
12418 	sas_wwn = ptgt->m_sas_wwn;
12419 	devinfo = ptgt->m_deviceinfo;
12420 	phy = ptgt->m_phynum;
12421 	mutex_exit(&mpt->m_mutex);
12422 
12423 	/*
12424 	 * generate compatible property with binding-set "mpt"
12425 	 */
12426 	scsi_hba_nodename_compatible_get(inq, NULL, inq->inq_dtype, NULL,
12427 	    &nodename, &compatible, &ncompatible);
12428 
12429 	/*
12430 	 * if nodename can't be determined then print a message and skip it
12431 	 */
12432 	if (nodename == NULL) {
12433 		mptsas_log(mpt, CE_WARN, "mptsas found no compatible driver "
12434 		    "for target %d lun %d", target, lun);
12435 		return (DDI_FAILURE);
12436 	}
12437 
12438 	ndi_rtn = ndi_devi_alloc(pdip, nodename,
12439 	    DEVI_SID_NODEID, lun_dip);
12440 
12441 	/*
12442 	 * if lun alloc success, set props
12443 	 */
12444 	if (ndi_rtn == NDI_SUCCESS) {
12445 
12446 		if (ndi_prop_update_int(DDI_DEV_T_NONE,
12447 		    *lun_dip, LUN_PROP, lun) !=
12448 		    DDI_PROP_SUCCESS) {
12449 			mptsas_log(mpt, CE_WARN, "mptsas unable to create "
12450 			    "property for target %d lun %d (LUN_PROP)",
12451 			    target, lun);
12452 			ndi_rtn = NDI_FAILURE;
12453 			goto phys_create_done;
12454 		}
12455 
12456 		if (ndi_prop_update_string_array(DDI_DEV_T_NONE,
12457 		    *lun_dip, "compatible", compatible, ncompatible)
12458 		    != DDI_PROP_SUCCESS) {
12459 			mptsas_log(mpt, CE_WARN, "mptsas unable to create "
12460 			    "property for target %d lun %d (COMPATIBLE)",
12461 			    target, lun);
12462 			ndi_rtn = NDI_FAILURE;
12463 			goto phys_create_done;
12464 		}
12465 
12466 		/*
12467 		 * We need the SAS WWN for non-multipath devices, so
12468 		 * we'll use the same property as that multipathing
12469 		 * devices need to present for MPAPI. If we don't have
12470 		 * a WWN (e.g. parallel SCSI), don't create the prop.
12471 		 */
12472 		wwn_str = kmem_zalloc(MPTSAS_WWN_STRLEN, KM_SLEEP);
12473 		(void) sprintf(wwn_str, "%016"PRIx64, sas_wwn);
12474 		if (sas_wwn && ndi_prop_update_string(DDI_DEV_T_NONE,
12475 		    *lun_dip, SCSI_ADDR_PROP_TARGET_PORT, wwn_str)
12476 		    != DDI_PROP_SUCCESS) {
12477 			mptsas_log(mpt, CE_WARN, "mptsas unable to "
12478 			    "create property for SAS target %d lun %d "
12479 			    "(target-port)", target, lun);
12480 			ndi_rtn = NDI_FAILURE;
12481 			goto phys_create_done;
12482 		}
12483 		be_sas_wwn = BE_64(sas_wwn);
12484 		if (sas_wwn && ndi_prop_update_byte_array(
12485 		    DDI_DEV_T_NONE, *lun_dip, "port-wwn",
12486 		    (uchar_t *)&be_sas_wwn, 8) != DDI_PROP_SUCCESS) {
12487 			mptsas_log(mpt, CE_WARN, "mptsas unable to "
12488 			    "create property for SAS target %d lun %d "
12489 			    "(port-wwn)", target, lun);
12490 			ndi_rtn = NDI_FAILURE;
12491 			goto phys_create_done;
12492 		} else if ((sas_wwn == 0) && (ndi_prop_update_int(
12493 		    DDI_DEV_T_NONE, *lun_dip, "sata-phy", phy) !=
12494 		    DDI_PROP_SUCCESS)) {
12495 			/*
12496 			 * Direct attached SATA device without DeviceName
12497 			 */
12498 			mptsas_log(mpt, CE_WARN, "mptsas unable to "
12499 			    "create property for SAS target %d lun %d "
12500 			    "(sata-phy)", target, lun);
12501 			ndi_rtn = NDI_FAILURE;
12502 			goto phys_create_done;
12503 		}
12504 		if (ndi_prop_create_boolean(DDI_DEV_T_NONE,
12505 		    *lun_dip, SAS_PROP) != DDI_PROP_SUCCESS) {
12506 			mptsas_log(mpt, CE_WARN, "mptsas unable to"
12507 			    "create property for SAS target %d lun %d"
12508 			    " (SAS_PROP)", target, lun);
12509 			ndi_rtn = NDI_FAILURE;
12510 			goto phys_create_done;
12511 		}
12512 		if (guid && (ndi_prop_update_string(DDI_DEV_T_NONE,
12513 		    *lun_dip, NDI_GUID, guid) != DDI_SUCCESS)) {
12514 			mptsas_log(mpt, CE_WARN, "mptsas unable "
12515 			    "to create guid property for target %d "
12516 			    "lun %d", target, lun);
12517 			ndi_rtn = NDI_FAILURE;
12518 			goto phys_create_done;
12519 		}
12520 
12521 		/*
12522 		 * if this is a SAS controller, and the target is a SATA
12523 		 * drive, set the 'pm-capable' property for sd and if on
12524 		 * an OPL platform, also check if this is an ATAPI
12525 		 * device.
12526 		 */
12527 		instance = ddi_get_instance(mpt->m_dip);
12528 		if (devinfo & (MPI2_SAS_DEVICE_INFO_SATA_DEVICE |
12529 		    MPI2_SAS_DEVICE_INFO_ATAPI_DEVICE)) {
12530 			NDBG2(("mptsas%d: creating pm-capable property, "
12531 			    "target %d", instance, target));
12532 
12533 			if ((ndi_prop_update_int(DDI_DEV_T_NONE,
12534 			    *lun_dip, "pm-capable", 1)) !=
12535 			    DDI_PROP_SUCCESS) {
12536 				mptsas_log(mpt, CE_WARN, "mptsas "
12537 				    "failed to create pm-capable "
12538 				    "property, target %d", target);
12539 				ndi_rtn = NDI_FAILURE;
12540 				goto phys_create_done;
12541 			}
12542 
12543 		}
12544 
12545 		if (inq->inq_dtype == 0) {
12546 			/*
12547 			 * add 'obp-path' properties for devinfo
12548 			 */
12549 			component = kmem_zalloc(MAXPATHLEN, KM_SLEEP);
12550 			if (sas_wwn) {
12551 				(void) snprintf(component, MAXPATHLEN,
12552 				    "disk@w%s,%x", wwn_str, lun);
12553 			} else {
12554 				(void) snprintf(component, MAXPATHLEN,
12555 				    "disk@p%x,%x", phy, lun);
12556 			}
12557 			if (ddi_pathname_obp_set(*lun_dip, component)
12558 			    != DDI_SUCCESS) {
12559 				mptsas_log(mpt, CE_WARN, "mpt_sas driver "
12560 				    "unable to set obp-path for SAS "
12561 				    "object %s", component);
12562 				ndi_rtn = NDI_FAILURE;
12563 				goto phys_create_done;
12564 			}
12565 		}
12566 
12567 phys_create_done:
12568 		/*
12569 		 * If props were setup ok, online the lun
12570 		 */
12571 		if (ndi_rtn == NDI_SUCCESS) {
12572 			/*
12573 			 * Try to online the new node
12574 			 */
12575 			ndi_rtn = ndi_devi_online(*lun_dip, NDI_ONLINE_ATTACH);
12576 		}
12577 
12578 		/*
12579 		 * If success set rtn flag, else unwire alloc'd lun
12580 		 */
12581 		if (ndi_rtn != NDI_SUCCESS) {
12582 			NDBG12(("mptsas driver unable to online "
12583 			    "target %d lun %d", target, lun));
12584 			ndi_prop_remove_all(*lun_dip);
12585 			(void) ndi_devi_free(*lun_dip);
12586 			*lun_dip = NULL;
12587 		}
12588 	}
12589 
12590 	scsi_hba_nodename_compatible_free(nodename, compatible);
12591 
12592 	if (wwn_str != NULL) {
12593 		kmem_free(wwn_str, MPTSAS_WWN_STRLEN);
12594 	}
12595 	if (component != NULL) {
12596 		kmem_free(component, MAXPATHLEN);
12597 	}
12598 
12599 	return ((ndi_rtn == NDI_SUCCESS) ? DDI_SUCCESS : DDI_FAILURE);
12600 }
12601 
12602 static int
12603 mptsas_probe_smp(dev_info_t *pdip, uint64_t wwn)
12604 {
12605 	struct smp_device smp;
12606 
12607 	bzero(&smp, sizeof (struct smp_device));
12608 	smp.smp_addr.a_hba_tran = ndi_flavorv_get(pdip, SCSA_FLAVOR_SMP);
12609 	bcopy(&wwn, smp.smp_addr.a_wwn, SAS_WWN_BYTE_SIZE);
12610 
12611 	if (sas_hba_probe_smp(&smp) != DDI_PROBE_SUCCESS) {
12612 		return (NDI_FAILURE);
12613 	}
12614 	return (NDI_SUCCESS);
12615 }
12616 
12617 static int
12618 mptsas_config_smp(dev_info_t *pdip, uint64_t sas_wwn, dev_info_t **smp_dip)
12619 {
12620 	mptsas_t	*mpt = DIP2MPT(pdip);
12621 	mptsas_smp_t	*psmp = NULL;
12622 	int		rval;
12623 	int		phymask;
12624 
12625 	/*
12626 	 * Get the physical port associated to the iport
12627 	 * PHYMASK TODO
12628 	 */
12629 	phymask = ddi_prop_get_int(DDI_DEV_T_ANY, pdip, 0,
12630 	    "phymask", 0);
12631 	/*
12632 	 * Find the smp node in hash table with specified sas address and
12633 	 * physical port
12634 	 */
12635 	psmp = mptsas_wwid_to_psmp(mpt, phymask, sas_wwn);
12636 	if (psmp == NULL) {
12637 		return (DDI_FAILURE);
12638 	}
12639 
12640 	rval = mptsas_online_smp(pdip, psmp, smp_dip);
12641 
12642 	return (rval);
12643 }
12644 
12645 static int
12646 mptsas_online_smp(dev_info_t *pdip, mptsas_smp_t *smp_node,
12647     dev_info_t **smp_dip)
12648 {
12649 	char		wwn_str[MPTSAS_WWN_STRLEN];
12650 	int		ndi_rtn = NDI_FAILURE;
12651 	mptsas_t	*mpt = DIP2MPT(pdip);
12652 
12653 	(void) sprintf(wwn_str, "%"PRIx64, smp_node->m_sasaddr);
12654 
12655 	/*
12656 	 * Probe smp device, prevent the node of removed device from being
12657 	 * configured succesfully
12658 	 */
12659 	if (mptsas_probe_smp(pdip, smp_node->m_sasaddr) != NDI_SUCCESS) {
12660 		return (DDI_FAILURE);
12661 	}
12662 
12663 	if ((*smp_dip = mptsas_find_smp_child(pdip, wwn_str)) != NULL) {
12664 		return (DDI_SUCCESS);
12665 	}
12666 
12667 	ndi_rtn = ndi_devi_alloc(pdip, "smp", DEVI_SID_NODEID, smp_dip);
12668 
12669 	/*
12670 	 * if lun alloc success, set props
12671 	 */
12672 	if (ndi_rtn == NDI_SUCCESS) {
12673 		/*
12674 		 * Set the flavor of the child to be SMP flavored
12675 		 */
12676 		ndi_flavor_set(*smp_dip, SCSA_FLAVOR_SMP);
12677 
12678 		if (ndi_prop_update_string(DDI_DEV_T_NONE,
12679 		    *smp_dip, SMP_WWN, wwn_str) !=
12680 		    DDI_PROP_SUCCESS) {
12681 			mptsas_log(mpt, CE_WARN, "mptsas unable to create "
12682 			    "property for smp device %s (sas_wwn)",
12683 			    wwn_str);
12684 			ndi_rtn = NDI_FAILURE;
12685 			goto smp_create_done;
12686 		}
12687 
12688 		if (ndi_prop_create_boolean(DDI_DEV_T_NONE,
12689 		    *smp_dip, SMP_PROP) != DDI_PROP_SUCCESS) {
12690 			mptsas_log(mpt, CE_WARN, "mptsas unable to "
12691 			    "create property for SMP %s (SMP_PROP) ",
12692 			    wwn_str);
12693 			ndi_rtn = NDI_FAILURE;
12694 			goto smp_create_done;
12695 		}
12696 
12697 smp_create_done:
12698 		/*
12699 		 * If props were setup ok, online the lun
12700 		 */
12701 		if (ndi_rtn == NDI_SUCCESS) {
12702 			/*
12703 			 * Try to online the new node
12704 			 */
12705 			ndi_rtn = ndi_devi_online(*smp_dip, NDI_ONLINE_ATTACH);
12706 		}
12707 
12708 		/*
12709 		 * If success set rtn flag, else unwire alloc'd lun
12710 		 */
12711 		if (ndi_rtn != NDI_SUCCESS) {
12712 			NDBG12(("mptsas unable to online "
12713 			    "SMP target %s", wwn_str));
12714 			ndi_prop_remove_all(*smp_dip);
12715 			(void) ndi_devi_free(*smp_dip);
12716 		}
12717 	}
12718 
12719 	return ((ndi_rtn == NDI_SUCCESS) ? DDI_SUCCESS : DDI_FAILURE);
12720 }
12721 
12722 /*ARGSUSED*/
12723 static int mptsas_getcap(struct sas_addr *ap, char *cap)
12724 {
12725 	int	ckey = -1;
12726 	int	ret = EINVAL;
12727 
12728 	ckey = sas_hba_lookup_capstr(cap);
12729 	if (ckey == -1)
12730 		return (EINVAL);
12731 
12732 	switch (ckey) {
12733 	case SAS_CAP_SMP_CRC:
12734 		/*
12735 		 * mpt controller support generate CRC for
12736 		 * SMP passthrough frame and handle CRC by
12737 		 * IOC itself.
12738 		 */
12739 		ret = 0;
12740 		break;
12741 	default:
12742 		ret = EINVAL;
12743 		break;
12744 	}
12745 	return (ret);
12746 }
12747 
12748 /* smp transport routine */
12749 static int mptsas_smp_start(struct smp_pkt *pktp)
12750 {
12751 	uint64_t			wwn;
12752 	Mpi2SmpPassthroughRequest_t	req;
12753 	Mpi2SmpPassthroughReply_t	rep;
12754 	uint32_t			direction = 0;
12755 	mptsas_t			*mpt;
12756 	int				ret;
12757 	uint64_t			tmp64;
12758 
12759 	mpt = (mptsas_t *)pktp->pkt_address->a_hba_tran->tran_hba_private;
12760 
12761 	bcopy(pktp->pkt_address->a_wwn, &wwn, SAS_WWN_BYTE_SIZE);
12762 	/*
12763 	 * Need to compose a SMP request message
12764 	 * and call mptsas_do_passthru() function
12765 	 */
12766 	bzero(&req, sizeof (req));
12767 	bzero(&rep, sizeof (rep));
12768 	req.PassthroughFlags = 0;
12769 	req.PhysicalPort = 0xff;
12770 	req.ChainOffset = 0;
12771 	req.Function = MPI2_FUNCTION_SMP_PASSTHROUGH;
12772 
12773 	if ((pktp->pkt_reqsize & 0xffff0000ul) != 0) {
12774 		pktp->pkt_reason = ERANGE;
12775 		return (DDI_FAILURE);
12776 	}
12777 	req.RequestDataLength = LE_16((uint16_t)(pktp->pkt_reqsize - 4));
12778 
12779 	req.MsgFlags = 0;
12780 	tmp64 = LE_64(wwn);
12781 	bcopy(&tmp64, &req.SASAddress, SAS_WWN_BYTE_SIZE);
12782 	if (pktp->pkt_rspsize > 0) {
12783 		direction |= MPTSAS_PASS_THRU_DIRECTION_READ;
12784 	}
12785 	if (pktp->pkt_reqsize > 0) {
12786 		direction |= MPTSAS_PASS_THRU_DIRECTION_WRITE;
12787 	}
12788 
12789 	mutex_enter(&mpt->m_mutex);
12790 	ret = mptsas_do_passthru(mpt, (uint8_t *)&req, (uint8_t *)&rep,
12791 	    (uint8_t *)pktp->pkt_rsp, offsetof(Mpi2SmpPassthroughRequest_t,
12792 	    SGL), sizeof (rep), pktp->pkt_rspsize - 4, direction,
12793 	    (uint8_t *)pktp->pkt_req, pktp->pkt_reqsize - 4,
12794 	    pktp->pkt_timeout, FKIOCTL);
12795 	mutex_exit(&mpt->m_mutex);
12796 	if (ret != 0) {
12797 		cmn_err(CE_WARN, "smp_start do passthru error %d", ret);
12798 		pktp->pkt_reason = (uchar_t)(ret);
12799 		return (DDI_FAILURE);
12800 	}
12801 	/* do passthrough success, check the smp status */
12802 	if (LE_16(rep.IOCStatus) != MPI2_IOCSTATUS_SUCCESS) {
12803 		switch (LE_16(rep.IOCStatus)) {
12804 		case MPI2_IOCSTATUS_SCSI_DEVICE_NOT_THERE:
12805 			pktp->pkt_reason = ENODEV;
12806 			break;
12807 		case MPI2_IOCSTATUS_SAS_SMP_DATA_OVERRUN:
12808 			pktp->pkt_reason = EOVERFLOW;
12809 			break;
12810 		case MPI2_IOCSTATUS_SAS_SMP_REQUEST_FAILED:
12811 			pktp->pkt_reason = EIO;
12812 			break;
12813 		default:
12814 			mptsas_log(mpt, CE_NOTE, "smp_start: get unknown ioc"
12815 			    "status:%x", LE_16(rep.IOCStatus));
12816 			pktp->pkt_reason = EIO;
12817 			break;
12818 		}
12819 		return (DDI_FAILURE);
12820 	}
12821 	if (rep.SASStatus != MPI2_SASSTATUS_SUCCESS) {
12822 		mptsas_log(mpt, CE_NOTE, "smp_start: get error SAS status:%x",
12823 		    rep.SASStatus);
12824 		pktp->pkt_reason = EIO;
12825 		return (DDI_FAILURE);
12826 	}
12827 
12828 	return (DDI_SUCCESS);
12829 }
12830 
12831 static void
12832 mptsas_idle_pm(void *arg)
12833 {
12834 	mptsas_t	*mpt = arg;
12835 
12836 	(void) pm_idle_component(mpt->m_dip, 0);
12837 	mutex_enter(&mpt->m_mutex);
12838 	mpt->m_pm_timeid = 0;
12839 	mutex_exit(&mpt->m_mutex);
12840 }
12841 
12842 /*
12843  * If we didn't get a match, we need to get sas page0 for each device, and
12844  * untill we get a match. If failed, return NULL
12845  * TODO should be implemented similar to mptsas_wwid_to_ptgt?
12846  */
12847 static mptsas_target_t *
12848 mptsas_phy_to_tgt(dev_info_t *pdip, uint8_t phy)
12849 {
12850 	int		i, j = 0;
12851 	int		rval = 0;
12852 	uint16_t	cur_handle;
12853 	uint32_t	page_address;
12854 	mptsas_target_t	*ptgt = NULL;
12855 	mptsas_t	*mpt = DIP2MPT(pdip);
12856 	int		phymask;
12857 
12858 	/*
12859 	 * Get the physical port associated to the iport
12860 	 */
12861 	phymask = ddi_prop_get_int(DDI_DEV_T_ANY, pdip, 0,
12862 	    "phymask", 0);
12863 
12864 	if (phymask == 0)
12865 		return (NULL);
12866 
12867 	/*
12868 	 * PHY named device must be direct attached and attaches to
12869 	 * narrow port, if the iport is not parent of the device which
12870 	 * we are looking for.
12871 	 */
12872 	for (i = 0; i < MPTSAS_MAX_PHYS; i++) {
12873 		if ((1 << i) & phymask)
12874 			j++;
12875 	}
12876 
12877 	if (j > 1)
12878 		return (NULL);
12879 
12880 	/*
12881 	 * Must be a narrow port and single device attached to the narrow port
12882 	 * So the physical port num of device  which is equal to the iport's
12883 	 * port num is the device what we are looking for.
12884 	 */
12885 
12886 	if (mpt->m_phy_info[phy].phy_mask != phymask)
12887 		return (NULL);
12888 
12889 	mutex_enter(&mpt->m_mutex);
12890 
12891 	ptgt = (mptsas_target_t *)mptsas_hash_traverse(&mpt->m_active->m_tgttbl,
12892 	    MPTSAS_HASH_FIRST);
12893 	while (ptgt != NULL) {
12894 			if ((ptgt->m_sas_wwn == 0) && (ptgt->m_phynum == phy)) {
12895 			mutex_exit(&mpt->m_mutex);
12896 			return (ptgt);
12897 		}
12898 
12899 		ptgt = (mptsas_target_t *)mptsas_hash_traverse(
12900 		    &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
12901 	}
12902 
12903 	if (mpt->m_done_traverse_dev) {
12904 		mutex_exit(&mpt->m_mutex);
12905 		return (NULL);
12906 	}
12907 
12908 	/* If didn't get a match, come here */
12909 	cur_handle = mpt->m_dev_handle;
12910 	for (; ; ) {
12911 		ptgt = NULL;
12912 		page_address = (MPI2_SAS_DEVICE_PGAD_FORM_GET_NEXT_HANDLE &
12913 		    MPI2_SAS_DEVICE_PGAD_FORM_MASK) | (uint32_t)cur_handle;
12914 		rval = mptsas_get_target_device_info(mpt, page_address,
12915 		    &cur_handle, &ptgt);
12916 		if ((rval == DEV_INFO_FAIL_PAGE0) ||
12917 		    (rval == DEV_INFO_FAIL_ALLOC)) {
12918 			break;
12919 		}
12920 		if ((rval == DEV_INFO_WRONG_DEVICE_TYPE) ||
12921 		    (rval == DEV_INFO_PHYS_DISK)) {
12922 			continue;
12923 		}
12924 		mpt->m_dev_handle = cur_handle;
12925 
12926 		if ((ptgt->m_sas_wwn == 0) && (ptgt->m_phynum == phy)) {
12927 			break;
12928 		}
12929 	}
12930 
12931 	mutex_exit(&mpt->m_mutex);
12932 	return (ptgt);
12933 }
12934 
12935 /*
12936  * The ptgt->m_sas_wwn contains the wwid for each disk.
12937  * For Raid volumes, we need to check m_raidvol[x].m_raidwwid
12938  * If we didn't get a match, we need to get sas page0 for each device, and
12939  * untill we get a match
12940  * If failed, return NULL
12941  */
12942 static mptsas_target_t *
12943 mptsas_wwid_to_ptgt(mptsas_t *mpt, int phymask, uint64_t wwid)
12944 {
12945 	int		rval = 0;
12946 	uint16_t	cur_handle;
12947 	uint32_t	page_address;
12948 	mptsas_target_t	*tmp_tgt = NULL;
12949 
12950 	mutex_enter(&mpt->m_mutex);
12951 	tmp_tgt = (struct mptsas_target *)mptsas_hash_search(
12952 	    &mpt->m_active->m_tgttbl, wwid, phymask);
12953 	if (tmp_tgt != NULL) {
12954 		mutex_exit(&mpt->m_mutex);
12955 		return (tmp_tgt);
12956 	}
12957 
12958 	if (phymask == 0) {
12959 		/*
12960 		 * It's IR volume
12961 		 */
12962 		rval = mptsas_get_raid_info(mpt);
12963 		if (rval) {
12964 			tmp_tgt = (struct mptsas_target *)mptsas_hash_search(
12965 			    &mpt->m_active->m_tgttbl, wwid, phymask);
12966 		}
12967 		mutex_exit(&mpt->m_mutex);
12968 		return (tmp_tgt);
12969 	}
12970 
12971 	if (mpt->m_done_traverse_dev) {
12972 		mutex_exit(&mpt->m_mutex);
12973 		return (NULL);
12974 	}
12975 
12976 	/* If didn't get a match, come here */
12977 	cur_handle = mpt->m_dev_handle;
12978 	for (; ; ) {
12979 		tmp_tgt = NULL;
12980 		page_address = (MPI2_SAS_DEVICE_PGAD_FORM_GET_NEXT_HANDLE &
12981 		    MPI2_SAS_DEVICE_PGAD_FORM_MASK) | cur_handle;
12982 		rval = mptsas_get_target_device_info(mpt, page_address,
12983 		    &cur_handle, &tmp_tgt);
12984 		if ((rval == DEV_INFO_FAIL_PAGE0) ||
12985 		    (rval == DEV_INFO_FAIL_ALLOC)) {
12986 			tmp_tgt = NULL;
12987 			break;
12988 		}
12989 		if ((rval == DEV_INFO_WRONG_DEVICE_TYPE) ||
12990 		    (rval == DEV_INFO_PHYS_DISK)) {
12991 			continue;
12992 		}
12993 		mpt->m_dev_handle = cur_handle;
12994 		if ((tmp_tgt->m_sas_wwn) && (tmp_tgt->m_sas_wwn == wwid) &&
12995 		    (tmp_tgt->m_phymask == phymask)) {
12996 			break;
12997 		}
12998 	}
12999 
13000 	mutex_exit(&mpt->m_mutex);
13001 	return (tmp_tgt);
13002 }
13003 
13004 static mptsas_smp_t *
13005 mptsas_wwid_to_psmp(mptsas_t *mpt, int phymask, uint64_t wwid)
13006 {
13007 	int		rval = 0;
13008 	uint16_t	cur_handle;
13009 	uint32_t	page_address;
13010 	mptsas_smp_t	smp_node, *psmp = NULL;
13011 
13012 	mutex_enter(&mpt->m_mutex);
13013 	psmp = (struct mptsas_smp *)mptsas_hash_search(&mpt->m_active->m_smptbl,
13014 	    wwid, phymask);
13015 	if (psmp != NULL) {
13016 		mutex_exit(&mpt->m_mutex);
13017 		return (psmp);
13018 	}
13019 
13020 	if (mpt->m_done_traverse_smp) {
13021 		mutex_exit(&mpt->m_mutex);
13022 		return (NULL);
13023 	}
13024 
13025 	/* If didn't get a match, come here */
13026 	cur_handle = mpt->m_smp_devhdl;
13027 	for (; ; ) {
13028 		psmp = NULL;
13029 		page_address = (MPI2_SAS_EXPAND_PGAD_FORM_GET_NEXT_HNDL &
13030 		    MPI2_SAS_EXPAND_PGAD_FORM_MASK) | (uint32_t)cur_handle;
13031 		rval = mptsas_get_sas_expander_page0(mpt, page_address,
13032 		    &smp_node);
13033 		if (rval != DDI_SUCCESS) {
13034 			break;
13035 		}
13036 		mpt->m_smp_devhdl = cur_handle = smp_node.m_devhdl;
13037 		psmp = mptsas_smp_alloc(&mpt->m_active->m_smptbl, &smp_node);
13038 		ASSERT(psmp);
13039 		if ((psmp->m_sasaddr) && (psmp->m_sasaddr == wwid) &&
13040 		    (psmp->m_phymask == phymask)) {
13041 			break;
13042 		}
13043 	}
13044 
13045 	mutex_exit(&mpt->m_mutex);
13046 	return (psmp);
13047 }
13048 
13049 /* helper functions using hash */
13050 
13051 /*
13052  * Can't have duplicate entries for same devhdl,
13053  * if there are invalid entries, the devhdl should be set to 0xffff
13054  */
13055 static void *
13056 mptsas_search_by_devhdl(mptsas_hash_table_t *hashtab, uint16_t devhdl)
13057 {
13058 	mptsas_hash_data_t *data;
13059 
13060 	data = mptsas_hash_traverse(hashtab, MPTSAS_HASH_FIRST);
13061 	while (data != NULL) {
13062 		if (data->devhdl == devhdl) {
13063 			break;
13064 		}
13065 		data = mptsas_hash_traverse(hashtab, MPTSAS_HASH_NEXT);
13066 	}
13067 	return (data);
13068 }
13069 
13070 mptsas_target_t *
13071 mptsas_tgt_alloc(mptsas_hash_table_t *hashtab, uint16_t devhdl, uint64_t wwid,
13072     uint32_t devinfo, uint8_t phymask, uint8_t phynum)
13073 {
13074 	mptsas_target_t *tmp_tgt = NULL;
13075 
13076 	tmp_tgt = mptsas_hash_search(hashtab, wwid, phymask);
13077 	if (tmp_tgt != NULL) {
13078 		NDBG20(("Hash item already exist"));
13079 		tmp_tgt->m_deviceinfo = devinfo;
13080 		tmp_tgt->m_devhdl = devhdl;
13081 		return (tmp_tgt);
13082 	}
13083 	tmp_tgt = kmem_zalloc(sizeof (struct mptsas_target), KM_SLEEP);
13084 	if (tmp_tgt == NULL) {
13085 		cmn_err(CE_WARN, "Fatal, allocated tgt failed");
13086 		return (NULL);
13087 	}
13088 	tmp_tgt->m_devhdl = devhdl;
13089 	tmp_tgt->m_sas_wwn = wwid;
13090 	tmp_tgt->m_deviceinfo = devinfo;
13091 	tmp_tgt->m_phymask = phymask;
13092 	tmp_tgt->m_phynum = phynum;
13093 	/* Initialized the tgt structure */
13094 	tmp_tgt->m_qfull_retries = QFULL_RETRIES;
13095 	tmp_tgt->m_qfull_retry_interval =
13096 	    drv_usectohz(QFULL_RETRY_INTERVAL * 1000);
13097 	tmp_tgt->m_t_throttle = MAX_THROTTLE;
13098 
13099 	mptsas_hash_add(hashtab, tmp_tgt);
13100 
13101 	return (tmp_tgt);
13102 }
13103 
13104 static void
13105 mptsas_tgt_free(mptsas_hash_table_t *hashtab, uint64_t wwid, uint8_t phymask)
13106 {
13107 	mptsas_target_t *tmp_tgt;
13108 	tmp_tgt = mptsas_hash_rem(hashtab, wwid, phymask);
13109 	if (tmp_tgt == NULL) {
13110 		cmn_err(CE_WARN, "Tgt not found, nothing to free");
13111 	} else {
13112 		kmem_free(tmp_tgt, sizeof (struct mptsas_target));
13113 	}
13114 }
13115 
13116 /*
13117  * Return the entry in the hash table
13118  */
13119 static mptsas_smp_t *
13120 mptsas_smp_alloc(mptsas_hash_table_t *hashtab, mptsas_smp_t *data)
13121 {
13122 	uint64_t key1 = data->m_sasaddr;
13123 	uint8_t key2 = data->m_phymask;
13124 	mptsas_smp_t *ret_data;
13125 
13126 	ret_data = mptsas_hash_search(hashtab, key1, key2);
13127 	if (ret_data != NULL) {
13128 		bcopy(data, ret_data, sizeof (mptsas_smp_t));
13129 		return (ret_data);
13130 	}
13131 
13132 	ret_data = kmem_alloc(sizeof (mptsas_smp_t), KM_SLEEP);
13133 	bcopy(data, ret_data, sizeof (mptsas_smp_t));
13134 	mptsas_hash_add(hashtab, ret_data);
13135 	return (ret_data);
13136 }
13137 
13138 static void
13139 mptsas_smp_free(mptsas_hash_table_t *hashtab, uint64_t wwid, uint8_t phymask)
13140 {
13141 	mptsas_smp_t *tmp_smp;
13142 	tmp_smp = mptsas_hash_rem(hashtab, wwid, phymask);
13143 	if (tmp_smp == NULL) {
13144 		cmn_err(CE_WARN, "Smp element not found, nothing to free");
13145 	} else {
13146 		kmem_free(tmp_smp, sizeof (struct mptsas_smp));
13147 	}
13148 }
13149 
13150 /*
13151  * Hash operation functions
13152  * key1 is the sas_wwn, key2 is the phymask
13153  */
13154 static void
13155 mptsas_hash_init(mptsas_hash_table_t *hashtab)
13156 {
13157 	if (hashtab == NULL) {
13158 		return;
13159 	}
13160 	bzero(hashtab->head, sizeof (mptsas_hash_node_t) *
13161 	    MPTSAS_HASH_ARRAY_SIZE);
13162 	hashtab->cur = NULL;
13163 	hashtab->line = 0;
13164 }
13165 
13166 static void
13167 mptsas_hash_uninit(mptsas_hash_table_t *hashtab, size_t datalen)
13168 {
13169 	uint16_t line = 0;
13170 	mptsas_hash_node_t *cur = NULL, *last = NULL;
13171 
13172 	if (hashtab == NULL) {
13173 		return;
13174 	}
13175 	for (line = 0; line < MPTSAS_HASH_ARRAY_SIZE; line++) {
13176 		cur = hashtab->head[line];
13177 		while (cur != NULL) {
13178 			last = cur;
13179 			cur = cur->next;
13180 			kmem_free(last->data, datalen);
13181 			kmem_free(last, sizeof (mptsas_hash_node_t));
13182 		}
13183 	}
13184 }
13185 
13186 /*
13187  * You must guarantee the element doesn't exist in the hash table
13188  * before you call mptsas_hash_add()
13189  */
13190 static void
13191 mptsas_hash_add(mptsas_hash_table_t *hashtab, void *data)
13192 {
13193 	uint64_t key1 = ((mptsas_hash_data_t *)data)->key1;
13194 	uint8_t	key2 = ((mptsas_hash_data_t *)data)->key2;
13195 	mptsas_hash_node_t **head = NULL;
13196 	mptsas_hash_node_t *node = NULL;
13197 
13198 	if (hashtab == NULL) {
13199 		return;
13200 	}
13201 	ASSERT(mptsas_hash_search(hashtab, key1, key2) == NULL);
13202 	node = kmem_zalloc(sizeof (mptsas_hash_node_t), KM_NOSLEEP);
13203 	node->data = data;
13204 
13205 	head = &(hashtab->head[key1 % MPTSAS_HASH_ARRAY_SIZE]);
13206 	if (*head == NULL) {
13207 		*head = node;
13208 	} else {
13209 		node->next = *head;
13210 		*head = node;
13211 	}
13212 }
13213 
13214 static void *
13215 mptsas_hash_rem(mptsas_hash_table_t *hashtab, uint64_t key1, uint8_t key2)
13216 {
13217 	mptsas_hash_node_t **head = NULL;
13218 	mptsas_hash_node_t *last = NULL, *cur = NULL;
13219 	mptsas_hash_data_t *data;
13220 	if (hashtab == NULL) {
13221 		return (NULL);
13222 	}
13223 	head = &(hashtab->head[key1 % MPTSAS_HASH_ARRAY_SIZE]);
13224 	cur = *head;
13225 	while (cur != NULL) {
13226 		data = cur->data;
13227 		if ((data->key1 == key1) && (data->key2 == key2)) {
13228 			if (last == NULL) {
13229 				(*head) = cur->next;
13230 			} else {
13231 				last->next = cur->next;
13232 			}
13233 			kmem_free(cur, sizeof (mptsas_hash_node_t));
13234 			return (data);
13235 		} else {
13236 			last = cur;
13237 			cur = cur->next;
13238 		}
13239 	}
13240 	return (NULL);
13241 }
13242 
13243 static void *
13244 mptsas_hash_search(mptsas_hash_table_t *hashtab, uint64_t key1, uint8_t key2)
13245 {
13246 	mptsas_hash_node_t *cur = NULL;
13247 	mptsas_hash_data_t *data;
13248 	if (hashtab == NULL) {
13249 		return (NULL);
13250 	}
13251 	cur = hashtab->head[key1 % MPTSAS_HASH_ARRAY_SIZE];
13252 	while (cur != NULL) {
13253 		data = cur->data;
13254 		if ((data->key1 == key1) && (data->key2 == key2)) {
13255 			return (data);
13256 		} else {
13257 			cur = cur->next;
13258 		}
13259 	}
13260 	return (NULL);
13261 }
13262 
13263 static void *
13264 mptsas_hash_traverse(mptsas_hash_table_t *hashtab, int pos)
13265 {
13266 	mptsas_hash_node_t *this = NULL;
13267 
13268 	if (hashtab == NULL) {
13269 		return (NULL);
13270 	}
13271 
13272 	if (pos == MPTSAS_HASH_FIRST) {
13273 		hashtab->line = 0;
13274 		hashtab->cur = NULL;
13275 		this = hashtab->head[0];
13276 	} else {
13277 		if (hashtab->cur == NULL) {
13278 			return (NULL);
13279 		} else {
13280 			this = hashtab->cur->next;
13281 		}
13282 	}
13283 
13284 	while (this == NULL) {
13285 		hashtab->line++;
13286 		if (hashtab->line >= MPTSAS_HASH_ARRAY_SIZE) {
13287 			/* the traverse reaches the end */
13288 			hashtab->cur = NULL;
13289 			return (NULL);
13290 		} else {
13291 			this = hashtab->head[hashtab->line];
13292 		}
13293 	}
13294 	hashtab->cur = this;
13295 	return (this->data);
13296 }
13297