Mercurial > illumos > illumos-gate
changeset 11240:530d474a5d9e
6904131 COMSTAR: Fix unsolicited exchange abort issue
6904115 Turn off DMA handle checking in the fm-capable config parameter
6904120 IO hang during diskomizer test and pci errors during UE register access in FCoE adapter
6901958 memory leak in emlxs_mem_alloc and emlxs_sli3_online
line wrap: on
line diff
--- a/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_clock.c Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_clock.c Thu Dec 03 10:09:44 2009 -0800 @@ -146,14 +146,6 @@ return; } - /* DEBUG - re-examine this path for SLI4 later */ - if (hba->model_info.sli_mask & EMLXS_SLI4_MASK) { - /* Check for linkup timeout */ - emlxs_timer_check_linkup(hba); - - return; - } - bzero((void *)flag, sizeof (flag)); /* Check SLI level timeouts */ @@ -884,7 +876,7 @@ mutex_exit(&EMLXS_PORT_LOCK); /* Try to send clear link attention, if needed */ - if ((send_clear_la == 1) && + if ((hba->sli_mode < EMLXS_HBA_SLI4_MODE) && (send_clear_la == 1) && (mbox = (MAILBOXQ *)emlxs_mem_get(hba, MEM_MBOX, 1))) { mutex_enter(&EMLXS_PORT_LOCK);
--- a/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_dfc.c Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_dfc.c Thu Dec 03 10:09:44 2009 -0800 @@ -10289,6 +10289,13 @@ return (DFC_FCOE_NOTSUPPORTED); } + if (hba->state != FC_READY) { + EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_dfc_error_msg, + "%s: HBA not ready.", emlxs_dfc_xlate(dfc->cmd)); + + return (DFC_DRV_ERROR); + } + size = sizeof (DFC_FCoEFCFList_t) + hba->sli.sli4.FCFICount * sizeof (DFC_FCoEFCFInfo_t); fcflist = (DFC_FCoEFCFList_t *)kmem_zalloc(size, KM_SLEEP);
--- a/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_download.c Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_download.c Thu Dec 03 10:09:44 2009 -0800 @@ -4593,6 +4593,10 @@ vpd = &VPD; + if (hba->model_info.chip == EMLXS_BE_CHIP) { + return (EMLXS_OP_NOT_SUP); + } + if (emlxs_read_wakeup_parms(hba, &hba->wakeup_parms, 0)) { EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_sfs_debug_msg, "emlxs_boot_code_disable: Unable to read wake up parms."); @@ -4644,6 +4648,10 @@ vpd = &VPD; + if (hba->model_info.chip == EMLXS_BE_CHIP) { + return (FC_SUCCESS); + } + /* Read the wakeup parms */ if (emlxs_read_wakeup_parms(hba, &hba->wakeup_parms, 0)) { EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_sfs_debug_msg, @@ -4709,6 +4717,10 @@ { emlxs_port_t *port = &PPORT; + if (hba->model_info.chip == EMLXS_BE_CHIP) { + return (FC_SUCCESS); + } + /* Read the wakeup parms */ if (emlxs_read_wakeup_parms(hba, &hba->wakeup_parms, 1)) { EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_sfs_debug_msg,
--- a/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_fcp.c Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_fcp.c Thu Dec 03 10:09:44 2009 -0800 @@ -3743,7 +3743,7 @@ /* * Issue an ABORT_XRI_CN iocb command to abort an FCP command already issued. - * This must be called while holding the EMLXS_FCCTAB_LOCK + * This must be called while holding the EMLXS_FCTAB_LOCK */ extern IOCBQ * emlxs_create_abort_xri_cn(emlxs_port_t *port, NODELIST *ndlp, @@ -3809,6 +3809,7 @@ } /* emlxs_create_abort_xri_cn() */ +/* This must be called while holding the EMLXS_FCTAB_LOCK */ extern IOCBQ * emlxs_create_abort_xri_cx(emlxs_port_t *port, NODELIST *ndlp, uint16_t xid, CHANNEL *cp, uint8_t class, int32_t flag) @@ -3863,7 +3864,7 @@ -/* This must be called while holding the EMLXS_FCCTAB_LOCK */ +/* This must be called while holding the EMLXS_FCTAB_LOCK */ extern IOCBQ * emlxs_create_close_xri_cn(emlxs_port_t *port, NODELIST *ndlp, uint16_t iotag, CHANNEL *cp) @@ -3927,7 +3928,7 @@ } /* emlxs_create_close_xri_cn() */ -/* This must be called while holding the EMLXS_FCCTAB_LOCK */ +/* This must be called while holding the EMLXS_FCTAB_LOCK */ extern IOCBQ * emlxs_create_close_xri_cx(emlxs_port_t *port, NODELIST *ndlp, uint16_t xid, CHANNEL *cp) @@ -3980,16 +3981,122 @@ } /* emlxs_create_close_xri_cx() */ +#ifdef SFCT_SUPPORT +void +emlxs_abort_fct_exchange(emlxs_hba_t *hba, emlxs_port_t *port, uint32_t rxid) +{ + CHANNEL *cp; + IOCBQ *iocbq; + IOCB *iocb; + + if (rxid == 0 || rxid == 0xFFFF) { + return; + } + + if (hba->sli_mode == EMLXS_HBA_SLI4_MODE) { + EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_fct_detail_msg, + "Aborting FCT exchange: xid=%x", rxid); + + if (emlxs_sli4_unreserve_xri(hba, rxid) == 0) { + /* We have no way to abort unsolicited exchanges */ + /* that we have not responded to at this time */ + /* So we will return for now */ + return; + } + } + + cp = &hba->chan[hba->channel_fcp]; + + mutex_enter(&EMLXS_FCTAB_LOCK); + + /* Create the abort IOCB */ + if (hba->state >= FC_LINK_UP) { + iocbq = emlxs_create_abort_xri_cx(port, NULL, rxid, cp, + CLASS3, ABORT_TYPE_ABTS); + } else { + iocbq = emlxs_create_close_xri_cx(port, NULL, rxid, cp); + } + + mutex_exit(&EMLXS_FCTAB_LOCK); + + if (iocbq) { + iocb = &iocbq->iocb; + EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_fct_detail_msg, + "Aborting FCT exchange: xid=%x iotag=%x", rxid, + iocb->ULPIOTAG); + + EMLXS_SLI_ISSUE_IOCB_CMD(hba, cp, iocbq); + } + +} /* emlxs_abort_fct_exchange() */ +#endif /* SFCT_SUPPORT */ + + +void +emlxs_abort_els_exchange(emlxs_hba_t *hba, emlxs_port_t *port, uint32_t rxid) +{ + CHANNEL *cp; + IOCBQ *iocbq; + IOCB *iocb; + + if (rxid == 0 || rxid == 0xFFFF) { + return; + } + + if (hba->sli_mode == EMLXS_HBA_SLI4_MODE) { + + EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_unsol_els_msg, + "Aborting ELS exchange: xid=%x", rxid); + + if (emlxs_sli4_unreserve_xri(hba, rxid) == 0) { + /* We have no way to abort unsolicited exchanges */ + /* that we have not responded to at this time */ + /* So we will return for now */ + return; + } + } + + cp = &hba->chan[hba->channel_els]; + + mutex_enter(&EMLXS_FCTAB_LOCK); + + /* Create the abort IOCB */ + if (hba->state >= FC_LINK_UP) { + iocbq = emlxs_create_abort_xri_cx(port, NULL, rxid, cp, + CLASS3, ABORT_TYPE_ABTS); + } else { + iocbq = emlxs_create_close_xri_cx(port, NULL, rxid, cp); + } + + mutex_exit(&EMLXS_FCTAB_LOCK); + + if (iocbq) { + iocb = &iocbq->iocb; + EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_unsol_els_msg, + "Aborting ELS exchange: xid=%x iotag=%x", rxid, + iocb->ULPIOTAG); + + EMLXS_SLI_ISSUE_IOCB_CMD(hba, cp, iocbq); + } + +} /* emlxs_abort_els_exchange() */ + + void emlxs_abort_ct_exchange(emlxs_hba_t *hba, emlxs_port_t *port, uint32_t rxid) { CHANNEL *cp; IOCBQ *iocbq; - - EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_unsol_ct_msg, - "Aborting CT exchange: xid=%x", rxid); + IOCB *iocb; + + if (rxid == 0 || rxid == 0xFFFF) { + return; + } if (hba->sli_mode == EMLXS_HBA_SLI4_MODE) { + EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_unsol_ct_msg, + "Aborting CT exchange: xid=%x", rxid); + if (emlxs_sli4_unreserve_xri(hba, rxid) == 0) { /* We have no way to abort unsolicited exchanges */ /* that we have not responded to at this time */ @@ -4000,23 +4107,31 @@ cp = &hba->chan[hba->channel_ct]; + mutex_enter(&EMLXS_FCTAB_LOCK); + /* Create the abort IOCB */ if (hba->state >= FC_LINK_UP) { - iocbq = - emlxs_create_abort_xri_cx(port, NULL, rxid, cp, CLASS3, - ABORT_TYPE_ABTS); + iocbq = emlxs_create_abort_xri_cx(port, NULL, rxid, cp, + CLASS3, ABORT_TYPE_ABTS); } else { iocbq = emlxs_create_close_xri_cx(port, NULL, rxid, cp); } + mutex_exit(&EMLXS_FCTAB_LOCK); + if (iocbq) { + iocb = &iocbq->iocb; + EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_unsol_els_msg, + "Aborting CT exchange: xid=%x iotag=%x", rxid, + iocb->ULPIOTAG); + EMLXS_SLI_ISSUE_IOCB_CMD(hba, cp, iocbq); } } /* emlxs_abort_ct_exchange() */ -/* This must be called while holding the EMLXS_FCCTAB_LOCK */ +/* This must be called while holding the EMLXS_FCTAB_LOCK */ static void emlxs_sbp_abort_add(emlxs_port_t *port, emlxs_buf_t *sbp, Q *abort, uint8_t *flag, emlxs_buf_t *fpkt)
--- a/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_fct.c Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_fct.c Thu Dec 03 10:09:44 2009 -0800 @@ -92,7 +92,8 @@ CHANNEL *cp, IOCBQ *iocbq, MATCHMAP *mp, uint32_t size); static uint32_t emlxs_fct_process_unsol_plogi(emlxs_port_t *port, CHANNEL *cp, IOCBQ *iocbq, MATCHMAP *mp, uint32_t size); -static fct_status_t emlxs_fct_pkt_abort(emlxs_port_t *port, emlxs_buf_t *sbp); +static uint32_t emlxs_fct_pkt_abort_txq(emlxs_port_t *port, + emlxs_buf_t *cmd_sbp); static fct_status_t emlxs_fct_send_qfull_reply(emlxs_port_t *port, emlxs_node_t *ndlp, uint16_t xid, uint32_t class, emlxs_fcp_cmd_t *fcp_cmd); static void emlxs_fct_dbuf_dma_sync(stmf_data_buf_t *dbuf, uint_t sync_type); @@ -1919,7 +1920,7 @@ "emlxs_fct_send_cmd_rsp: Invalid cmd type found. type=%x", fct_cmd->cmd_type); - emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_OWNED); + emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_CMD_POSTED); /* mutex_exit(&cmd_sbp->fct_mtx); */ return (FCT_FAILURE); @@ -1932,7 +1933,7 @@ "Unable to handle FCT_IOF_FORCE_FCA_DONE. type=%x", fct_cmd->cmd_type); - emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_OWNED); + emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_CMD_POSTED); /* mutex_exit(&cmd_sbp->fct_mtx); */ return (FCT_FAILURE); @@ -2273,7 +2274,7 @@ remote_port->rp_handle = ndlp->nlp_Rpi; - emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_OWNED); + emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_CMD_POSTED); /* mutex_exit(&cmd_sbp->fct_mtx); */ TGTPORTSTAT.FctPortRegister++; @@ -2287,7 +2288,7 @@ remote_port->rp_handle = FCT_HANDLE_NONE; - emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_OWNED); + emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_CMD_POSTED); /* mutex_exit(&cmd_sbp->fct_mtx); */ TGTPORTSTAT.FctFailedPortRegister++; @@ -2574,7 +2575,7 @@ if (EMLXS_SLI_PREP_FCT_IOCB(port, cmd_sbp, channel) != IOERR_SUCCESS) { - emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_OWNED); + emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_CMD_POSTED); /* mutex_exit(&cmd_sbp->fct_mtx); */ return (FCT_BUSY); @@ -2644,7 +2645,7 @@ EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_fct_error_msg, "emlxs_fct_send_fcp_status: Unable to allocate packet."); - emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_OWNED); + emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_CMD_POSTED); /* mutex_exit(&cmd_sbp->fct_mtx); */ return (FCT_BUSY); @@ -2740,7 +2741,7 @@ } /* mutex_enter(&cmd_sbp->fct_mtx); */ - emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_OWNED); + emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_CMD_POSTED); /* mutex_exit(&cmd_sbp->fct_mtx); */ return (FCT_BUSY); @@ -2970,7 +2971,7 @@ cmd_sbp->fct_flags &= ~EMLXS_FCT_SEND_STATUS; - emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_OWNED); + emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_CMD_POSTED); /* mutex_exit(&cmd_sbp->fct_mtx); */ #ifdef FCT_API_TRACE @@ -3313,8 +3314,9 @@ return (1); } - EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_unsol_els_msg, "FLOGI: sid=0x%x %s", - iocb->un.elsreq.remoteID, buffer); + EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_unsol_els_msg, + "FLOGI: sid=0x%x xid=%x %s", + iocb->un.elsreq.remoteID, iocb->ULPIOTAG, buffer); return (0); @@ -3338,8 +3340,9 @@ return (1); } - EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_unsol_els_msg, "PLOGI: sid=0x%x %s", - iocb->un.elsreq.remoteID, buffer); + EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_unsol_els_msg, + "PLOGI: sid=0x%x xid=%x %s", + iocb->un.elsreq.remoteID, iocb->ULPIOTAG, buffer); return (0); @@ -4003,7 +4006,7 @@ EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_fct_error_msg, "emlxs_fct_send_els_rsp: Unable to allocate packet."); - emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_OWNED); + emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_CMD_POSTED); /* mutex_exit(&cmd_sbp->fct_mtx); */ return (FCT_FAILURE); @@ -4058,7 +4061,7 @@ } /* mutex_enter(&cmd_sbp->fct_mtx); */ - emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_OWNED); + emlxs_fct_cmd_post(port, fct_cmd, EMLXS_FCT_CMD_POSTED); /* mutex_exit(&cmd_sbp->fct_mtx); */ return (FCT_FAILURE); @@ -4156,7 +4159,7 @@ /* cmd_sbp->fct_mtx must be held to enter */ -uint32_t +static uint32_t emlxs_fct_pkt_abort_txq(emlxs_port_t *port, emlxs_buf_t *cmd_sbp) { emlxs_hba_t *hba = HBA; @@ -4397,10 +4400,10 @@ } EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_fct_detail_msg, - "emlxs_fct_abort: HbaLink %d. " - "xid=%x. cmd_sbp=%p state=%d flags=%x,%x,%x", - hba->state, fct_cmd->cmd_rxid, cmd_sbp, cmd_sbp->fct_state, flags, - cmd_sbp->fct_flags, cmd_sbp->pkt_flags); + "emlxs_fct_abort: hbastate=%x. " + "xid=%x,%x cmd_sbp=%p fctstate=%d flags=%x,%x,%x", + hba->state, fct_cmd->cmd_oxid, fct_cmd->cmd_rxid, cmd_sbp, + cmd_sbp->fct_state, flags, cmd_sbp->fct_flags, cmd_sbp->pkt_flags); if (cmd_sbp->fct_flags & EMLXS_FCT_ABORT_INP) { EMLXS_SLI_ISSUE_IOCB_CMD(hba, cmd_sbp->channel, 0); @@ -4420,9 +4423,9 @@ switch (cmd_sbp->fct_state) { /* These are currently owned by COMSTAR. */ /* They were last processed by emlxs_fct_cmd_post() */ - case EMLXS_FCT_CMD_POSTED: + /* We have NO exchange resources associated with this IO. */ case EMLXS_FCT_OWNED: - goto abort_it_now; + goto abort_done; /* These are on the unsol waitQ in the driver */ case EMLXS_FCT_CMD_WAITQ: @@ -4453,7 +4456,24 @@ } mutex_exit(&EMLXS_PORT_LOCK); - goto abort_it_now; + /*FALLTHROUGH*/ + + /* These are currently owned by COMSTAR. */ + /* They were last processed by emlxs_fct_cmd_post() */ + /* We have residual exchange resources associated with this IO */ + case EMLXS_FCT_CMD_POSTED: + switch (fct_cmd->cmd_type) { + case FCT_CMD_FCP_XCHG: /* Unsol */ + TGTPORTSTAT.FctOutstandingIO--; + emlxs_abort_fct_exchange(hba, port, fct_cmd->cmd_rxid); + break; + + case FCT_CMD_RCVD_ELS: /* Unsol */ + emlxs_abort_els_exchange(hba, port, fct_cmd->cmd_rxid); + break; + } + + goto abort_done; /* These are active in the driver */ /* They were last processed by emlxs_fct_cmd_release() */ @@ -4470,7 +4490,7 @@ TGTPORTSTAT.FctOutstandingIO--; } - goto abort_it_now; + goto abort_done; } /* If we're not online, then all IO will be flushed anyway */ @@ -4579,7 +4599,7 @@ return (FCT_SUCCESS); -abort_it_now: +abort_done: emlxs_fct_cmd_done(port, fct_cmd, EMLXS_FCT_ABORT_DONE); @@ -4613,7 +4633,6 @@ #endif /* FCT_API_TRACE */ MODSYM(fct_handle_event) (port->fct_port, FCT_EVENT_LINK_UP, 0, 0); - } else { if (!hba->ini_mode && !(port->fct_flags & FCT_STATE_PORT_ONLINE)) {
--- a/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_node.c Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_node.c Thu Dec 03 10:09:44 2009 -0800 @@ -82,7 +82,7 @@ mutex_exit(&EMLXS_TX_CHANNEL_LOCK); EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_node_closed_msg, - "node=%p did=%06x channel=%d. offline=%d set.", + "node=%p did=%06x channel=%d. offline=%d update.", ndlp, ndlp->nlp_DID, channelno, timeout); } else if (timeout) { @@ -90,7 +90,7 @@ mutex_exit(&EMLXS_TX_CHANNEL_LOCK); EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_node_closed_msg, - "node=%p did=%06x channel=%d. timeout=%d set.", + "node=%p did=%06x channel=%d. timeout=%d update.", ndlp, ndlp->nlp_DID, channelno, timeout); } else { mutex_exit(&EMLXS_TX_CHANNEL_LOCK); @@ -106,8 +106,20 @@ ndlp->nlp_tics[channelno] = hba->timer_tics + timeout; ndlp->nlp_flag[channelno] |= NLP_OFFLINE; + EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_node_closed_msg, + "node=%p did=%06x channel=%d. offline=%d set.", + ndlp, ndlp->nlp_DID, channelno, timeout); + } else if (timeout) { ndlp->nlp_tics[channelno] = hba->timer_tics + timeout; + + EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_node_closed_msg, + "node=%p did=%06x channel=%d. timeout=%d set.", + ndlp, ndlp->nlp_DID, channelno, timeout); + } else { + EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_node_closed_msg, + "node=%p did=%06x channel=%d.", + ndlp, ndlp->nlp_DID, channelno); }
--- a/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_sli3.c Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_sli3.c Thu Dec 03 10:09:44 2009 -0800 @@ -947,6 +947,12 @@ } } + /* Free the buffers since we were polling */ + (void) emlxs_mem_put(hba, MEM_BUF, (uint8_t *)mp); + mp = NULL; + (void) emlxs_mem_put(hba, MEM_BUF, (uint8_t *)mp1); + mp1 = NULL; + hba->channel_fcp = FC_FCP_RING; hba->channel_els = FC_ELS_RING; hba->channel_ip = FC_IP_RING; @@ -1049,10 +1055,6 @@ } #endif /* MAX_RRDY_SUPPORT */ - /* Free the buffer since we were polling */ - (void) emlxs_mem_put(hba, MEM_BUF, (uint8_t *)mp); - mp = NULL; - /* Reuse mbq from previous mbox */ bzero(mbq, sizeof (MAILBOXQ)); @@ -1470,6 +1472,7 @@ * The leadvile driver will now handle the FLOGI at the driver level */ + (void) kmem_free((uint8_t *)mbq, sizeof (MAILBOXQ)); return (0); failed:
--- a/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_sli4.c Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_sli4.c Thu Dec 03 10:09:44 2009 -0800 @@ -623,7 +623,8 @@ "FCOE info dumped. rsp_cnt=%d status=%x", mb->un.varDmp4.rsp_cnt, mb->mbxStatus); (void) emlxs_parse_fcoe(hba, - (uint8_t *)hba->sli.sli4.dump_region.virt, 0); + (uint8_t *)hba->sli.sli4.dump_region.virt, + mb->un.varDmp4.rsp_cnt); } /* Reuse mbq from previous mbox */ @@ -1454,6 +1455,12 @@ hba->sli.sli4.cfgFCOE.FCMap[1] = FCOE_FCF_MAP1; hba->sli.sli4.cfgFCOE.FCMap[2] = FCOE_FCF_MAP2; + /* Cache the UE MASK registers value for UE error detection */ + hba->sli.sli4.ue_mask_lo = ddi_get32(hba->pci_acc_handle, + (uint32_t *)(hba->pci_addr + PCICFG_UE_MASK_LO_OFFSET)); + hba->sli.sli4.ue_mask_hi = ddi_get32(hba->pci_acc_handle, + (uint32_t *)(hba->pci_addr + PCICFG_UE_MASK_HI_OFFSET)); + return (0); } /* emlxs_sli4_hba_init() */ @@ -3370,7 +3377,7 @@ EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_sli_detail_msg, "FCOE Async Event VLINK CLEAR %d: received ", fcoe->ref_index); - if (fcoe->ref_index == 0) { + if (fcoe->ref_index == hba->vpi_base) { /* * Bounce the link to force rediscovery for * VPI 0. We are ignoring this event for @@ -4348,10 +4355,12 @@ iocbq->flag |= (IOCB_PRIORITY | IOCB_SPECIAL); /* Set up an iotag using special Abort iotags */ + mutex_enter(&EMLXS_FCTAB_LOCK); if ((hba->fc_oor_iotag >= EMLXS_MAX_ABORT_TAG)) { hba->fc_oor_iotag = hba->max_iotag; } iotag = hba->fc_oor_iotag++; + mutex_exit(&EMLXS_FCTAB_LOCK); /* BLS ACC Response */ wqe = &iocbq->wqe; @@ -6893,29 +6902,25 @@ emlxs_port_t *port = &PPORT; uint32_t ue_h; uint32_t ue_l; - uint32_t on1; - uint32_t on2; if (hba->flag & FC_HARDWARE_ERROR) { return; } - on1 = ddi_get32(hba->pci_acc_handle, - (uint32_t *)(hba->pci_addr + PCICFG_UE_STATUS_ONLINE1)); - on2 = ddi_get32(hba->pci_acc_handle, - (uint32_t *)(hba->pci_addr + PCICFG_UE_STATUS_ONLINE2)); - - if (on1 != 0xffffffff || on2 != 0xffffffff) { - ue_l = ddi_get32(hba->pci_acc_handle, - (uint32_t *)(hba->pci_addr + PCICFG_UE_STATUS_LO_OFFSET)); - ue_h = ddi_get32(hba->pci_acc_handle, - (uint32_t *)(hba->pci_addr + PCICFG_UE_STATUS_HI_OFFSET)); - + ue_l = ddi_get32(hba->pci_acc_handle, + (uint32_t *)(hba->pci_addr + PCICFG_UE_STATUS_LO_OFFSET)); + ue_h = ddi_get32(hba->pci_acc_handle, + (uint32_t *)(hba->pci_addr + PCICFG_UE_STATUS_HI_OFFSET)); + + if ((~hba->sli.sli4.ue_mask_lo & ue_l) || + (~hba->sli.sli4.ue_mask_hi & ue_h)) { /* Unrecoverable error detected */ /* Shut the HBA down */ EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_hardware_error_msg, - "Host Error: ueLow:%08x ueHigh:%08x on1:%08x on2:%08x", - ue_l, ue_h, on1, on2); + "Host Error: ueLow:%08x ueHigh:%08x maskLow:%08x " + "maskHigh:%08x", + ue_l, ue_h, hba->sli.sli4.ue_mask_lo, + hba->sli.sli4.ue_mask_hi); EMLXS_STATE_CHANGE(hba, FC_ERROR); @@ -6924,21 +6929,6 @@ emlxs_thread_spawn(hba, emlxs_shutdown_thread, NULL, NULL); } -#ifdef FMA_SUPPORT - /* The PCI(e) driver generates PCI error when PCI read returns */ - /* 0xFFFFFFFF value. Since PCICFG_UE_STATUS_ONLINE0 and */ - /* PCICFG_UE_STATUS_ONLINE1 registers return 0xFFFFFFFF to */ - /* indicate that no internal component has an unrecoverable */ - /* error on HBA, no access handle check and just call below */ - /* function to clear the access handle error here. */ - - /* Some S10 versions do not define the ddi_fm_acc_err_clear function */ - if ((void *)&ddi_fm_acc_err_clear != NULL) { - (void) ddi_fm_acc_err_clear(hba->pci_acc_handle, - DDI_FME_VERSION); - } -#endif /* FMA_SUPPORT */ - } /* emlxs_sli4_poll_erratt() */ int
--- a/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_solaris.c Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/io/fibre-channel/fca/emlxs/emlxs_solaris.c Thu Dec 03 10:09:44 2009 -0800 @@ -1412,6 +1412,44 @@ } /* emlxs_port_init() */ +void +emlxs_disable_pcie_ce_err(emlxs_hba_t *hba) +{ +#define NXT_PTR_OFF PCI_BYTE +#define PCIE_DEVCTL_OFF 0x8 +#define PCIE_CAP_ID 0x10 + + uint8_t cap_ptr; + uint8_t cap_id; + uint16_t tmp16; + + cap_ptr = ddi_get8(hba->pci_acc_handle, + (uint8_t *)(hba->pci_addr + PCI_CAP_POINTER)); + + while (cap_ptr) { + cap_id = ddi_get8(hba->pci_acc_handle, + (uint8_t *)(hba->pci_addr + cap_ptr)); + + if (cap_id == PCIE_CAP_ID) { + break; + } + cap_ptr = ddi_get8(hba->pci_acc_handle, + (uint8_t *)(hba->pci_addr + cap_ptr + NXT_PTR_OFF)); + } + + /* PCI Express Capability Register Set */ + /* Turn off the Correctable Error Reporting */ + /* (the Device Control Register, bit 0). */ + + if (cap_id == PCIE_CAP_ID) { + tmp16 = ddi_get16(hba->pci_acc_handle, + (uint16_t *)(hba->pci_addr + cap_ptr + PCIE_DEVCTL_OFF)); + tmp16 &= ~1; + (void) ddi_put16(hba->pci_acc_handle, + (uint16_t *)(hba->pci_addr + cap_ptr + PCIE_DEVCTL_OFF), + tmp16); + } +} /* * emlxs_bind_port @@ -1632,6 +1670,12 @@ } + /* PCIE Correctable Error Reporting workaround */ + if ((hba->model_info.chip == EMLXS_BE_CHIP) && + (bind_info->port_num == 0)) { + emlxs_disable_pcie_ce_err(hba); + } + /* Save initial state */ port->ulp_statec = port_info->pi_port_state;
--- a/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_config.h Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_config.h Thu Dec 03 10:09:44 2009 -0800 @@ -363,7 +363,7 @@ #ifdef FMA_SUPPORT /* CFG_FM_CAPS */ {"fm-capable", - 0, 0xF, 0xF, 0, + 0, 0xF, 0xB, 0, PARM_HEX | PARM_HIDDEN, "Sets FMA capabilities. [bit 3:errcb, 2:dmachk, 1:accchk, 0:ereport]"}, #endif /* FMA_SUPPORT */
--- a/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_dfclib.h Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_dfclib.h Thu Dec 03 10:09:44 2009 -0800 @@ -196,6 +196,7 @@ #define MBX_READ_LA64 0x95 #define MBX_FLASH_WR_ULA 0x98 #define MBX_SET_DEBUG 0x99 +#define MBX_SLI_CONFIG 0x9B #define MBX_LOAD_EXP_ROM 0x9C #define MBX_REQUEST_FEATURES 0x9D #define MBX_RESUME_RPI 0x9E @@ -379,6 +380,131 @@ } update_cfg_var_t; + +typedef struct +{ + union { + struct { +#ifdef EMLXS_BIG_ENDIAN + uint8_t domain; + uint8_t port_number; + uint8_t subsystem; + uint8_t opcode; +#else + uint8_t opcode; + uint8_t subsystem; + uint8_t port_number; + uint8_t domain; +#endif + uint32_t timeout; + uint32_t request_length; + uint32_t rsvd0; + }req; + + struct { +#ifdef EMLXS_BIG_ENDIAN + /* dw 0 */ + uint8_t domain; + uint8_t rsvd0; + uint8_t subsystem; + uint8_t opcode; + + /* dw 1 */ + uint16_t rsvd1; + uint8_t additional_status; + uint8_t status; +#else + /* dw 0 */ + uint8_t opcode; + uint8_t subsystem; + uint8_t rsvd0; + uint8_t domain; + + /* dw 1 */ + uint8_t status; + uint8_t additional_status; + uint16_t rsvd1; +#endif + + uint32_t rsp_length; + uint32_t actual_rsp_length; + }rsp; + uint32_t dw[4]; + }u0; +} common_hdr_t; + +typedef struct get_oem_attrs +{ + common_hdr_t hdr; + union { + struct { + uint32_t rsvd0; + }req; + + struct { + uint8_t emulex_serial_number[12]; + uint8_t oem_serial_number[24]; + uint32_t oem_personality_mgmt_word; +#ifdef EMLXS_BIG_ENDIAN + uint8_t rsvd[3]; + uint8_t oem_current_personality; +#else + uint8_t oem_current_personality; + uint8_t rsvd[3]; +#endif + + }rsp; + }params; + +} get_oem_attrs_t; + + +typedef struct read_write_flashrom { + common_hdr_t hdr; + uint32_t flash_op_code; + uint32_t flash_op_type; + uint32_t data_buffer_size; + uint32_t data_offset; + uint8_t data_buffer[4]; +} read_write_flashrom_t; + + +typedef struct +{ +#ifdef EMLXS_BIG_ENDIAN + uint32_t special:8; /* word 1 */ + uint32_t reserved2:16; /* word 1 */ + uint32_t sge_cnt:5; /* word 1 */ + uint32_t reserved1:2; /* word 1 */ + uint32_t embedded:1; /* word 1 */ +#endif +#ifdef EMLXS_LITTLE_ENDIAN + uint32_t embedded:1; /* word 1 */ + uint32_t reserved1:2; /* word 1 */ + uint32_t sge_cnt:5; /* word 1 */ + uint32_t reserved2:16; /* word 1 */ + uint32_t special:8; /* word 1 */ +#endif + uint32_t payload_length; /* word 2 */ + uint32_t tag_low; /* word 3 */ + uint32_t tag_hi; /* word 4 */ + uint32_t reserved3; /* word 5 */ + +} be_req_header_t; + +typedef struct +{ + be_req_header_t be; + + union + { + get_oem_attrs_t varOemAttrs; + read_write_flashrom_t varFlashRom; + } un; + +} sli_config_var_t; + + typedef struct read_cfg_var { #ifdef EMLXS_BIG_ENDIAN @@ -573,10 +699,13 @@ uint32_t varWords[63]; dump4_var_t varDmp; update_cfg_var_t varUpdateCfg; + sli_config_var_t varSLIConfig; } un; } dfc_mailbox4_t; + + /* Config Region 23 Records */ typedef struct tlv_fcoe {
--- a/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_extern.h Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_extern.h Thu Dec 03 10:09:44 2009 -0800 @@ -682,7 +682,10 @@ CHANNEL *cp); extern void emlxs_abort_ct_exchange(emlxs_hba_t *hba, emlxs_port_t *port, uint32_t rxid); - +extern void emlxs_abort_els_exchange(emlxs_hba_t *hba, + emlxs_port_t *port, uint32_t rxid); +extern void emlxs_abort_fct_exchange(emlxs_hba_t *hba, + emlxs_port_t *port, uint32_t rxid); extern emlxs_buf_t *emlxs_chipq_get(CHANNEL *cp, uint16_t iotag); extern void emlxs_chipq_put(CHANNEL *cp, emlxs_buf_t *sbp); extern uint32_t emlxs_chipq_node_flush(emlxs_port_t *port,
--- a/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_fc.h Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_fc.h Thu Dec 03 10:09:44 2009 -0800 @@ -1658,6 +1658,8 @@ RXQ_DESC_t rxq[EMLXS_MAX_RXQS]; + uint32_t ue_mask_lo; + uint32_t ue_mask_hi; } emlxs_sli4_t;
--- a/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_fcio.h Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_fcio.h Thu Dec 03 10:09:44 2009 -0800 @@ -91,7 +91,9 @@ /* offline */ #define EMLXS_NO_BOOT_CODE (EMLXS_ERRNO_START + 5) /* No boot */ /* code image */ -#define EMLXS_ERRNO_END (EMLXS_ERRNO_START + 5) +#define EMLXS_OP_NOT_SUP (EMLXS_ERRNO_START + 6) /* Operation */ + /* not supp */ +#define EMLXS_ERRNO_END (EMLXS_ERRNO_START + 6) typedef struct emlxs_parm
--- a/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_hw.h Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_hw.h Thu Dec 03 10:09:44 2009 -0800 @@ -690,6 +690,8 @@ /* PCI Config Register offsets */ #define PCICFG_UE_STATUS_LO_OFFSET 0xA0 /* Error Indication - low */ #define PCICFG_UE_STATUS_HI_OFFSET 0xA4 /* Error Indication - high */ +#define PCICFG_UE_MASK_LO_OFFSET 0xA8 /* Error mask - low */ +#define PCICFG_UE_MASK_HI_OFFSET 0xAC /* Error mask - high */ #define PCICFG_UE_STATUS_ONLINE1 0xB0 /* Error status1 */ #define PCICFG_UE_STATUS_ONLINE2 0xB4 /* Error status2 */
--- a/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_version.h Thu Dec 03 12:01:36 2009 -0500 +++ b/usr/src/uts/common/sys/fibre-channel/fca/emlxs/emlxs_version.h Thu Dec 03 10:09:44 2009 -0800 @@ -31,10 +31,10 @@ extern "C" { #endif -#define EMLXS_VERSION "2.50i" +#define EMLXS_VERSION "2.50k" #define EMLXS_DATE_MINUTE "30" /* 00-59 */ -#define EMLXS_DATE_HOUR "12" /* 00-23 */ -#define EMLXS_DATE_DAY "10" /* 00-31 */ +#define EMLXS_DATE_HOUR "11" /* 00-23 */ +#define EMLXS_DATE_DAY "25" /* 00-31 */ #define EMLXS_DATE_MONTH "11" /* 01-12 */ #define EMLXS_DATE_YEAR "2009" /* YYYY */