Print this page
NEX-17866
Release lun_mutex/port_mutex before logging an online/offline event, and only
do logging if online/offline operation was successful.
While here, follow the comment suggestion and only hold lun_mutex while checking
its state in fcp_scsi_start().

*** 8211,8245 **** mutex_enter(&pptr->port_mutex); mutex_enter(&plun->lun_mutex); if (online == FCP_ONLINE) { ccip = fcp_get_cip(plun, cip, lcount, tcount); ! if (ccip == NULL) { ! goto fail; ! } } else { ! if (fcp_is_child_present(plun, cip) != FC_SUCCESS) { ! goto fail; ! } ccip = cip; } if (online == FCP_ONLINE) { rval = fcp_online_child(plun, ccip, lcount, tcount, flags, &circ); - fc_ulp_log_device_event(pptr->port_fp_handle, - FC_ULP_DEVICE_ONLINE); } else { rval = fcp_offline_child(plun, ccip, lcount, tcount, flags, &circ); - fc_ulp_log_device_event(pptr->port_fp_handle, - FC_ULP_DEVICE_OFFLINE); } ! fail: mutex_exit(&plun->lun_mutex); mutex_exit(&pptr->port_mutex); if (is_mpxio) { mdi_devi_exit(pptr->port_dip, circ); } else { ndi_devi_exit(pptr->port_dip, circ); } --- 8211,8246 ---- mutex_enter(&pptr->port_mutex); mutex_enter(&plun->lun_mutex); if (online == FCP_ONLINE) { ccip = fcp_get_cip(plun, cip, lcount, tcount); ! if (ccip == NULL) ! goto skip; } else { ! if (fcp_is_child_present(plun, cip) != FC_SUCCESS) ! goto skip; ccip = cip; } if (online == FCP_ONLINE) { rval = fcp_online_child(plun, ccip, lcount, tcount, flags, &circ); } else { rval = fcp_offline_child(plun, ccip, lcount, tcount, flags, &circ); } ! skip: ! mutex_exit(&plun->lun_mutex); mutex_exit(&pptr->port_mutex); + if (rval == NDI_SUCCESS) { + fc_ulp_log_device_event(pptr->port_fp_handle, + online == FCP_ONLINE ? + FC_ULP_DEVICE_ONLINE : FC_ULP_DEVICE_OFFLINE); + } + if (is_mpxio) { mdi_devi_exit(pptr->port_dip, circ); } else { ndi_devi_exit(pptr->port_dip, circ); }
*** 11042,11073 **** FCP_DTRACE(fcp_logq, pptr->port_instbuf, fcp_trace, FCP_BUF_LEVEL_9, 0, "fcp_transport Invoked for %x", plun->lun_tgt->tgt_d_id); /* - * It is strange that we enter the fcp_port mutex and the target - * mutex to check the lun state (which has a mutex of its own). - */ - mutex_enter(&pptr->port_mutex); - mutex_enter(&ptgt->tgt_mutex); - - /* * If the device is offline and is not in the process of coming * online, fail the request. */ ! if ((plun->lun_state & FCP_LUN_OFFLINE) && !(plun->lun_state & FCP_LUN_ONLINING)) { ! mutex_exit(&ptgt->tgt_mutex); ! mutex_exit(&pptr->port_mutex); ! ! if (cmd->cmd_fp_pkt->pkt_pd == NULL) { pkt->pkt_reason = CMD_DEV_GONE; - } - return (TRAN_FATAL_ERROR); } cmd->cmd_fp_pkt->pkt_timeout = pkt->pkt_time; /* * If we are suspended, kernel is trying to dump, so don't * block, fail or defer requests - send them down right away. --- 11043,11065 ---- FCP_DTRACE(fcp_logq, pptr->port_instbuf, fcp_trace, FCP_BUF_LEVEL_9, 0, "fcp_transport Invoked for %x", plun->lun_tgt->tgt_d_id); /* * If the device is offline and is not in the process of coming * online, fail the request. */ ! mutex_enter(&plun->lun_mutex); if ((plun->lun_state & FCP_LUN_OFFLINE) && !(plun->lun_state & FCP_LUN_ONLINING)) { ! mutex_exit(&plun->lun_mutex); ! if (cmd->cmd_fp_pkt->pkt_pd == NULL) pkt->pkt_reason = CMD_DEV_GONE; return (TRAN_FATAL_ERROR); } + mutex_exit(&plun->lun_mutex); + cmd->cmd_fp_pkt->pkt_timeout = pkt->pkt_time; /* * If we are suspended, kernel is trying to dump, so don't * block, fail or defer requests - send them down right away.
*** 11088,11097 **** --- 11080,11092 ---- * has gone NULL, while fcp deals cases where pkt_pd is NULL. pkt_pd * could be NULL because the device was disappearing during or since * packet initialization. */ + mutex_enter(&pptr->port_mutex); + mutex_enter(&ptgt->tgt_mutex); + if (((plun->lun_state & FCP_LUN_BUSY) && (!(pptr->port_state & FCP_STATE_SUSPENDED)) && !ddi_in_panic()) || (pptr->port_state & (FCP_STATE_ONLINING | FCP_STATE_IN_CB_DEVC)) || (ptgt->tgt_pd_handle == NULL) || (cmd->cmd_fp_pkt->pkt_pd == NULL)) {