220 static void mptsas_flush_hba(mptsas_t *mpt);
221 static void mptsas_flush_target(mptsas_t *mpt, ushort_t target, int lun,
222 uint8_t tasktype);
223 static void mptsas_set_pkt_reason(mptsas_t *mpt, mptsas_cmd_t *cmd,
224 uchar_t reason, uint_t stat);
225
226 static uint_t mptsas_intr(caddr_t arg1, caddr_t arg2);
227 static void mptsas_process_intr(mptsas_t *mpt,
228 pMpi2ReplyDescriptorsUnion_t reply_desc_union);
229 static void mptsas_handle_scsi_io_success(mptsas_t *mpt,
230 pMpi2ReplyDescriptorsUnion_t reply_desc);
231 static void mptsas_handle_address_reply(mptsas_t *mpt,
232 pMpi2ReplyDescriptorsUnion_t reply_desc);
233 static int mptsas_wait_intr(mptsas_t *mpt, int polltime);
234 static void mptsas_sge_setup(mptsas_t *mpt, mptsas_cmd_t *cmd,
235 uint32_t *control, pMpi2SCSIIORequest_t frame, ddi_acc_handle_t acc_hdl);
236
237 static void mptsas_watch(void *arg);
238 static void mptsas_watchsubr(mptsas_t *mpt);
239 static void mptsas_cmd_timeout(mptsas_t *mpt, uint16_t devhdl);
240
241 static void mptsas_start_passthru(mptsas_t *mpt, mptsas_cmd_t *cmd);
242 static int mptsas_do_passthru(mptsas_t *mpt, uint8_t *request, uint8_t *reply,
243 uint8_t *data, uint32_t request_size, uint32_t reply_size,
244 uint32_t data_size, uint32_t direction, uint8_t *dataout,
245 uint32_t dataout_size, short timeout, int mode);
246 static int mptsas_free_devhdl(mptsas_t *mpt, uint16_t devhdl);
247
248 static uint8_t mptsas_get_fw_diag_buffer_number(mptsas_t *mpt,
249 uint32_t unique_id);
250 static void mptsas_start_diag(mptsas_t *mpt, mptsas_cmd_t *cmd);
251 static int mptsas_post_fw_diag_buffer(mptsas_t *mpt,
252 mptsas_fw_diagnostic_buffer_t *pBuffer, uint32_t *return_code);
253 static int mptsas_release_fw_diag_buffer(mptsas_t *mpt,
254 mptsas_fw_diagnostic_buffer_t *pBuffer, uint32_t *return_code,
255 uint32_t diag_type);
256 static int mptsas_diag_register(mptsas_t *mpt,
257 mptsas_fw_diag_register_t *diag_register, uint32_t *return_code);
258 static int mptsas_diag_unregister(mptsas_t *mpt,
259 mptsas_fw_diag_unregister_t *diag_unregister, uint32_t *return_code);
330 static dev_info_t *mptsas_find_smp_child(dev_info_t *pdip, char *str_wwn);
331
332 static int mptsas_parse_address(char *name, uint64_t *wwid, uint8_t *phy,
333 int *lun);
334 static int mptsas_parse_smp_name(char *name, uint64_t *wwn);
335
336 static mptsas_target_t *mptsas_phy_to_tgt(mptsas_t *mpt, int phymask,
337 uint8_t phy);
338 static mptsas_target_t *mptsas_wwid_to_ptgt(mptsas_t *mpt, int phymask,
339 uint64_t wwid);
340 static mptsas_smp_t *mptsas_wwid_to_psmp(mptsas_t *mpt, int phymask,
341 uint64_t wwid);
342
343 static int mptsas_inquiry(mptsas_t *mpt, mptsas_target_t *ptgt, int lun,
344 uchar_t page, unsigned char *buf, int len, int *rlen, uchar_t evpd);
345
346 static int mptsas_get_target_device_info(mptsas_t *mpt, uint32_t page_address,
347 uint16_t *handle, mptsas_target_t **pptgt);
348 static void mptsas_update_phymask(mptsas_t *mpt);
349
350 static int mptsas_send_sep(mptsas_t *mpt, mptsas_target_t *ptgt,
351 uint32_t *status, uint8_t cmd);
352 static dev_info_t *mptsas_get_dip_from_dev(dev_t dev,
353 mptsas_phymask_t *phymask);
354 static mptsas_target_t *mptsas_addr_to_ptgt(mptsas_t *mpt, char *addr,
355 mptsas_phymask_t phymask);
356 static int mptsas_set_led_status(mptsas_t *mpt, mptsas_target_t *ptgt,
357 uint32_t slotstatus);
358
359
360 /*
361 * Enumeration / DR functions
362 */
363 static void mptsas_config_all(dev_info_t *pdip);
364 static int mptsas_config_one_addr(dev_info_t *pdip, uint64_t sasaddr, int lun,
365 dev_info_t **lundip);
366 static int mptsas_config_one_phy(dev_info_t *pdip, uint8_t phy, int lun,
367 dev_info_t **lundip);
368
369 static int mptsas_config_target(dev_info_t *pdip, mptsas_target_t *ptgt);
370 static int mptsas_offline_target(dev_info_t *pdip, char *name);
371
372 static int mptsas_config_raid(dev_info_t *pdip, uint16_t target,
373 dev_info_t **dip);
374
375 static int mptsas_config_luns(dev_info_t *pdip, mptsas_target_t *ptgt);
376 static int mptsas_probe_lun(dev_info_t *pdip, int lun,
377 dev_info_t **dip, mptsas_target_t *ptgt);
448 * FMA Prototypes
449 */
450 static void mptsas_fm_init(mptsas_t *mpt);
451 static void mptsas_fm_fini(mptsas_t *mpt);
452 static int mptsas_fm_error_cb(dev_info_t *, ddi_fm_error_t *, const void *);
453
454 extern pri_t minclsyspri, maxclsyspri;
455
456 /*
457 * This device is created by the SCSI pseudo nexus driver (SCSI vHCI). It is
458 * under this device that the paths to a physical device are created when
459 * MPxIO is used.
460 */
461 extern dev_info_t *scsi_vhci_dip;
462
463 /*
464 * Tunable timeout value for Inquiry VPD page 0x83
465 * By default the value is 30 seconds.
466 */
467 int mptsas_inq83_retry_timeout = 30;
468
469 /*
470 * This is used to allocate memory for message frame storage, not for
471 * data I/O DMA. All message frames must be stored in the first 4G of
472 * physical memory.
473 */
474 ddi_dma_attr_t mptsas_dma_attrs = {
475 DMA_ATTR_V0, /* attribute layout version */
476 0x0ull, /* address low - should be 0 (longlong) */
477 0xffffffffull, /* address high - 32-bit max range */
478 0x00ffffffull, /* count max - max DMA object size */
479 4, /* allocation alignment requirements */
480 0x78, /* burstsizes - binary encoded values */
481 1, /* minxfer - gran. of DMA engine */
482 0x00ffffffull, /* maxxfer - gran. of DMA engine */
483 0xffffffffull, /* max segment size (DMA boundary) */
484 MPTSAS_MAX_DMA_SEGS, /* scatter/gather list length */
485 512, /* granularity - device transfer size */
486 0 /* flags, set to 0 */
487 };
2601
2602 /*
2603 * Store the reply descriptor post queue memory address. This chip
2604 * uses this address to write to the reply descriptor post queue. The
2605 * second address is the address mpt uses to manage the queue.
2606 */
2607 mpt->m_post_queue_dma_addr = cookie.dmac_laddress;
2608 mpt->m_post_queue = memp;
2609
2610 /*
2611 * Clear the reply post queue memory.
2612 */
2613 bzero(mpt->m_post_queue, mem_size);
2614
2615 return (DDI_SUCCESS);
2616 }
2617
2618 static void
2619 mptsas_alloc_reply_args(mptsas_t *mpt)
2620 {
2621 if (mpt->m_replyh_args != NULL) {
2622 kmem_free(mpt->m_replyh_args, sizeof (m_replyh_arg_t)
2623 * mpt->m_max_replies);
2624 mpt->m_replyh_args = NULL;
2625 }
2626 mpt->m_replyh_args = kmem_zalloc(sizeof (m_replyh_arg_t) *
2627 mpt->m_max_replies, KM_SLEEP);
2628 }
2629
2630 static int
2631 mptsas_alloc_extra_sgl_frame(mptsas_t *mpt, mptsas_cmd_t *cmd)
2632 {
2633 mptsas_cache_frames_t *frames = NULL;
2634 if (cmd->cmd_extra_frames == NULL) {
2635 frames = kmem_cache_alloc(mpt->m_cache_frames, KM_NOSLEEP);
2636 if (frames == NULL) {
2637 return (DDI_FAILURE);
2638 }
2639 cmd->cmd_extra_frames = frames;
2640 }
2641 return (DDI_SUCCESS);
2642 }
2643
2644 static void
2645 mptsas_free_extra_sgl_frame(mptsas_t *mpt, mptsas_cmd_t *cmd)
2646 {
2647 if (cmd->cmd_extra_frames) {
4809 args->rfm = reply_addr;
4810
4811 /*
4812 * Record the event if its type is enabled in
4813 * this mpt instance by ioctl.
4814 */
4815 mptsas_record_event(args);
4816
4817 /*
4818 * Handle time critical events
4819 * NOT_RESPONDING/ADDED only now
4820 */
4821 if (mptsas_handle_event_sync(args) == DDI_SUCCESS) {
4822 /*
4823 * Would not return main process,
4824 * just let taskq resolve ack action
4825 * and ack would be sent in taskq thread
4826 */
4827 NDBG20(("send mptsas_handle_event_sync success"));
4828 }
4829 if ((ddi_taskq_dispatch(mpt->m_event_taskq, mptsas_handle_event,
4830 (void *)args, DDI_NOSLEEP)) != DDI_SUCCESS) {
4831 mptsas_log(mpt, CE_WARN, "No memory available"
4832 "for dispatch taskq");
4833 /*
4834 * Return the reply frame to the free queue.
4835 */
4836 ddi_put32(mpt->m_acc_free_queue_hdl,
4837 &((uint32_t *)(void *)
4838 mpt->m_free_queue)[mpt->m_free_index], reply_addr);
4839 (void) ddi_dma_sync(mpt->m_dma_free_queue_hdl, 0, 0,
4840 DDI_DMA_SYNC_FORDEV);
4841 if (++mpt->m_free_index == mpt->m_free_queue_depth) {
4842 mpt->m_free_index = 0;
4843 }
4844
4845 ddi_put32(mpt->m_datap,
4846 &mpt->m_reg->ReplyFreeHostIndex, mpt->m_free_index);
4847 }
4848 return;
5746 mutex_exit(&mpt->m_mutex);
5747
5748 parent = NULL;
5749 continue;
5750 }
5751 (void) sprintf(phy_mask_name, "%x", phymask);
5752 }
5753 parent = scsi_hba_iport_find(mpt->m_dip,
5754 phy_mask_name);
5755 if (parent == NULL) {
5756 mptsas_log(mpt, CE_WARN, "Failed to find an "
5757 "iport, should not happen!");
5758 goto out;
5759 }
5760
5761 }
5762 ASSERT(parent);
5763 handle_topo_change:
5764
5765 mutex_enter(&mpt->m_mutex);
5766
5767 mptsas_handle_topo_change(topo_node, parent);
5768 save_node = topo_node;
5769 topo_node = topo_node->next;
5770 ASSERT(save_node);
5771 kmem_free(save_node, sizeof (mptsas_topo_change_list_t));
5772 mutex_exit(&mpt->m_mutex);
5773
5774 if ((flags == MPTSAS_TOPO_FLAG_DIRECT_ATTACHED_DEVICE) ||
5775 (flags == MPTSAS_TOPO_FLAG_RAID_PHYSDRV_ASSOCIATED) ||
5776 (flags == MPTSAS_TOPO_FLAG_RAID_ASSOCIATED)) {
5777 /*
5778 * If direct attached device associated, make sure
5779 * reset the parent before start the next one. But
5780 * all devices associated with expander shares the
5781 * parent. Also, reset parent if this is for RAID.
5782 */
5783 parent = NULL;
5784 }
5785 }
5786 out:
5787 kmem_free(phy_mask_name, MPTSAS_MAX_PHYS);
6037 MPTSAS_NUM_PHYS, 0) !=
6038 DDI_PROP_SUCCESS) {
6039 (void) ddi_prop_remove(DDI_DEV_T_NONE, parent,
6040 MPTSAS_NUM_PHYS);
6041 mptsas_log(mpt, CE_WARN, "mptsas num phys "
6042 "prop update failed");
6043 break;
6044 }
6045 if (ddi_prop_update_int(DDI_DEV_T_NONE, parent,
6046 MPTSAS_VIRTUAL_PORT, 1) !=
6047 DDI_PROP_SUCCESS) {
6048 (void) ddi_prop_remove(DDI_DEV_T_NONE, parent,
6049 MPTSAS_VIRTUAL_PORT);
6050 mptsas_log(mpt, CE_WARN, "mptsas virtual port "
6051 "prop update failed");
6052 break;
6053 }
6054 }
6055
6056 mutex_enter(&mpt->m_mutex);
6057 if (mptsas_set_led_status(mpt, ptgt, 0) != DDI_SUCCESS) {
6058 NDBG14(("mptsas: clear LED for tgt %x failed",
6059 ptgt->m_slot_num));
6060 }
6061 if (rval == DDI_SUCCESS) {
6062 mptsas_tgt_free(&mpt->m_active->m_tgttbl,
6063 ptgt->m_sas_wwn, ptgt->m_phymask);
6064 ptgt = NULL;
6065 } else {
6066 /*
6067 * clean DR_INTRANSITION flag to allow I/O down to
6068 * PHCI driver since failover finished.
6069 * Invalidate the devhdl
6070 */
6071 ptgt->m_devhdl = MPTSAS_INVALID_DEVHDL;
6072 ptgt->m_tgt_unconfigured = 0;
6073 mutex_enter(&mpt->m_tx_waitq_mutex);
6074 ptgt->m_dr_flag = MPTSAS_DR_INACTIVE;
6075 mutex_exit(&mpt->m_tx_waitq_mutex);
6076 }
6077
6078 /*
6079 * Send SAS IO Unit Control to free the dev handle
6080 */
6973
6974 /*
6975 * handle events from ioc
6976 */
6977 static void
6978 mptsas_handle_event(void *args)
6979 {
6980 m_replyh_arg_t *replyh_arg;
6981 pMpi2EventNotificationReply_t eventreply;
6982 uint32_t event, iocloginfo, rfm;
6983 uint32_t status;
6984 uint8_t port;
6985 mptsas_t *mpt;
6986 uint_t iocstatus;
6987
6988 replyh_arg = (m_replyh_arg_t *)args;
6989 rfm = replyh_arg->rfm;
6990 mpt = replyh_arg->mpt;
6991
6992 mutex_enter(&mpt->m_mutex);
6993
6994 eventreply = (pMpi2EventNotificationReply_t)
6995 (mpt->m_reply_frame + (rfm - mpt->m_reply_frame_dma_addr));
6996 event = ddi_get16(mpt->m_acc_reply_frame_hdl, &eventreply->Event);
6997
6998 if (iocstatus = ddi_get16(mpt->m_acc_reply_frame_hdl,
6999 &eventreply->IOCStatus)) {
7000 if (iocstatus == MPI2_IOCSTATUS_FLAG_LOG_INFO_AVAILABLE) {
7001 mptsas_log(mpt, CE_WARN,
7002 "!mptsas_handle_event: IOCStatus=0x%x, "
7003 "IOCLogInfo=0x%x", iocstatus,
7004 ddi_get32(mpt->m_acc_reply_frame_hdl,
7005 &eventreply->IOCLogInfo));
7006 } else {
7007 mptsas_log(mpt, CE_WARN,
7008 "mptsas_handle_event: IOCStatus=0x%x, "
7009 "IOCLogInfo=0x%x", iocstatus,
7010 ddi_get32(mpt->m_acc_reply_frame_hdl,
7011 &eventreply->IOCLogInfo));
7012 }
8500 int slot;
8501 uchar_t reason;
8502 uint_t stat;
8503
8504 NDBG25(("mptsas_flush_target: target=%d lun=%d", target, lun));
8505
8506 /*
8507 * Make sure the I/O Controller has flushed all cmds
8508 * that are associated with this target for a target reset
8509 * and target/lun for abort task set.
8510 * Account for TM requests, which use the last SMID.
8511 */
8512 for (slot = 0; slot <= mpt->m_active->m_n_slots; slot++) {
8513 if ((cmd = slots->m_slot[slot]) == NULL)
8514 continue;
8515 reason = CMD_RESET;
8516 stat = STAT_DEV_RESET;
8517 switch (tasktype) {
8518 case MPI2_SCSITASKMGMT_TASKTYPE_TARGET_RESET:
8519 if (Tgt(cmd) == target) {
8520 NDBG25(("mptsas_flush_target discovered non-"
8521 "NULL cmd in slot %d, tasktype 0x%x", slot,
8522 tasktype));
8523 mptsas_dump_cmd(mpt, cmd);
8524 mptsas_remove_cmd(mpt, cmd);
8525 mptsas_set_pkt_reason(mpt, cmd, reason, stat);
8526 mptsas_doneq_add(mpt, cmd);
8527 }
8528 break;
8529 case MPI2_SCSITASKMGMT_TASKTYPE_ABRT_TASK_SET:
8530 reason = CMD_ABORTED;
8531 stat = STAT_ABORTED;
8532 /*FALLTHROUGH*/
8533 case MPI2_SCSITASKMGMT_TASKTYPE_LOGICAL_UNIT_RESET:
8534 if ((Tgt(cmd) == target) && (Lun(cmd) == lun)) {
8535
8536 NDBG25(("mptsas_flush_target discovered non-"
8537 "NULL cmd in slot %d, tasktype 0x%x", slot,
8538 tasktype));
8539 mptsas_dump_cmd(mpt, cmd);
8687 cmd->cmd_flags |= CFLAG_FINISHED;
8688 cv_broadcast(&mpt->m_passthru_cv);
8689 cv_broadcast(&mpt->m_config_cv);
8690 cv_broadcast(&mpt->m_fw_diag_cv);
8691 } else {
8692 mptsas_doneq_add(mpt, cmd);
8693 }
8694 }
8695
8696 /*
8697 * Flush the tx_waitq
8698 */
8699 mutex_enter(&mpt->m_tx_waitq_mutex);
8700 while ((cmd = mptsas_tx_waitq_rm(mpt)) != NULL) {
8701 mutex_exit(&mpt->m_tx_waitq_mutex);
8702 mptsas_set_pkt_reason(mpt, cmd, CMD_RESET, STAT_BUS_RESET);
8703 mptsas_doneq_add(mpt, cmd);
8704 mutex_enter(&mpt->m_tx_waitq_mutex);
8705 }
8706 mutex_exit(&mpt->m_tx_waitq_mutex);
8707 }
8708
8709 /*
8710 * set pkt_reason and OR in pkt_statistics flag
8711 */
8712 static void
8713 mptsas_set_pkt_reason(mptsas_t *mpt, mptsas_cmd_t *cmd, uchar_t reason,
8714 uint_t stat)
8715 {
8716 #ifndef __lock_lint
8717 _NOTE(ARGUNUSED(mpt))
8718 #endif
8719
8720 NDBG25(("mptsas_set_pkt_reason: cmd=0x%p reason=%x stat=%x",
8721 (void *)cmd, reason, stat));
8722
8723 if (cmd) {
8724 if (cmd->cmd_pkt->pkt_reason == CMD_CMPLT) {
8725 cmd->cmd_pkt->pkt_reason = reason;
8726 }
9367 (ptgt->m_t_throttle > HOLD_THROTTLE) &&
9368 (ptgt->m_t_ncmds < ptgt->m_t_throttle)) {
9369 mptsas_set_throttle(mpt, ptgt, MAX_THROTTLE);
9370 mptsas_restart_hba(mpt);
9371 }
9372
9373 if ((ptgt->m_t_ncmds > 0) &&
9374 (ptgt->m_timebase)) {
9375
9376 if (ptgt->m_timebase <=
9377 mptsas_scsi_watchdog_tick) {
9378 ptgt->m_timebase +=
9379 mptsas_scsi_watchdog_tick;
9380 ptgt = (mptsas_target_t *)mptsas_hash_traverse(
9381 &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
9382 continue;
9383 }
9384
9385 ptgt->m_timeout -= mptsas_scsi_watchdog_tick;
9386
9387 if (ptgt->m_timeout < 0) {
9388 mptsas_cmd_timeout(mpt, ptgt->m_devhdl);
9389 ptgt = (mptsas_target_t *)mptsas_hash_traverse(
9390 &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
9391 continue;
9392 }
9393
9394 if ((ptgt->m_timeout) <=
9395 mptsas_scsi_watchdog_tick) {
9396 NDBG23(("pending timeout"));
9397 mptsas_set_throttle(mpt, ptgt,
9398 DRAIN_THROTTLE);
9399 }
9400 }
9401
9402 ptgt = (mptsas_target_t *)mptsas_hash_traverse(
9403 &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
9404 }
9405 }
9406
9407 /*
9408 * timeout recovery
9410 static void
9411 mptsas_cmd_timeout(mptsas_t *mpt, uint16_t devhdl)
9412 {
9413
9414 NDBG29(("mptsas_cmd_timeout: target=%d", devhdl));
9415 mptsas_log(mpt, CE_WARN, "Disconnected command timeout for "
9416 "Target %d", devhdl);
9417
9418 /*
9419 * If the current target is not the target passed in,
9420 * try to reset that target.
9421 */
9422 NDBG29(("mptsas_cmd_timeout: device reset"));
9423 if (mptsas_do_scsi_reset(mpt, devhdl) != TRUE) {
9424 mptsas_log(mpt, CE_WARN, "Target %d reset for command timeout "
9425 "recovery failed!", devhdl);
9426 }
9427 }
9428
9429 /*
9430 * Device / Hotplug control
9431 */
9432 static int
9433 mptsas_scsi_quiesce(dev_info_t *dip)
9434 {
9435 mptsas_t *mpt;
9436 scsi_hba_tran_t *tran;
9437
9438 tran = ddi_get_driver_private(dip);
9439 if (tran == NULL || (mpt = TRAN2MPT(tran)) == NULL)
9440 return (-1);
9441
9442 return (mptsas_quiesce_bus(mpt));
9443 }
9444
9445 static int
9446 mptsas_scsi_unquiesce(dev_info_t *dip)
9447 {
9448 mptsas_t *mpt;
9449 scsi_hba_tran_t *tran;
11309 (void) pm_busy_component(mpt->m_dip, 0);
11310 if (mpt->m_power_level != PM_LEVEL_D0) {
11311 mutex_exit(&mpt->m_mutex);
11312 if (pm_raise_power(mpt->m_dip, 0, PM_LEVEL_D0) !=
11313 DDI_SUCCESS) {
11314 mptsas_log(mpt, CE_WARN,
11315 "mptsas%d: mptsas_ioctl: Raise power "
11316 "request failed.", mpt->m_instance);
11317 (void) pm_idle_component(mpt->m_dip, 0);
11318 return (ENXIO);
11319 }
11320 } else {
11321 mutex_exit(&mpt->m_mutex);
11322 }
11323 } else {
11324 mutex_exit(&mpt->m_mutex);
11325 }
11326
11327 if (iport_flag) {
11328 status = scsi_hba_ioctl(dev, cmd, data, mode, credp, rval);
11329 if (status != 0) {
11330 goto out;
11331 }
11332 /*
11333 * The following code control the OK2RM LED, it doesn't affect
11334 * the ioctl return status.
11335 */
11336 if ((cmd == DEVCTL_DEVICE_ONLINE) ||
11337 (cmd == DEVCTL_DEVICE_OFFLINE)) {
11338 if (ndi_dc_allochdl((void *)data, &dcp) !=
11339 NDI_SUCCESS) {
11340 goto out;
11341 }
11342 addr = ndi_dc_getaddr(dcp);
11343 ptgt = mptsas_addr_to_ptgt(mpt, addr, phymask);
11344 if (ptgt == NULL) {
11345 NDBG14(("mptsas_ioctl led control: tgt %s not "
11346 "found", addr));
11347 ndi_dc_freehdl(dcp);
11348 goto out;
11349 }
11350 mutex_enter(&mpt->m_mutex);
11351 if (cmd == DEVCTL_DEVICE_ONLINE) {
11352 ptgt->m_tgt_unconfigured = 0;
11353 } else if (cmd == DEVCTL_DEVICE_OFFLINE) {
11354 ptgt->m_tgt_unconfigured = 1;
11355 }
11356 slotstatus = 0;
11357 #ifdef MPTSAS_GET_LED
11358 /*
11359 * The get led status can't get a valid/reasonable
11360 * state, so ignore the get led status, and write the
11361 * required value directly
11362 */
11363 if (mptsas_get_led_status(mpt, ptgt, &slotstatus) !=
11364 DDI_SUCCESS) {
11365 NDBG14(("mptsas_ioctl: get LED for tgt %s "
11366 "failed %x", addr, slotstatus));
11367 slotstatus = 0;
11368 }
11369 NDBG14(("mptsas_ioctl: LED status %x for %s",
11370 slotstatus, addr));
11371 #endif
11372 if (cmd == DEVCTL_DEVICE_OFFLINE) {
11373 slotstatus |=
11374 MPI2_SEP_REQ_SLOTSTATUS_REQUEST_REMOVE;
11375 } else {
11376 slotstatus &=
11377 ~MPI2_SEP_REQ_SLOTSTATUS_REQUEST_REMOVE;
11378 }
11379 if (mptsas_set_led_status(mpt, ptgt, slotstatus) !=
11380 DDI_SUCCESS) {
11381 NDBG14(("mptsas_ioctl: set LED for tgt %s "
11382 "failed %x", addr, slotstatus));
11383 }
11384 mutex_exit(&mpt->m_mutex);
11385 ndi_dc_freehdl(dcp);
11386 }
11387 goto out;
11388 }
11389 switch (cmd) {
11390 case MPTIOCTL_UPDATE_FLASH:
11391 if (ddi_copyin((void *)data, &flashdata,
11392 sizeof (struct mptsas_update_flash), mode)) {
11393 status = EFAULT;
11394 break;
11395 }
11396
11397 mutex_enter(&mpt->m_mutex);
11398 if (mptsas_update_flash(mpt,
11399 (caddr_t)(long)flashdata.PtrBuffer,
11400 flashdata.ImageSize, flashdata.ImageType, mode)) {
11401 status = EFAULT;
11402 }
11403
11404 /*
11405 * Reset the chip to start using the new
11406 * firmware. Reset if failed also.
11407 */
11408 mpt->m_softstate &= ~MPTSAS_SS_MSG_UNIT_RESET;
13821 *pip = mptsas_find_path_addr(pdip, sas_wwn, lun);
13822 } else {
13823 *pip = mptsas_find_path_phy(pdip, phy);
13824 }
13825
13826 if (*pip != NULL) {
13827 *lun_dip = MDI_PI(*pip)->pi_client->ct_dip;
13828 ASSERT(*lun_dip != NULL);
13829 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, *lun_dip,
13830 (DDI_PROP_DONTPASS | DDI_PROP_NOTPROM),
13831 MDI_CLIENT_GUID_PROP, &old_guid) == DDI_SUCCESS) {
13832 if (strncmp(guid, old_guid, strlen(guid)) == 0) {
13833 /*
13834 * Same path back online again.
13835 */
13836 (void) ddi_prop_free(old_guid);
13837 if ((!MDI_PI_IS_ONLINE(*pip)) &&
13838 (!MDI_PI_IS_STANDBY(*pip)) &&
13839 (ptgt->m_tgt_unconfigured == 0)) {
13840 rval = mdi_pi_online(*pip, 0);
13841 mutex_enter(&mpt->m_mutex);
13842 (void) mptsas_set_led_status(mpt, ptgt,
13843 0);
13844 mutex_exit(&mpt->m_mutex);
13845 } else {
13846 rval = DDI_SUCCESS;
13847 }
13848 if (rval != DDI_SUCCESS) {
13849 mptsas_log(mpt, CE_WARN, "path:target: "
13850 "%x, lun:%x online failed!", target,
13851 lun);
13852 *pip = NULL;
13853 *lun_dip = NULL;
13854 }
13855 return (rval);
13856 } else {
13857 /*
13858 * The GUID of the LUN has changed which maybe
13859 * because customer mapped another volume to the
13860 * same LUN.
13861 */
13862 mptsas_log(mpt, CE_WARN, "The GUID of the "
13863 "target:%x, lun:%x was changed, maybe "
13864 "because someone mapped another volume "
14078 mptsas_log(mpt, CE_WARN, "mptsas driver"
14079 "failed to create pm-capable "
14080 "property, target %d", target);
14081 mdi_rtn = MDI_FAILURE;
14082 goto virt_create_done;
14083 }
14084 }
14085 /*
14086 * Create the phy-num property
14087 */
14088 if (mdi_prop_update_int(*pip, "phy-num",
14089 ptgt->m_phynum) != DDI_SUCCESS) {
14090 mptsas_log(mpt, CE_WARN, "mptsas driver unable to "
14091 "create phy-num property for target %d lun %d",
14092 target, lun);
14093 mdi_rtn = MDI_FAILURE;
14094 goto virt_create_done;
14095 }
14096 NDBG20(("new path:%s onlining,", MDI_PI(*pip)->pi_addr));
14097 mdi_rtn = mdi_pi_online(*pip, 0);
14098 if (mdi_rtn == MDI_SUCCESS) {
14099 mutex_enter(&mpt->m_mutex);
14100 if (mptsas_set_led_status(mpt, ptgt, 0) !=
14101 DDI_SUCCESS) {
14102 NDBG14(("mptsas: clear LED for slot %x "
14103 "failed", ptgt->m_slot_num));
14104 }
14105 mutex_exit(&mpt->m_mutex);
14106 }
14107 if (mdi_rtn == MDI_NOT_SUPPORTED) {
14108 mdi_rtn = MDI_FAILURE;
14109 }
14110 virt_create_done:
14111 if (*pip && mdi_rtn != MDI_SUCCESS) {
14112 (void) mdi_pi_free(*pip, 0);
14113 *pip = NULL;
14114 *lun_dip = NULL;
14115 }
14116 }
14117
14118 scsi_hba_nodename_compatible_free(nodename, compatible);
14119 if (lun_addr != NULL) {
14120 kmem_free(lun_addr, SCSI_MAXNAMELEN);
14121 }
14122 if (wwn_str != NULL) {
14123 kmem_free(wwn_str, MPTSAS_WWN_STRLEN);
14124 }
14125 if (component != NULL) {
14126 kmem_free(component, MAXPATHLEN);
14440 if (ndi_prop_update_int(DDI_DEV_T_NONE,
14441 *lun_dip, "phy-num", ptgt->m_phynum) !=
14442 DDI_PROP_SUCCESS) {
14443 mptsas_log(mpt, CE_WARN, "mptsas driver "
14444 "failed to create phy-num property for "
14445 "target %d", target);
14446 ndi_rtn = NDI_FAILURE;
14447 goto phys_create_done;
14448 }
14449 }
14450 phys_create_done:
14451 /*
14452 * If props were setup ok, online the lun
14453 */
14454 if (ndi_rtn == NDI_SUCCESS) {
14455 /*
14456 * Try to online the new node
14457 */
14458 ndi_rtn = ndi_devi_online(*lun_dip, NDI_ONLINE_ATTACH);
14459 }
14460 if (ndi_rtn == NDI_SUCCESS) {
14461 mutex_enter(&mpt->m_mutex);
14462 if (mptsas_set_led_status(mpt, ptgt, 0) !=
14463 DDI_SUCCESS) {
14464 NDBG14(("mptsas: clear LED for tgt %x "
14465 "failed", ptgt->m_slot_num));
14466 }
14467 mutex_exit(&mpt->m_mutex);
14468 }
14469
14470 /*
14471 * If success set rtn flag, else unwire alloc'd lun
14472 */
14473 if (ndi_rtn != NDI_SUCCESS) {
14474 NDBG12(("mptsas driver unable to online "
14475 "target %d lun %d", target, lun));
14476 ndi_prop_remove_all(*lun_dip);
14477 (void) ndi_devi_free(*lun_dip);
14478 *lun_dip = NULL;
14479 }
14480 }
14481
14482 scsi_hba_nodename_compatible_free(nodename, compatible);
14483
14484 if (wwn_str != NULL) {
14485 kmem_free(wwn_str, MPTSAS_WWN_STRLEN);
14486 }
14487 if (component != NULL) {
14488 kmem_free(component, MAXPATHLEN);
15341 }
15342 static mptsas_target_t *
15343 mptsas_addr_to_ptgt(mptsas_t *mpt, char *addr, mptsas_phymask_t phymask)
15344 {
15345 uint8_t phynum;
15346 uint64_t wwn;
15347 int lun;
15348 mptsas_target_t *ptgt = NULL;
15349
15350 if (mptsas_parse_address(addr, &wwn, &phynum, &lun) != DDI_SUCCESS) {
15351 return (NULL);
15352 }
15353 if (addr[0] == 'w') {
15354 ptgt = mptsas_wwid_to_ptgt(mpt, (int)phymask, wwn);
15355 } else {
15356 ptgt = mptsas_phy_to_tgt(mpt, (int)phymask, phynum);
15357 }
15358 return (ptgt);
15359 }
15360
15361 #ifdef MPTSAS_GET_LED
15362 static int
15363 mptsas_get_led_status(mptsas_t *mpt, mptsas_target_t *ptgt,
15364 uint32_t *slotstatus)
15365 {
15366 return (mptsas_send_sep(mpt, ptgt, slotstatus,
15367 MPI2_SEP_REQ_ACTION_READ_STATUS));
15368 }
15369 #endif
15370 static int
15371 mptsas_set_led_status(mptsas_t *mpt, mptsas_target_t *ptgt, uint32_t slotstatus)
15372 {
15373 NDBG14(("mptsas_ioctl: set LED status %x for slot %x",
15374 slotstatus, ptgt->m_slot_num));
15375 return (mptsas_send_sep(mpt, ptgt, &slotstatus,
15376 MPI2_SEP_REQ_ACTION_WRITE_STATUS));
15377 }
15378 /*
15379 * send sep request, use enclosure/slot addressing
15380 */
15381 static int mptsas_send_sep(mptsas_t *mpt, mptsas_target_t *ptgt,
15382 uint32_t *status, uint8_t act)
15383 {
15384 Mpi2SepRequest_t req;
15385 Mpi2SepReply_t rep;
15386 int ret;
15387
15388 ASSERT(mutex_owned(&mpt->m_mutex));
15389
15390 bzero(&req, sizeof (req));
15391 bzero(&rep, sizeof (rep));
15392
15393 /* Do nothing for RAID volumes */
15394 if (ptgt->m_phymask == 0) {
15395 NDBG14(("mptsas_send_sep: Skip RAID volumes"));
15396 return (DDI_FAILURE);
15397 }
15398
15399 req.Function = MPI2_FUNCTION_SCSI_ENCLOSURE_PROCESSOR;
15400 req.Action = act;
15401 req.Flags = MPI2_SEP_REQ_FLAGS_ENCLOSURE_SLOT_ADDRESS;
15402 req.EnclosureHandle = LE_16(ptgt->m_enclosure);
15403 req.Slot = LE_16(ptgt->m_slot_num);
15404 if (act == MPI2_SEP_REQ_ACTION_WRITE_STATUS) {
15405 req.SlotStatus = LE_32(*status);
15406 }
15407 ret = mptsas_do_passthru(mpt, (uint8_t *)&req, (uint8_t *)&rep, NULL,
15408 sizeof (req), sizeof (rep), NULL, 0, NULL, 0, 60, FKIOCTL);
15409 if (ret != 0) {
15410 mptsas_log(mpt, CE_NOTE, "mptsas_send_sep: passthru SEP "
15411 "Processor Request message error %d", ret);
15412 return (DDI_FAILURE);
15413 }
15414 /* do passthrough success, check the ioc status */
15415 if (LE_16(rep.IOCStatus) != MPI2_IOCSTATUS_SUCCESS) {
15416 if ((LE_16(rep.IOCStatus) & MPI2_IOCSTATUS_MASK) ==
15417 MPI2_IOCSTATUS_INVALID_FIELD) {
15418 mptsas_log(mpt, CE_NOTE, "send sep act %x: Not "
15419 "supported action, loginfo %x", act,
15420 LE_32(rep.IOCLogInfo));
15421 return (DDI_FAILURE);
15422 }
15423 mptsas_log(mpt, CE_NOTE, "send_sep act %x: ioc "
15424 "status:%x", act, LE_16(rep.IOCStatus));
15425 return (DDI_FAILURE);
15426 }
15427 if (act != MPI2_SEP_REQ_ACTION_WRITE_STATUS) {
15428 *status = LE_32(rep.SlotStatus);
15429 }
15430
15431 return (DDI_SUCCESS);
15432 }
15433
15434 int
15435 mptsas_dma_addr_create(mptsas_t *mpt, ddi_dma_attr_t dma_attr,
15436 ddi_dma_handle_t *dma_hdp, ddi_acc_handle_t *acc_hdp, caddr_t *dma_memp,
15437 uint32_t alloc_size, ddi_dma_cookie_t *cookiep)
15438 {
15439 ddi_dma_cookie_t new_cookie;
15440 size_t alloc_len;
15441 uint_t ncookie;
15442
15443 if (cookiep == NULL)
15444 cookiep = &new_cookie;
15445
15446 if (ddi_dma_alloc_handle(mpt->m_dip, &dma_attr, DDI_DMA_SLEEP,
15447 NULL, dma_hdp) != DDI_SUCCESS) {
15448 dma_hdp = NULL;
15449 return (FALSE);
15450 }
15451
15452 if (ddi_dma_mem_alloc(*dma_hdp, alloc_size, &mpt->m_dev_acc_attr,
15453 DDI_DMA_CONSISTENT, DDI_DMA_SLEEP, NULL, dma_memp, &alloc_len,
|
220 static void mptsas_flush_hba(mptsas_t *mpt);
221 static void mptsas_flush_target(mptsas_t *mpt, ushort_t target, int lun,
222 uint8_t tasktype);
223 static void mptsas_set_pkt_reason(mptsas_t *mpt, mptsas_cmd_t *cmd,
224 uchar_t reason, uint_t stat);
225
226 static uint_t mptsas_intr(caddr_t arg1, caddr_t arg2);
227 static void mptsas_process_intr(mptsas_t *mpt,
228 pMpi2ReplyDescriptorsUnion_t reply_desc_union);
229 static void mptsas_handle_scsi_io_success(mptsas_t *mpt,
230 pMpi2ReplyDescriptorsUnion_t reply_desc);
231 static void mptsas_handle_address_reply(mptsas_t *mpt,
232 pMpi2ReplyDescriptorsUnion_t reply_desc);
233 static int mptsas_wait_intr(mptsas_t *mpt, int polltime);
234 static void mptsas_sge_setup(mptsas_t *mpt, mptsas_cmd_t *cmd,
235 uint32_t *control, pMpi2SCSIIORequest_t frame, ddi_acc_handle_t acc_hdl);
236
237 static void mptsas_watch(void *arg);
238 static void mptsas_watchsubr(mptsas_t *mpt);
239 static void mptsas_cmd_timeout(mptsas_t *mpt, uint16_t devhdl);
240 static void mptsas_kill_target(mptsas_t *mpt, mptsas_target_t *ptgt);
241
242 static void mptsas_start_passthru(mptsas_t *mpt, mptsas_cmd_t *cmd);
243 static int mptsas_do_passthru(mptsas_t *mpt, uint8_t *request, uint8_t *reply,
244 uint8_t *data, uint32_t request_size, uint32_t reply_size,
245 uint32_t data_size, uint32_t direction, uint8_t *dataout,
246 uint32_t dataout_size, short timeout, int mode);
247 static int mptsas_free_devhdl(mptsas_t *mpt, uint16_t devhdl);
248
249 static uint8_t mptsas_get_fw_diag_buffer_number(mptsas_t *mpt,
250 uint32_t unique_id);
251 static void mptsas_start_diag(mptsas_t *mpt, mptsas_cmd_t *cmd);
252 static int mptsas_post_fw_diag_buffer(mptsas_t *mpt,
253 mptsas_fw_diagnostic_buffer_t *pBuffer, uint32_t *return_code);
254 static int mptsas_release_fw_diag_buffer(mptsas_t *mpt,
255 mptsas_fw_diagnostic_buffer_t *pBuffer, uint32_t *return_code,
256 uint32_t diag_type);
257 static int mptsas_diag_register(mptsas_t *mpt,
258 mptsas_fw_diag_register_t *diag_register, uint32_t *return_code);
259 static int mptsas_diag_unregister(mptsas_t *mpt,
260 mptsas_fw_diag_unregister_t *diag_unregister, uint32_t *return_code);
331 static dev_info_t *mptsas_find_smp_child(dev_info_t *pdip, char *str_wwn);
332
333 static int mptsas_parse_address(char *name, uint64_t *wwid, uint8_t *phy,
334 int *lun);
335 static int mptsas_parse_smp_name(char *name, uint64_t *wwn);
336
337 static mptsas_target_t *mptsas_phy_to_tgt(mptsas_t *mpt, int phymask,
338 uint8_t phy);
339 static mptsas_target_t *mptsas_wwid_to_ptgt(mptsas_t *mpt, int phymask,
340 uint64_t wwid);
341 static mptsas_smp_t *mptsas_wwid_to_psmp(mptsas_t *mpt, int phymask,
342 uint64_t wwid);
343
344 static int mptsas_inquiry(mptsas_t *mpt, mptsas_target_t *ptgt, int lun,
345 uchar_t page, unsigned char *buf, int len, int *rlen, uchar_t evpd);
346
347 static int mptsas_get_target_device_info(mptsas_t *mpt, uint32_t page_address,
348 uint16_t *handle, mptsas_target_t **pptgt);
349 static void mptsas_update_phymask(mptsas_t *mpt);
350
351 static dev_info_t *mptsas_get_dip_from_dev(dev_t dev,
352 mptsas_phymask_t *phymask);
353 static mptsas_target_t *mptsas_addr_to_ptgt(mptsas_t *mpt, char *addr,
354 mptsas_phymask_t phymask);
355
356
357 /*
358 * Enumeration / DR functions
359 */
360 static void mptsas_config_all(dev_info_t *pdip);
361 static int mptsas_config_one_addr(dev_info_t *pdip, uint64_t sasaddr, int lun,
362 dev_info_t **lundip);
363 static int mptsas_config_one_phy(dev_info_t *pdip, uint8_t phy, int lun,
364 dev_info_t **lundip);
365
366 static int mptsas_config_target(dev_info_t *pdip, mptsas_target_t *ptgt);
367 static int mptsas_offline_target(dev_info_t *pdip, char *name);
368
369 static int mptsas_config_raid(dev_info_t *pdip, uint16_t target,
370 dev_info_t **dip);
371
372 static int mptsas_config_luns(dev_info_t *pdip, mptsas_target_t *ptgt);
373 static int mptsas_probe_lun(dev_info_t *pdip, int lun,
374 dev_info_t **dip, mptsas_target_t *ptgt);
445 * FMA Prototypes
446 */
447 static void mptsas_fm_init(mptsas_t *mpt);
448 static void mptsas_fm_fini(mptsas_t *mpt);
449 static int mptsas_fm_error_cb(dev_info_t *, ddi_fm_error_t *, const void *);
450
451 extern pri_t minclsyspri, maxclsyspri;
452
453 /*
454 * This device is created by the SCSI pseudo nexus driver (SCSI vHCI). It is
455 * under this device that the paths to a physical device are created when
456 * MPxIO is used.
457 */
458 extern dev_info_t *scsi_vhci_dip;
459
460 /*
461 * Tunable timeout value for Inquiry VPD page 0x83
462 * By default the value is 30 seconds.
463 */
464 int mptsas_inq83_retry_timeout = 30;
465 /*
466 * Maximum number of command timeouts (0 - 255) considered acceptable.
467 */
468 int mptsas_timeout_threshold = 2;
469 /*
470 * Timeouts exceeding threshold within this period are considered excessive.
471 */
472 int mptsas_timeout_interval = 30;
473
474 /*
475 * This is used to allocate memory for message frame storage, not for
476 * data I/O DMA. All message frames must be stored in the first 4G of
477 * physical memory.
478 */
479 ddi_dma_attr_t mptsas_dma_attrs = {
480 DMA_ATTR_V0, /* attribute layout version */
481 0x0ull, /* address low - should be 0 (longlong) */
482 0xffffffffull, /* address high - 32-bit max range */
483 0x00ffffffull, /* count max - max DMA object size */
484 4, /* allocation alignment requirements */
485 0x78, /* burstsizes - binary encoded values */
486 1, /* minxfer - gran. of DMA engine */
487 0x00ffffffull, /* maxxfer - gran. of DMA engine */
488 0xffffffffull, /* max segment size (DMA boundary) */
489 MPTSAS_MAX_DMA_SEGS, /* scatter/gather list length */
490 512, /* granularity - device transfer size */
491 0 /* flags, set to 0 */
492 };
2606
2607 /*
2608 * Store the reply descriptor post queue memory address. This chip
2609 * uses this address to write to the reply descriptor post queue. The
2610 * second address is the address mpt uses to manage the queue.
2611 */
2612 mpt->m_post_queue_dma_addr = cookie.dmac_laddress;
2613 mpt->m_post_queue = memp;
2614
2615 /*
2616 * Clear the reply post queue memory.
2617 */
2618 bzero(mpt->m_post_queue, mem_size);
2619
2620 return (DDI_SUCCESS);
2621 }
2622
2623 static void
2624 mptsas_alloc_reply_args(mptsas_t *mpt)
2625 {
2626 if (mpt->m_replyh_args == NULL) {
2627 mpt->m_replyh_args = kmem_zalloc(sizeof (m_replyh_arg_t) *
2628 mpt->m_max_replies, KM_SLEEP);
2629 }
2630 }
2631
2632 static int
2633 mptsas_alloc_extra_sgl_frame(mptsas_t *mpt, mptsas_cmd_t *cmd)
2634 {
2635 mptsas_cache_frames_t *frames = NULL;
2636 if (cmd->cmd_extra_frames == NULL) {
2637 frames = kmem_cache_alloc(mpt->m_cache_frames, KM_NOSLEEP);
2638 if (frames == NULL) {
2639 return (DDI_FAILURE);
2640 }
2641 cmd->cmd_extra_frames = frames;
2642 }
2643 return (DDI_SUCCESS);
2644 }
2645
2646 static void
2647 mptsas_free_extra_sgl_frame(mptsas_t *mpt, mptsas_cmd_t *cmd)
2648 {
2649 if (cmd->cmd_extra_frames) {
4811 args->rfm = reply_addr;
4812
4813 /*
4814 * Record the event if its type is enabled in
4815 * this mpt instance by ioctl.
4816 */
4817 mptsas_record_event(args);
4818
4819 /*
4820 * Handle time critical events
4821 * NOT_RESPONDING/ADDED only now
4822 */
4823 if (mptsas_handle_event_sync(args) == DDI_SUCCESS) {
4824 /*
4825 * Would not return main process,
4826 * just let taskq resolve ack action
4827 * and ack would be sent in taskq thread
4828 */
4829 NDBG20(("send mptsas_handle_event_sync success"));
4830 }
4831
4832 if (mpt->m_in_reset) {
4833 NDBG20(("dropping event received during reset"));
4834 return;
4835 }
4836
4837 if ((ddi_taskq_dispatch(mpt->m_event_taskq, mptsas_handle_event,
4838 (void *)args, DDI_NOSLEEP)) != DDI_SUCCESS) {
4839 mptsas_log(mpt, CE_WARN, "No memory available"
4840 "for dispatch taskq");
4841 /*
4842 * Return the reply frame to the free queue.
4843 */
4844 ddi_put32(mpt->m_acc_free_queue_hdl,
4845 &((uint32_t *)(void *)
4846 mpt->m_free_queue)[mpt->m_free_index], reply_addr);
4847 (void) ddi_dma_sync(mpt->m_dma_free_queue_hdl, 0, 0,
4848 DDI_DMA_SYNC_FORDEV);
4849 if (++mpt->m_free_index == mpt->m_free_queue_depth) {
4850 mpt->m_free_index = 0;
4851 }
4852
4853 ddi_put32(mpt->m_datap,
4854 &mpt->m_reg->ReplyFreeHostIndex, mpt->m_free_index);
4855 }
4856 return;
5754 mutex_exit(&mpt->m_mutex);
5755
5756 parent = NULL;
5757 continue;
5758 }
5759 (void) sprintf(phy_mask_name, "%x", phymask);
5760 }
5761 parent = scsi_hba_iport_find(mpt->m_dip,
5762 phy_mask_name);
5763 if (parent == NULL) {
5764 mptsas_log(mpt, CE_WARN, "Failed to find an "
5765 "iport, should not happen!");
5766 goto out;
5767 }
5768
5769 }
5770 ASSERT(parent);
5771 handle_topo_change:
5772
5773 mutex_enter(&mpt->m_mutex);
5774 /*
5775 * If HBA is being reset, don't perform operations depending
5776 * on the IOC. We must free the topo list, however.
5777 */
5778 if (!mpt->m_in_reset)
5779 mptsas_handle_topo_change(topo_node, parent);
5780 else
5781 NDBG20(("skipping topo change received during reset"));
5782 save_node = topo_node;
5783 topo_node = topo_node->next;
5784 ASSERT(save_node);
5785 kmem_free(save_node, sizeof (mptsas_topo_change_list_t));
5786 mutex_exit(&mpt->m_mutex);
5787
5788 if ((flags == MPTSAS_TOPO_FLAG_DIRECT_ATTACHED_DEVICE) ||
5789 (flags == MPTSAS_TOPO_FLAG_RAID_PHYSDRV_ASSOCIATED) ||
5790 (flags == MPTSAS_TOPO_FLAG_RAID_ASSOCIATED)) {
5791 /*
5792 * If direct attached device associated, make sure
5793 * reset the parent before start the next one. But
5794 * all devices associated with expander shares the
5795 * parent. Also, reset parent if this is for RAID.
5796 */
5797 parent = NULL;
5798 }
5799 }
5800 out:
5801 kmem_free(phy_mask_name, MPTSAS_MAX_PHYS);
6051 MPTSAS_NUM_PHYS, 0) !=
6052 DDI_PROP_SUCCESS) {
6053 (void) ddi_prop_remove(DDI_DEV_T_NONE, parent,
6054 MPTSAS_NUM_PHYS);
6055 mptsas_log(mpt, CE_WARN, "mptsas num phys "
6056 "prop update failed");
6057 break;
6058 }
6059 if (ddi_prop_update_int(DDI_DEV_T_NONE, parent,
6060 MPTSAS_VIRTUAL_PORT, 1) !=
6061 DDI_PROP_SUCCESS) {
6062 (void) ddi_prop_remove(DDI_DEV_T_NONE, parent,
6063 MPTSAS_VIRTUAL_PORT);
6064 mptsas_log(mpt, CE_WARN, "mptsas virtual port "
6065 "prop update failed");
6066 break;
6067 }
6068 }
6069
6070 mutex_enter(&mpt->m_mutex);
6071 if (rval == DDI_SUCCESS) {
6072 mptsas_tgt_free(&mpt->m_active->m_tgttbl,
6073 ptgt->m_sas_wwn, ptgt->m_phymask);
6074 ptgt = NULL;
6075 } else {
6076 /*
6077 * clean DR_INTRANSITION flag to allow I/O down to
6078 * PHCI driver since failover finished.
6079 * Invalidate the devhdl
6080 */
6081 ptgt->m_devhdl = MPTSAS_INVALID_DEVHDL;
6082 ptgt->m_tgt_unconfigured = 0;
6083 mutex_enter(&mpt->m_tx_waitq_mutex);
6084 ptgt->m_dr_flag = MPTSAS_DR_INACTIVE;
6085 mutex_exit(&mpt->m_tx_waitq_mutex);
6086 }
6087
6088 /*
6089 * Send SAS IO Unit Control to free the dev handle
6090 */
6983
6984 /*
6985 * handle events from ioc
6986 */
6987 static void
6988 mptsas_handle_event(void *args)
6989 {
6990 m_replyh_arg_t *replyh_arg;
6991 pMpi2EventNotificationReply_t eventreply;
6992 uint32_t event, iocloginfo, rfm;
6993 uint32_t status;
6994 uint8_t port;
6995 mptsas_t *mpt;
6996 uint_t iocstatus;
6997
6998 replyh_arg = (m_replyh_arg_t *)args;
6999 rfm = replyh_arg->rfm;
7000 mpt = replyh_arg->mpt;
7001
7002 mutex_enter(&mpt->m_mutex);
7003 /*
7004 * If HBA is being reset, drop incoming event.
7005 */
7006 if (mpt->m_in_reset) {
7007 NDBG20(("dropping event received prior to reset"));
7008 mutex_exit(&mpt->m_mutex);
7009 return;
7010 }
7011
7012 eventreply = (pMpi2EventNotificationReply_t)
7013 (mpt->m_reply_frame + (rfm - mpt->m_reply_frame_dma_addr));
7014 event = ddi_get16(mpt->m_acc_reply_frame_hdl, &eventreply->Event);
7015
7016 if (iocstatus = ddi_get16(mpt->m_acc_reply_frame_hdl,
7017 &eventreply->IOCStatus)) {
7018 if (iocstatus == MPI2_IOCSTATUS_FLAG_LOG_INFO_AVAILABLE) {
7019 mptsas_log(mpt, CE_WARN,
7020 "!mptsas_handle_event: IOCStatus=0x%x, "
7021 "IOCLogInfo=0x%x", iocstatus,
7022 ddi_get32(mpt->m_acc_reply_frame_hdl,
7023 &eventreply->IOCLogInfo));
7024 } else {
7025 mptsas_log(mpt, CE_WARN,
7026 "mptsas_handle_event: IOCStatus=0x%x, "
7027 "IOCLogInfo=0x%x", iocstatus,
7028 ddi_get32(mpt->m_acc_reply_frame_hdl,
7029 &eventreply->IOCLogInfo));
7030 }
8518 int slot;
8519 uchar_t reason;
8520 uint_t stat;
8521
8522 NDBG25(("mptsas_flush_target: target=%d lun=%d", target, lun));
8523
8524 /*
8525 * Make sure the I/O Controller has flushed all cmds
8526 * that are associated with this target for a target reset
8527 * and target/lun for abort task set.
8528 * Account for TM requests, which use the last SMID.
8529 */
8530 for (slot = 0; slot <= mpt->m_active->m_n_slots; slot++) {
8531 if ((cmd = slots->m_slot[slot]) == NULL)
8532 continue;
8533 reason = CMD_RESET;
8534 stat = STAT_DEV_RESET;
8535 switch (tasktype) {
8536 case MPI2_SCSITASKMGMT_TASKTYPE_TARGET_RESET:
8537 if (Tgt(cmd) == target) {
8538 if (cmd->cmd_tgt_addr->m_timeout < 0) {
8539 /*
8540 * When timeout requested, propagate
8541 * proper reason and statistics to
8542 * target drivers.
8543 */
8544 reason = CMD_TIMEOUT;
8545 stat |= STAT_TIMEOUT;
8546 }
8547
8548 NDBG25(("mptsas_flush_target discovered non-"
8549 "NULL cmd in slot %d, tasktype 0x%x", slot,
8550 tasktype));
8551 mptsas_dump_cmd(mpt, cmd);
8552 mptsas_remove_cmd(mpt, cmd);
8553 mptsas_set_pkt_reason(mpt, cmd, reason, stat);
8554 mptsas_doneq_add(mpt, cmd);
8555 }
8556 break;
8557 case MPI2_SCSITASKMGMT_TASKTYPE_ABRT_TASK_SET:
8558 reason = CMD_ABORTED;
8559 stat = STAT_ABORTED;
8560 /*FALLTHROUGH*/
8561 case MPI2_SCSITASKMGMT_TASKTYPE_LOGICAL_UNIT_RESET:
8562 if ((Tgt(cmd) == target) && (Lun(cmd) == lun)) {
8563
8564 NDBG25(("mptsas_flush_target discovered non-"
8565 "NULL cmd in slot %d, tasktype 0x%x", slot,
8566 tasktype));
8567 mptsas_dump_cmd(mpt, cmd);
8715 cmd->cmd_flags |= CFLAG_FINISHED;
8716 cv_broadcast(&mpt->m_passthru_cv);
8717 cv_broadcast(&mpt->m_config_cv);
8718 cv_broadcast(&mpt->m_fw_diag_cv);
8719 } else {
8720 mptsas_doneq_add(mpt, cmd);
8721 }
8722 }
8723
8724 /*
8725 * Flush the tx_waitq
8726 */
8727 mutex_enter(&mpt->m_tx_waitq_mutex);
8728 while ((cmd = mptsas_tx_waitq_rm(mpt)) != NULL) {
8729 mutex_exit(&mpt->m_tx_waitq_mutex);
8730 mptsas_set_pkt_reason(mpt, cmd, CMD_RESET, STAT_BUS_RESET);
8731 mptsas_doneq_add(mpt, cmd);
8732 mutex_enter(&mpt->m_tx_waitq_mutex);
8733 }
8734 mutex_exit(&mpt->m_tx_waitq_mutex);
8735
8736 /*
8737 * Drain the taskqs prior to reallocating resources.
8738 */
8739 mutex_exit(&mpt->m_mutex);
8740 ddi_taskq_wait(mpt->m_event_taskq);
8741 ddi_taskq_wait(mpt->m_dr_taskq);
8742 mutex_enter(&mpt->m_mutex);
8743 }
8744
8745 /*
8746 * set pkt_reason and OR in pkt_statistics flag
8747 */
8748 static void
8749 mptsas_set_pkt_reason(mptsas_t *mpt, mptsas_cmd_t *cmd, uchar_t reason,
8750 uint_t stat)
8751 {
8752 #ifndef __lock_lint
8753 _NOTE(ARGUNUSED(mpt))
8754 #endif
8755
8756 NDBG25(("mptsas_set_pkt_reason: cmd=0x%p reason=%x stat=%x",
8757 (void *)cmd, reason, stat));
8758
8759 if (cmd) {
8760 if (cmd->cmd_pkt->pkt_reason == CMD_CMPLT) {
8761 cmd->cmd_pkt->pkt_reason = reason;
8762 }
9403 (ptgt->m_t_throttle > HOLD_THROTTLE) &&
9404 (ptgt->m_t_ncmds < ptgt->m_t_throttle)) {
9405 mptsas_set_throttle(mpt, ptgt, MAX_THROTTLE);
9406 mptsas_restart_hba(mpt);
9407 }
9408
9409 if ((ptgt->m_t_ncmds > 0) &&
9410 (ptgt->m_timebase)) {
9411
9412 if (ptgt->m_timebase <=
9413 mptsas_scsi_watchdog_tick) {
9414 ptgt->m_timebase +=
9415 mptsas_scsi_watchdog_tick;
9416 ptgt = (mptsas_target_t *)mptsas_hash_traverse(
9417 &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
9418 continue;
9419 }
9420
9421 ptgt->m_timeout -= mptsas_scsi_watchdog_tick;
9422
9423 if (ptgt->m_timeout_count > 0) {
9424 ptgt->m_timeout_interval +=
9425 mptsas_scsi_watchdog_tick;
9426 }
9427 if (ptgt->m_timeout_interval > mptsas_timeout_interval) {
9428 ptgt->m_timeout_interval = 0;
9429 ptgt->m_timeout_count = 0;
9430 }
9431
9432 if (ptgt->m_timeout < 0) {
9433 ptgt->m_timeout_count++;
9434 if (ptgt->m_timeout_count >
9435 mptsas_timeout_threshold) {
9436 ptgt->m_timeout_count = 0;
9437 mptsas_kill_target(mpt, ptgt);
9438 } else {
9439 mptsas_cmd_timeout(mpt, ptgt->m_devhdl);
9440 }
9441 ptgt = (mptsas_target_t *)mptsas_hash_traverse(
9442 &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
9443 continue;
9444 }
9445
9446 if ((ptgt->m_timeout) <=
9447 mptsas_scsi_watchdog_tick) {
9448 NDBG23(("pending timeout"));
9449 mptsas_set_throttle(mpt, ptgt,
9450 DRAIN_THROTTLE);
9451 }
9452 }
9453
9454 ptgt = (mptsas_target_t *)mptsas_hash_traverse(
9455 &mpt->m_active->m_tgttbl, MPTSAS_HASH_NEXT);
9456 }
9457 }
9458
9459 /*
9460 * timeout recovery
9462 static void
9463 mptsas_cmd_timeout(mptsas_t *mpt, uint16_t devhdl)
9464 {
9465
9466 NDBG29(("mptsas_cmd_timeout: target=%d", devhdl));
9467 mptsas_log(mpt, CE_WARN, "Disconnected command timeout for "
9468 "Target %d", devhdl);
9469
9470 /*
9471 * If the current target is not the target passed in,
9472 * try to reset that target.
9473 */
9474 NDBG29(("mptsas_cmd_timeout: device reset"));
9475 if (mptsas_do_scsi_reset(mpt, devhdl) != TRUE) {
9476 mptsas_log(mpt, CE_WARN, "Target %d reset for command timeout "
9477 "recovery failed!", devhdl);
9478 }
9479 }
9480
9481 /*
9482 * target causing too many timeouts
9483 */
9484 static void
9485 mptsas_kill_target(mptsas_t *mpt, mptsas_target_t *ptgt)
9486 {
9487 mptsas_topo_change_list_t *topo_node = NULL;
9488
9489 NDBG29(("mptsas_tgt_kill: target=%d", ptgt->m_devhdl));
9490 mptsas_log(mpt, CE_WARN, "timeout threshold exceeded for "
9491 "Target %d", ptgt->m_devhdl);
9492
9493 topo_node = kmem_zalloc(sizeof (mptsas_topo_change_list_t), KM_SLEEP);
9494 topo_node->mpt = mpt;
9495 topo_node->un.phymask = ptgt->m_phymask;
9496 topo_node->event = MPTSAS_DR_EVENT_OFFLINE_TARGET;
9497 topo_node->devhdl = ptgt->m_devhdl;
9498 if (ptgt->m_deviceinfo & DEVINFO_DIRECT_ATTACHED)
9499 topo_node->flags = MPTSAS_TOPO_FLAG_DIRECT_ATTACHED_DEVICE;
9500 else
9501 topo_node->flags = MPTSAS_TOPO_FLAG_EXPANDER_ATTACHED_DEVICE;
9502 topo_node->object = NULL;
9503
9504 /*
9505 * Launch DR taskq to fake topology change
9506 */
9507 if ((ddi_taskq_dispatch(mpt->m_dr_taskq,
9508 mptsas_handle_dr, (void *)topo_node,
9509 DDI_NOSLEEP)) != DDI_SUCCESS) {
9510 mptsas_log(mpt, CE_NOTE, "mptsas start taskq "
9511 "for fake offline event failed. \n");
9512 }
9513 }
9514
9515 /*
9516 * Device / Hotplug control
9517 */
9518 static int
9519 mptsas_scsi_quiesce(dev_info_t *dip)
9520 {
9521 mptsas_t *mpt;
9522 scsi_hba_tran_t *tran;
9523
9524 tran = ddi_get_driver_private(dip);
9525 if (tran == NULL || (mpt = TRAN2MPT(tran)) == NULL)
9526 return (-1);
9527
9528 return (mptsas_quiesce_bus(mpt));
9529 }
9530
9531 static int
9532 mptsas_scsi_unquiesce(dev_info_t *dip)
9533 {
9534 mptsas_t *mpt;
9535 scsi_hba_tran_t *tran;
11395 (void) pm_busy_component(mpt->m_dip, 0);
11396 if (mpt->m_power_level != PM_LEVEL_D0) {
11397 mutex_exit(&mpt->m_mutex);
11398 if (pm_raise_power(mpt->m_dip, 0, PM_LEVEL_D0) !=
11399 DDI_SUCCESS) {
11400 mptsas_log(mpt, CE_WARN,
11401 "mptsas%d: mptsas_ioctl: Raise power "
11402 "request failed.", mpt->m_instance);
11403 (void) pm_idle_component(mpt->m_dip, 0);
11404 return (ENXIO);
11405 }
11406 } else {
11407 mutex_exit(&mpt->m_mutex);
11408 }
11409 } else {
11410 mutex_exit(&mpt->m_mutex);
11411 }
11412
11413 if (iport_flag) {
11414 status = scsi_hba_ioctl(dev, cmd, data, mode, credp, rval);
11415 goto out;
11416 }
11417 switch (cmd) {
11418 case MPTIOCTL_UPDATE_FLASH:
11419 if (ddi_copyin((void *)data, &flashdata,
11420 sizeof (struct mptsas_update_flash), mode)) {
11421 status = EFAULT;
11422 break;
11423 }
11424
11425 mutex_enter(&mpt->m_mutex);
11426 if (mptsas_update_flash(mpt,
11427 (caddr_t)(long)flashdata.PtrBuffer,
11428 flashdata.ImageSize, flashdata.ImageType, mode)) {
11429 status = EFAULT;
11430 }
11431
11432 /*
11433 * Reset the chip to start using the new
11434 * firmware. Reset if failed also.
11435 */
11436 mpt->m_softstate &= ~MPTSAS_SS_MSG_UNIT_RESET;
13849 *pip = mptsas_find_path_addr(pdip, sas_wwn, lun);
13850 } else {
13851 *pip = mptsas_find_path_phy(pdip, phy);
13852 }
13853
13854 if (*pip != NULL) {
13855 *lun_dip = MDI_PI(*pip)->pi_client->ct_dip;
13856 ASSERT(*lun_dip != NULL);
13857 if (ddi_prop_lookup_string(DDI_DEV_T_ANY, *lun_dip,
13858 (DDI_PROP_DONTPASS | DDI_PROP_NOTPROM),
13859 MDI_CLIENT_GUID_PROP, &old_guid) == DDI_SUCCESS) {
13860 if (strncmp(guid, old_guid, strlen(guid)) == 0) {
13861 /*
13862 * Same path back online again.
13863 */
13864 (void) ddi_prop_free(old_guid);
13865 if ((!MDI_PI_IS_ONLINE(*pip)) &&
13866 (!MDI_PI_IS_STANDBY(*pip)) &&
13867 (ptgt->m_tgt_unconfigured == 0)) {
13868 rval = mdi_pi_online(*pip, 0);
13869 } else {
13870 rval = DDI_SUCCESS;
13871 }
13872 if (rval != DDI_SUCCESS) {
13873 mptsas_log(mpt, CE_WARN, "path:target: "
13874 "%x, lun:%x online failed!", target,
13875 lun);
13876 *pip = NULL;
13877 *lun_dip = NULL;
13878 }
13879 return (rval);
13880 } else {
13881 /*
13882 * The GUID of the LUN has changed which maybe
13883 * because customer mapped another volume to the
13884 * same LUN.
13885 */
13886 mptsas_log(mpt, CE_WARN, "The GUID of the "
13887 "target:%x, lun:%x was changed, maybe "
13888 "because someone mapped another volume "
14102 mptsas_log(mpt, CE_WARN, "mptsas driver"
14103 "failed to create pm-capable "
14104 "property, target %d", target);
14105 mdi_rtn = MDI_FAILURE;
14106 goto virt_create_done;
14107 }
14108 }
14109 /*
14110 * Create the phy-num property
14111 */
14112 if (mdi_prop_update_int(*pip, "phy-num",
14113 ptgt->m_phynum) != DDI_SUCCESS) {
14114 mptsas_log(mpt, CE_WARN, "mptsas driver unable to "
14115 "create phy-num property for target %d lun %d",
14116 target, lun);
14117 mdi_rtn = MDI_FAILURE;
14118 goto virt_create_done;
14119 }
14120 NDBG20(("new path:%s onlining,", MDI_PI(*pip)->pi_addr));
14121 mdi_rtn = mdi_pi_online(*pip, 0);
14122 if (mdi_rtn == MDI_NOT_SUPPORTED) {
14123 mdi_rtn = MDI_FAILURE;
14124 }
14125 virt_create_done:
14126 if (*pip && mdi_rtn != MDI_SUCCESS) {
14127 (void) mdi_pi_free(*pip, 0);
14128 *pip = NULL;
14129 *lun_dip = NULL;
14130 }
14131 }
14132
14133 scsi_hba_nodename_compatible_free(nodename, compatible);
14134 if (lun_addr != NULL) {
14135 kmem_free(lun_addr, SCSI_MAXNAMELEN);
14136 }
14137 if (wwn_str != NULL) {
14138 kmem_free(wwn_str, MPTSAS_WWN_STRLEN);
14139 }
14140 if (component != NULL) {
14141 kmem_free(component, MAXPATHLEN);
14455 if (ndi_prop_update_int(DDI_DEV_T_NONE,
14456 *lun_dip, "phy-num", ptgt->m_phynum) !=
14457 DDI_PROP_SUCCESS) {
14458 mptsas_log(mpt, CE_WARN, "mptsas driver "
14459 "failed to create phy-num property for "
14460 "target %d", target);
14461 ndi_rtn = NDI_FAILURE;
14462 goto phys_create_done;
14463 }
14464 }
14465 phys_create_done:
14466 /*
14467 * If props were setup ok, online the lun
14468 */
14469 if (ndi_rtn == NDI_SUCCESS) {
14470 /*
14471 * Try to online the new node
14472 */
14473 ndi_rtn = ndi_devi_online(*lun_dip, NDI_ONLINE_ATTACH);
14474 }
14475
14476 /*
14477 * If success set rtn flag, else unwire alloc'd lun
14478 */
14479 if (ndi_rtn != NDI_SUCCESS) {
14480 NDBG12(("mptsas driver unable to online "
14481 "target %d lun %d", target, lun));
14482 ndi_prop_remove_all(*lun_dip);
14483 (void) ndi_devi_free(*lun_dip);
14484 *lun_dip = NULL;
14485 }
14486 }
14487
14488 scsi_hba_nodename_compatible_free(nodename, compatible);
14489
14490 if (wwn_str != NULL) {
14491 kmem_free(wwn_str, MPTSAS_WWN_STRLEN);
14492 }
14493 if (component != NULL) {
14494 kmem_free(component, MAXPATHLEN);
15347 }
15348 static mptsas_target_t *
15349 mptsas_addr_to_ptgt(mptsas_t *mpt, char *addr, mptsas_phymask_t phymask)
15350 {
15351 uint8_t phynum;
15352 uint64_t wwn;
15353 int lun;
15354 mptsas_target_t *ptgt = NULL;
15355
15356 if (mptsas_parse_address(addr, &wwn, &phynum, &lun) != DDI_SUCCESS) {
15357 return (NULL);
15358 }
15359 if (addr[0] == 'w') {
15360 ptgt = mptsas_wwid_to_ptgt(mpt, (int)phymask, wwn);
15361 } else {
15362 ptgt = mptsas_phy_to_tgt(mpt, (int)phymask, phynum);
15363 }
15364 return (ptgt);
15365 }
15366
15367 int
15368 mptsas_dma_addr_create(mptsas_t *mpt, ddi_dma_attr_t dma_attr,
15369 ddi_dma_handle_t *dma_hdp, ddi_acc_handle_t *acc_hdp, caddr_t *dma_memp,
15370 uint32_t alloc_size, ddi_dma_cookie_t *cookiep)
15371 {
15372 ddi_dma_cookie_t new_cookie;
15373 size_t alloc_len;
15374 uint_t ncookie;
15375
15376 if (cookiep == NULL)
15377 cookiep = &new_cookie;
15378
15379 if (ddi_dma_alloc_handle(mpt->m_dip, &dma_attr, DDI_DMA_SLEEP,
15380 NULL, dma_hdp) != DDI_SUCCESS) {
15381 dma_hdp = NULL;
15382 return (FALSE);
15383 }
15384
15385 if (ddi_dma_mem_alloc(*dma_hdp, alloc_size, &mpt->m_dev_acc_attr,
15386 DDI_DMA_CONSISTENT, DDI_DMA_SLEEP, NULL, dma_memp, &alloc_len,
|