diff options
Diffstat (limited to 'drivers/scsi/qla2xxx')
-rw-r--r-- | drivers/scsi/qla2xxx/qla_attr.c | 3 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_bsg.c | 72 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_dbg.c | 8 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_def.h | 4 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_fw.h | 21 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_gbl.h | 3 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_gs.c | 6 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_init.c | 153 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_iocb.c | 15 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_isr.c | 38 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_mbx.c | 6 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_mid.c | 3 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_nx.c | 79 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_os.c | 59 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_target.c | 48 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_target.h | 1 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/qla_version.h | 2 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/tcm_qla2xxx.c | 81 | ||||
-rw-r--r-- | drivers/scsi/qla2xxx/tcm_qla2xxx.h | 2 |
19 files changed, 359 insertions, 245 deletions
diff --git a/drivers/scsi/qla2xxx/qla_attr.c b/drivers/scsi/qla2xxx/qla_attr.c index 1c28215f8be..83d798428c1 100644 --- a/drivers/scsi/qla2xxx/qla_attr.c +++ b/drivers/scsi/qla2xxx/qla_attr.c @@ -1615,8 +1615,7 @@ qla2x00_terminate_rport_io(struct fc_rport *rport) * At this point all fcport's software-states are cleared. Perform any * final cleanup of firmware resources (PCBs and XCBs). */ - if (fcport->loop_id != FC_NO_LOOP_ID && - !test_bit(UNLOADING, &fcport->vha->dpc_flags)) { + if (fcport->loop_id != FC_NO_LOOP_ID) { if (IS_FWI2_CAPABLE(fcport->vha->hw)) fcport->vha->hw->isp_ops->fabric_logout(fcport->vha, fcport->loop_id, fcport->d_id.b.domain, diff --git a/drivers/scsi/qla2xxx/qla_bsg.c b/drivers/scsi/qla2xxx/qla_bsg.c index 2f9bddd3c61..9f34dedcdad 100644 --- a/drivers/scsi/qla2xxx/qla_bsg.c +++ b/drivers/scsi/qla2xxx/qla_bsg.c @@ -219,7 +219,8 @@ qla24xx_proc_fcp_prio_cfg_cmd(struct fc_bsg_job *bsg_job) break; } exit_fcp_prio_cfg: - bsg_job->job_done(bsg_job); + if (!ret) + bsg_job->job_done(bsg_job); return ret; } @@ -741,9 +742,8 @@ qla2x00_process_loopback(struct fc_bsg_job *bsg_job) if (qla81xx_get_port_config(vha, config)) { ql_log(ql_log_warn, vha, 0x701f, "Get port config failed.\n"); - bsg_job->reply->result = (DID_ERROR << 16); rval = -EPERM; - goto done_free_dma_req; + goto done_free_dma_rsp; } ql_dbg(ql_dbg_user, vha, 0x70c0, @@ -761,9 +761,8 @@ qla2x00_process_loopback(struct fc_bsg_job *bsg_job) new_config, elreq.options); if (rval) { - bsg_job->reply->result = (DID_ERROR << 16); rval = -EPERM; - goto done_free_dma_req; + goto done_free_dma_rsp; } type = "FC_BSG_HST_VENDOR_LOOPBACK"; @@ -795,9 +794,8 @@ qla2x00_process_loopback(struct fc_bsg_job *bsg_job) "MPI reset failed.\n"); } - bsg_job->reply->result = (DID_ERROR << 16); rval = -EIO; - goto done_free_dma_req; + goto done_free_dma_rsp; } } else { type = "FC_BSG_HST_VENDOR_LOOPBACK"; @@ -812,34 +810,27 @@ qla2x00_process_loopback(struct fc_bsg_job *bsg_job) ql_log(ql_log_warn, vha, 0x702c, "Vendor request %s failed.\n", type); - fw_sts_ptr = ((uint8_t *)bsg_job->req->sense) + - sizeof(struct fc_bsg_reply); - - memcpy(fw_sts_ptr, response, sizeof(response)); - fw_sts_ptr += sizeof(response); - *fw_sts_ptr = command_sent; rval = 0; bsg_job->reply->result = (DID_ERROR << 16); + bsg_job->reply->reply_payload_rcv_len = 0; } else { ql_dbg(ql_dbg_user, vha, 0x702d, "Vendor request %s completed.\n", type); - - bsg_job->reply_len = sizeof(struct fc_bsg_reply) + - sizeof(response) + sizeof(uint8_t); - bsg_job->reply->reply_payload_rcv_len = - bsg_job->reply_payload.payload_len; - fw_sts_ptr = ((uint8_t *)bsg_job->req->sense) + - sizeof(struct fc_bsg_reply); - memcpy(fw_sts_ptr, response, sizeof(response)); - fw_sts_ptr += sizeof(response); - *fw_sts_ptr = command_sent; - bsg_job->reply->result = DID_OK; + bsg_job->reply->result = (DID_OK << 16); sg_copy_from_buffer(bsg_job->reply_payload.sg_list, bsg_job->reply_payload.sg_cnt, rsp_data, rsp_data_len); } - bsg_job->job_done(bsg_job); + bsg_job->reply_len = sizeof(struct fc_bsg_reply) + + sizeof(response) + sizeof(uint8_t); + fw_sts_ptr = ((uint8_t *)bsg_job->req->sense) + + sizeof(struct fc_bsg_reply); + memcpy(fw_sts_ptr, response, sizeof(response)); + fw_sts_ptr += sizeof(response); + *fw_sts_ptr = command_sent; + +done_free_dma_rsp: dma_free_coherent(&ha->pdev->dev, rsp_data_len, rsp_data, rsp_data_dma); done_free_dma_req: @@ -853,6 +844,8 @@ done_unmap_req_sg: dma_unmap_sg(&ha->pdev->dev, bsg_job->request_payload.sg_list, bsg_job->request_payload.sg_cnt, DMA_TO_DEVICE); + if (!rval) + bsg_job->job_done(bsg_job); return rval; } @@ -877,16 +870,15 @@ qla84xx_reset(struct fc_bsg_job *bsg_job) if (rval) { ql_log(ql_log_warn, vha, 0x7030, "Vendor request 84xx reset failed.\n"); - rval = 0; - bsg_job->reply->result = (DID_ERROR << 16); + rval = (DID_ERROR << 16); } else { ql_dbg(ql_dbg_user, vha, 0x7031, "Vendor request 84xx reset completed.\n"); bsg_job->reply->result = DID_OK; + bsg_job->job_done(bsg_job); } - bsg_job->job_done(bsg_job); return rval; } @@ -976,8 +968,7 @@ qla84xx_updatefw(struct fc_bsg_job *bsg_job) ql_log(ql_log_warn, vha, 0x7037, "Vendor request 84xx updatefw failed.\n"); - rval = 0; - bsg_job->reply->result = (DID_ERROR << 16); + rval = (DID_ERROR << 16); } else { ql_dbg(ql_dbg_user, vha, 0x7038, "Vendor request 84xx updatefw completed.\n"); @@ -986,7 +977,6 @@ qla84xx_updatefw(struct fc_bsg_job *bsg_job) bsg_job->reply->result = DID_OK; } - bsg_job->job_done(bsg_job); dma_pool_free(ha->s_dma_pool, mn, mn_dma); done_free_fw_buf: @@ -996,6 +986,8 @@ done_unmap_sg: dma_unmap_sg(&ha->pdev->dev, bsg_job->request_payload.sg_list, bsg_job->request_payload.sg_cnt, DMA_TO_DEVICE); + if (!rval) + bsg_job->job_done(bsg_job); return rval; } @@ -1163,8 +1155,7 @@ qla84xx_mgmt_cmd(struct fc_bsg_job *bsg_job) ql_log(ql_log_warn, vha, 0x7043, "Vendor request 84xx mgmt failed.\n"); - rval = 0; - bsg_job->reply->result = (DID_ERROR << 16); + rval = (DID_ERROR << 16); } else { ql_dbg(ql_dbg_user, vha, 0x7044, @@ -1184,8 +1175,6 @@ qla84xx_mgmt_cmd(struct fc_bsg_job *bsg_job) } } - bsg_job->job_done(bsg_job); - done_unmap_sg: if (mgmt_b) dma_free_coherent(&ha->pdev->dev, data_len, mgmt_b, mgmt_dma); @@ -1200,6 +1189,8 @@ done_unmap_sg: exit_mgmt: dma_pool_free(ha->s_dma_pool, mn, mn_dma); + if (!rval) + bsg_job->job_done(bsg_job); return rval; } @@ -1276,9 +1267,7 @@ qla24xx_iidma(struct fc_bsg_job *bsg_job) fcport->port_name[3], fcport->port_name[4], fcport->port_name[5], fcport->port_name[6], fcport->port_name[7], rval, fcport->fp_speed, mb[0], mb[1]); - rval = 0; - bsg_job->reply->result = (DID_ERROR << 16); - + rval = (DID_ERROR << 16); } else { if (!port_param->mode) { bsg_job->reply_len = sizeof(struct fc_bsg_reply) + @@ -1292,9 +1281,9 @@ qla24xx_iidma(struct fc_bsg_job *bsg_job) } bsg_job->reply->result = DID_OK; + bsg_job->job_done(bsg_job); } - bsg_job->job_done(bsg_job); return rval; } @@ -1887,8 +1876,6 @@ qla2x00_process_vendor_specific(struct fc_bsg_job *bsg_job) return qla24xx_process_bidir_cmd(bsg_job); default: - bsg_job->reply->result = (DID_ERROR << 16); - bsg_job->job_done(bsg_job); return -ENOSYS; } } @@ -1919,8 +1906,6 @@ qla24xx_bsg_request(struct fc_bsg_job *bsg_job) ql_dbg(ql_dbg_user, vha, 0x709f, "BSG: ISP abort active/needed -- cmd=%d.\n", bsg_job->request->msgcode); - bsg_job->reply->result = (DID_ERROR << 16); - bsg_job->job_done(bsg_job); return -EBUSY; } @@ -1943,7 +1928,6 @@ qla24xx_bsg_request(struct fc_bsg_job *bsg_job) case FC_BSG_RPT_CT: default: ql_log(ql_log_warn, vha, 0x705a, "Unsupported BSG request.\n"); - bsg_job->reply->result = ret; break; } return ret; diff --git a/drivers/scsi/qla2xxx/qla_dbg.c b/drivers/scsi/qla2xxx/qla_dbg.c index 44efe3cc79e..53f9e492f9d 100644 --- a/drivers/scsi/qla2xxx/qla_dbg.c +++ b/drivers/scsi/qla2xxx/qla_dbg.c @@ -11,7 +11,7 @@ * ---------------------------------------------------------------------- * | Level | Last Value Used | Holes | * ---------------------------------------------------------------------- - * | Module Init and Probe | 0x0124 | 0x4b,0xba,0xfa | + * | Module Init and Probe | 0x0125 | 0x4b,0xba,0xfa | * | Mailbox commands | 0x114f | 0x111a-0x111b | * | | | 0x112c-0x112e | * | | | 0x113a | @@ -526,8 +526,8 @@ qla25xx_copy_mq(struct qla_hw_data *ha, void *ptr, uint32_t **last_chain) ha->max_req_queues : ha->max_rsp_queues; mq->count = htonl(que_cnt); for (cnt = 0; cnt < que_cnt; cnt++) { - reg = (struct device_reg_25xxmq *) ((void *) - ha->mqiobase + cnt * QLA_QUE_PAGE); + reg = (struct device_reg_25xxmq __iomem *) + (ha->mqiobase + cnt * QLA_QUE_PAGE); que_idx = cnt * 4; mq->qregs[que_idx] = htonl(RD_REG_DWORD(®->req_q_in)); mq->qregs[que_idx+1] = htonl(RD_REG_DWORD(®->req_q_out)); @@ -2268,7 +2268,7 @@ qla83xx_fw_dump(scsi_qla_host_t *vha, int hardware_locked) if (!cnt) { nxt = fw->code_ram; - nxt += sizeof(fw->code_ram), + nxt += sizeof(fw->code_ram); nxt += (ha->fw_memory_size - 0x100000 + 1); goto copy_queue; } else diff --git a/drivers/scsi/qla2xxx/qla_def.h b/drivers/scsi/qla2xxx/qla_def.h index a9725bf5527..6e7727f46d4 100644 --- a/drivers/scsi/qla2xxx/qla_def.h +++ b/drivers/scsi/qla2xxx/qla_def.h @@ -2486,9 +2486,9 @@ struct bidi_statistics { #define QLA_MAX_QUEUES 256 #define ISP_QUE_REG(ha, id) \ ((ha->mqenable || IS_QLA83XX(ha)) ? \ - ((void *)(ha->mqiobase) +\ + ((device_reg_t __iomem *)(ha->mqiobase) +\ (QLA_QUE_PAGE * id)) :\ - ((void *)(ha->iobase))) + ((device_reg_t __iomem *)(ha->iobase))) #define QLA_REQ_QUE_ID(tag) \ ((tag < QLA_MAX_QUEUES && tag > 0) ? tag : 0) #define QLA_DEFAULT_QUE_QOS 5 diff --git a/drivers/scsi/qla2xxx/qla_fw.h b/drivers/scsi/qla2xxx/qla_fw.h index 59524aa0ab3..be6d61a89ed 100644 --- a/drivers/scsi/qla2xxx/qla_fw.h +++ b/drivers/scsi/qla2xxx/qla_fw.h @@ -1092,6 +1092,27 @@ struct device_reg_24xx { uint32_t unused_6[2]; /* Gap. */ uint32_t iobase_sdata; }; +/* RISC-RISC semaphore register PCI offet */ +#define RISC_REGISTER_BASE_OFFSET 0x7010 +#define RISC_REGISTER_WINDOW_OFFET 0x6 + +/* RISC-RISC semaphore/flag register (risc address 0x7016) */ + +#define RISC_SEMAPHORE 0x1UL +#define RISC_SEMAPHORE_WE (RISC_SEMAPHORE << 16) +#define RISC_SEMAPHORE_CLR (RISC_SEMAPHORE_WE | 0x0UL) +#define RISC_SEMAPHORE_SET (RISC_SEMAPHORE_WE | RISC_SEMAPHORE) + +#define RISC_SEMAPHORE_FORCE 0x8000UL +#define RISC_SEMAPHORE_FORCE_WE (RISC_SEMAPHORE_FORCE << 16) +#define RISC_SEMAPHORE_FORCE_CLR (RISC_SEMAPHORE_FORCE_WE | 0x0UL) +#define RISC_SEMAPHORE_FORCE_SET \ + (RISC_SEMAPHORE_FORCE_WE | RISC_SEMAPHORE_FORCE) + +/* RISC semaphore timeouts (ms) */ +#define TIMEOUT_SEMAPHORE 2500 +#define TIMEOUT_SEMAPHORE_FORCE 2000 +#define TIMEOUT_TOTAL_ELAPSED 4500 /* Trace Control *************************************************************/ diff --git a/drivers/scsi/qla2xxx/qla_gbl.h b/drivers/scsi/qla2xxx/qla_gbl.h index 6acb39785a4..2411d1a12b2 100644 --- a/drivers/scsi/qla2xxx/qla_gbl.h +++ b/drivers/scsi/qla2xxx/qla_gbl.h @@ -416,7 +416,7 @@ extern int qla2x00_request_irqs(struct qla_hw_data *, struct rsp_que *); extern void qla2x00_free_irqs(scsi_qla_host_t *); extern int qla2x00_get_data_rate(scsi_qla_host_t *); -extern char *qla2x00_get_link_speed_str(struct qla_hw_data *); +extern const char *qla2x00_get_link_speed_str(struct qla_hw_data *, uint16_t); /* * Global Function Prototypes in qla_sup.c source file. @@ -598,7 +598,6 @@ extern void qla82xx_init_flags(struct qla_hw_data *); /* ISP 8021 hardware related */ extern void qla82xx_set_drv_active(scsi_qla_host_t *); -extern void qla82xx_crb_win_unlock(struct qla_hw_data *); extern int qla82xx_wr_32(struct qla_hw_data *, ulong, u32); extern int qla82xx_rd_32(struct qla_hw_data *, ulong); extern int qla82xx_rdmem(struct qla_hw_data *, u64, void *, int); diff --git a/drivers/scsi/qla2xxx/qla_gs.c b/drivers/scsi/qla2xxx/qla_gs.c index f4e4bd7c3f4..01efc0e9cc3 100644 --- a/drivers/scsi/qla2xxx/qla_gs.c +++ b/drivers/scsi/qla2xxx/qla_gs.c @@ -218,6 +218,9 @@ qla2x00_ga_nxt(scsi_qla_host_t *vha, fc_port_t *fcport) memcpy(fcport->port_name, ct_rsp->rsp.ga_nxt.port_name, WWN_SIZE); + fcport->fc4_type = (ct_rsp->rsp.ga_nxt.fc4_types[2] & BIT_0) ? + FC4_TYPE_FCP_SCSI : FC4_TYPE_OTHER; + if (ct_rsp->rsp.ga_nxt.port_type != NS_N_PORT_TYPE && ct_rsp->rsp.ga_nxt.port_type != NS_NL_PORT_TYPE) fcport->d_id.b.domain = 0xf0; @@ -1930,6 +1933,9 @@ qla2x00_gpsc(scsi_qla_host_t *vha, sw_info_t *list) case BIT_11: list[i].fp_speed = PORT_SPEED_8GB; break; + case BIT_10: + list[i].fp_speed = PORT_SPEED_16GB; + break; } ql_dbg(ql_dbg_disc, vha, 0x205b, diff --git a/drivers/scsi/qla2xxx/qla_init.c b/drivers/scsi/qla2xxx/qla_init.c index 48fca47384b..563eee3fa92 100644 --- a/drivers/scsi/qla2xxx/qla_init.c +++ b/drivers/scsi/qla2xxx/qla_init.c @@ -429,7 +429,7 @@ qla2x00_async_adisc_done(struct scsi_qla_host *vha, fc_port_t *fcport, /* QLogic ISP2x00 Hardware Support Functions. */ /****************************************************************************/ -int +static int qla83xx_nic_core_fw_load(scsi_qla_host_t *vha) { int rval = QLA_SUCCESS; @@ -997,7 +997,7 @@ qla2x00_reset_chip(scsi_qla_host_t *vha) * * Returns 0 on success. */ -int +static int qla81xx_reset_mpi(scsi_qla_host_t *vha) { uint16_t mb[4] = {0x1010, 0, 1, 0}; @@ -1095,6 +1095,83 @@ qla24xx_reset_risc(scsi_qla_host_t *vha) ha->isp_ops->enable_intrs(ha); } +static void +qla25xx_read_risc_sema_reg(scsi_qla_host_t *vha, uint32_t *data) +{ + struct device_reg_24xx __iomem *reg = &vha->hw->iobase->isp24; + + WRT_REG_DWORD(®->iobase_addr, RISC_REGISTER_BASE_OFFSET); + *data = RD_REG_DWORD(®->iobase_window + RISC_REGISTER_WINDOW_OFFET); + +} + +static void +qla25xx_write_risc_sema_reg(scsi_qla_host_t *vha, uint32_t data) +{ + struct device_reg_24xx __iomem *reg = &vha->hw->iobase->isp24; + + WRT_REG_DWORD(®->iobase_addr, RISC_REGISTER_BASE_OFFSET); + WRT_REG_DWORD(®->iobase_window + RISC_REGISTER_WINDOW_OFFET, data); +} + +static void +qla25xx_manipulate_risc_semaphore(scsi_qla_host_t *vha) +{ + struct qla_hw_data *ha = vha->hw; + uint32_t wd32 = 0; + uint delta_msec = 100; + uint elapsed_msec = 0; + uint timeout_msec; + ulong n; + + if (!IS_QLA25XX(ha) && !IS_QLA2031(ha)) + return; + +attempt: + timeout_msec = TIMEOUT_SEMAPHORE; + n = timeout_msec / delta_msec; + while (n--) { + qla25xx_write_risc_sema_reg(vha, RISC_SEMAPHORE_SET); + qla25xx_read_risc_sema_reg(vha, &wd32); + if (wd32 & RISC_SEMAPHORE) + break; + msleep(delta_msec); + elapsed_msec += delta_msec; + if (elapsed_msec > TIMEOUT_TOTAL_ELAPSED) + goto force; + } + + if (!(wd32 & RISC_SEMAPHORE)) + goto force; + + if (!(wd32 & RISC_SEMAPHORE_FORCE)) + goto acquired; + + qla25xx_write_risc_sema_reg(vha, RISC_SEMAPHORE_CLR); + timeout_msec = TIMEOUT_SEMAPHORE_FORCE; + n = timeout_msec / delta_msec; + while (n--) { + qla25xx_read_risc_sema_reg(vha, &wd32); + if (!(wd32 & RISC_SEMAPHORE_FORCE)) + break; + msleep(delta_msec); + elapsed_msec += delta_msec; + if (elapsed_msec > TIMEOUT_TOTAL_ELAPSED) + goto force; + } + + if (wd32 & RISC_SEMAPHORE_FORCE) + qla25xx_write_risc_sema_reg(vha, RISC_SEMAPHORE_FORCE_CLR); + + goto attempt; + +force: + qla25xx_write_risc_sema_reg(vha, RISC_SEMAPHORE_FORCE_SET); + +acquired: + return; +} + /** * qla24xx_reset_chip() - Reset ISP24xx chip. * @ha: HA context @@ -1113,6 +1190,8 @@ qla24xx_reset_chip(scsi_qla_host_t *vha) ha->isp_ops->disable_intrs(ha); + qla25xx_manipulate_risc_semaphore(vha); + /* Perform RISC reset. */ qla24xx_reset_risc(vha); } @@ -1888,10 +1967,6 @@ qla2x00_init_rings(scsi_qla_host_t *vha) qla2x00_init_response_q_entries(rsp); } - spin_lock(&ha->vport_slock); - - spin_unlock(&ha->vport_slock); - ha->tgt.atio_ring_ptr = ha->tgt.atio_ring; ha->tgt.atio_ring_index = 0; /* Initialize ATIO queue entries */ @@ -1971,6 +2046,7 @@ qla2x00_fw_ready(scsi_qla_host_t *vha) "Waiting for LIP to complete.\n"); do { + memset(state, -1, sizeof(state)); rval = qla2x00_get_firmware_state(vha, state); if (rval == QLA_SUCCESS) { if (state[0] < FSTATE_LOSS_OF_SYNC) { @@ -2907,7 +2983,6 @@ cleanup_allocation: static void qla2x00_iidma_fcport(scsi_qla_host_t *vha, fc_port_t *fcport) { - char *link_speed; int rval; uint16_t mb[4]; struct qla_hw_data *ha = vha->hw; @@ -2934,10 +3009,10 @@ qla2x00_iidma_fcport(scsi_qla_host_t *vha, fc_port_t *fcport) fcport->port_name[6], fcport->port_name[7], rval, fcport->fp_speed, mb[0], mb[1]); } else { - link_speed = qla2x00_get_link_speed_str(ha); ql_dbg(ql_dbg_disc, vha, 0x2005, "iIDMA adjusted to %s GB/s " - "on %02x%02x%02x%02x%02x%02x%02x%02x.\n", link_speed, + "on %02x%02x%02x%02x%02x%02x%02x%02x.\n", + qla2x00_get_link_speed_str(ha, fcport->fp_speed), fcport->port_name[0], fcport->port_name[1], fcport->port_name[2], fcport->port_name[3], fcport->port_name[4], fcport->port_name[5], @@ -3007,10 +3082,10 @@ qla2x00_update_fcport(scsi_qla_host_t *vha, fc_port_t *fcport) fcport->login_retry = 0; fcport->flags &= ~(FCF_LOGIN_NEEDED | FCF_ASYNC_SENT); + qla2x00_set_fcport_state(fcport, FCS_ONLINE); qla2x00_iidma_fcport(vha, fcport); qla24xx_update_fcport_fcp_prio(vha, fcport); qla2x00_reg_remote_port(vha, fcport); - qla2x00_set_fcport_state(fcport, FCS_ONLINE); } /* @@ -3868,7 +3943,7 @@ qla83xx_reset_ownership(scsi_qla_host_t *vha) } } -int +static int __qla83xx_set_drv_ack(scsi_qla_host_t *vha) { int rval = QLA_SUCCESS; @@ -3884,19 +3959,7 @@ __qla83xx_set_drv_ack(scsi_qla_host_t *vha) return rval; } -int -qla83xx_set_drv_ack(scsi_qla_host_t *vha) -{ - int rval = QLA_SUCCESS; - - qla83xx_idc_lock(vha, 0); - rval = __qla83xx_set_drv_ack(vha); - qla83xx_idc_unlock(vha, 0); - - return rval; -} - -int +static int __qla83xx_clear_drv_ack(scsi_qla_host_t *vha) { int rval = QLA_SUCCESS; @@ -3912,19 +3975,7 @@ __qla83xx_clear_drv_ack(scsi_qla_host_t *vha) return rval; } -int -qla83xx_clear_drv_ack(scsi_qla_host_t *vha) -{ - int rval = QLA_SUCCESS; - - qla83xx_idc_lock(vha, 0); - rval = __qla83xx_clear_drv_ack(vha); - qla83xx_idc_unlock(vha, 0); - - return rval; -} - -const char * +static const char * qla83xx_dev_state_to_string(uint32_t dev_state) { switch (dev_state) { @@ -3978,7 +4029,7 @@ qla83xx_idc_audit(scsi_qla_host_t *vha, int audit_type) } /* Assumes idc_lock always held on entry */ -int +static int qla83xx_initiating_reset(scsi_qla_host_t *vha) { struct qla_hw_data *ha = vha->hw; @@ -4026,36 +4077,12 @@ __qla83xx_set_idc_control(scsi_qla_host_t *vha, uint32_t idc_control) } int -qla83xx_set_idc_control(scsi_qla_host_t *vha, uint32_t idc_control) -{ - int rval = QLA_SUCCESS; - - qla83xx_idc_lock(vha, 0); - rval = __qla83xx_set_idc_control(vha, idc_control); - qla83xx_idc_unlock(vha, 0); - - return rval; -} - -int __qla83xx_get_idc_control(scsi_qla_host_t *vha, uint32_t *idc_control) { return qla83xx_rd_reg(vha, QLA83XX_IDC_CONTROL, idc_control); } -int -qla83xx_get_idc_control(scsi_qla_host_t *vha, uint32_t *idc_control) -{ - int rval = QLA_SUCCESS; - - qla83xx_idc_lock(vha, 0); - rval = __qla83xx_get_idc_control(vha, idc_control); - qla83xx_idc_unlock(vha, 0); - - return rval; -} - -int +static int qla83xx_check_driver_presence(scsi_qla_host_t *vha) { uint32_t drv_presence = 0; diff --git a/drivers/scsi/qla2xxx/qla_iocb.c b/drivers/scsi/qla2xxx/qla_iocb.c index 03b75263283..a481684479c 100644 --- a/drivers/scsi/qla2xxx/qla_iocb.c +++ b/drivers/scsi/qla2xxx/qla_iocb.c @@ -520,7 +520,7 @@ __qla2x00_marker(struct scsi_qla_host *vha, struct req_que *req, mrk24 = NULL; req = ha->req_q_map[0]; - mrk = (mrk_entry_t *)qla2x00_alloc_iocbs(vha, 0); + mrk = (mrk_entry_t *)qla2x00_alloc_iocbs(vha, NULL); if (mrk == NULL) { ql_log(ql_log_warn, base_vha, 0x3026, "Failed to allocate Marker IOCB.\n"); @@ -2551,7 +2551,7 @@ sufficient_dsds: (unsigned long __iomem *)ha->nxdb_wr_ptr, dbval); wmb(); - while (RD_REG_DWORD(ha->nxdb_rd_ptr) != dbval) { + while (RD_REG_DWORD((void __iomem *)ha->nxdb_rd_ptr) != dbval) { WRT_REG_DWORD( (unsigned long __iomem *)ha->nxdb_wr_ptr, dbval); @@ -2748,7 +2748,6 @@ qla2x00_start_bidir(srb_t *sp, struct scsi_qla_host *vha, uint32_t tot_dsds) struct rsp_que *rsp; struct req_que *req; int rval = EXT_STATUS_OK; - device_reg_t __iomem *reg = ISP_QUE_REG(ha, vha->req->id); rval = QLA_SUCCESS; @@ -2786,15 +2785,7 @@ qla2x00_start_bidir(srb_t *sp, struct scsi_qla_host *vha, uint32_t tot_dsds) /* Check for room on request queue. */ if (req->cnt < req_cnt + 2) { - if (ha->mqenable) - cnt = RD_REG_DWORD(®->isp25mq.req_q_out); - else if (IS_QLA82XX(ha)) - cnt = RD_REG_DWORD(®->isp82.req_q_out); - else if (IS_FWI2_CAPABLE(ha)) - cnt = RD_REG_DWORD(®->isp24.req_q_out); - else - cnt = qla2x00_debounce_register( - ISP_REQ_Q_OUT(ha, ®->isp)); + cnt = RD_REG_DWORD_RELAXED(req->req_q_out); if (req->ring_index < cnt) req->cnt = cnt - req->ring_index; diff --git a/drivers/scsi/qla2xxx/qla_isr.c b/drivers/scsi/qla2xxx/qla_isr.c index 9d1c7b56090..873c82014b1 100644 --- a/drivers/scsi/qla2xxx/qla_isr.c +++ b/drivers/scsi/qla2xxx/qla_isr.c @@ -316,28 +316,24 @@ qla81xx_idc_event(scsi_qla_host_t *vha, uint16_t aen, uint16_t descr) } #define LS_UNKNOWN 2 -char * -qla2x00_get_link_speed_str(struct qla_hw_data *ha) +const char * +qla2x00_get_link_speed_str(struct qla_hw_data *ha, uint16_t speed) { - static char *link_speeds[] = {"1", "2", "?", "4", "8", "16", "10"}; - char *link_speed; - int fw_speed = ha->link_data_rate; + static const char * const link_speeds[] = { + "1", "2", "?", "4", "8", "16", "10" + }; if (IS_QLA2100(ha) || IS_QLA2200(ha)) - link_speed = link_speeds[0]; - else if (fw_speed == 0x13) - link_speed = link_speeds[6]; - else { - link_speed = link_speeds[LS_UNKNOWN]; - if (fw_speed < 6) - link_speed = - link_speeds[fw_speed]; - } - - return link_speed; + return link_speeds[0]; + else if (speed == 0x13) + return link_speeds[6]; + else if (speed < 6) + return link_speeds[speed]; + else + return link_speeds[LS_UNKNOWN]; } -void +static void qla83xx_handle_8200_aen(scsi_qla_host_t *vha, uint16_t *mb) { struct qla_hw_data *ha = vha->hw; @@ -671,7 +667,7 @@ skip_rio: ql_dbg(ql_dbg_async, vha, 0x500a, "LOOP UP detected (%s Gbps).\n", - qla2x00_get_link_speed_str(ha)); + qla2x00_get_link_speed_str(ha, ha->link_data_rate)); vha->flags.management_server_logged_in = 0; qla2x00_post_aen_work(vha, FCH_EVT_LINKUP, ha->link_data_rate); @@ -860,7 +856,7 @@ skip_rio: mb[1], mb[2], mb[3]); ql_log(ql_log_warn, vha, 0x505f, "Link is operational (%s Gbps).\n", - qla2x00_get_link_speed_str(ha)); + qla2x00_get_link_speed_str(ha, ha->link_data_rate)); /* * Mark all devices as missing so we will login again. @@ -2944,7 +2940,9 @@ skip_msi: "Failed to reserve interrupt %d already in use.\n", ha->pdev->irq); goto fail; - } + } else if (!ha->flags.msi_enabled) + ql_dbg(ql_dbg_init, vha, 0x0125, + "INTa mode: Enabled.\n"); clear_risc_ints: diff --git a/drivers/scsi/qla2xxx/qla_mbx.c b/drivers/scsi/qla2xxx/qla_mbx.c index 18c509fae55..68c55eaa318 100644 --- a/drivers/scsi/qla2xxx/qla_mbx.c +++ b/drivers/scsi/qla2xxx/qla_mbx.c @@ -3122,7 +3122,7 @@ qla24xx_report_id_acquisition(scsi_qla_host_t *vha, if (vp_idx == 0 && (MSB(stat) != 1)) goto reg_needed; - if (MSB(stat) != 0) { + if (MSB(stat) != 0 && MSB(stat) != 2) { ql_dbg(ql_dbg_mbx, vha, 0x10ba, "Could not acquire ID for VP[%d].\n", vp_idx); return; @@ -3536,7 +3536,7 @@ qla25xx_init_req_que(struct scsi_qla_host *vha, struct req_que *req) if (IS_QLA83XX(ha)) mcp->mb[15] = 0; - reg = (struct device_reg_25xxmq *)((void *)(ha->mqiobase) + + reg = (struct device_reg_25xxmq __iomem *)((ha->mqiobase) + QLA_QUE_PAGE * req->id); mcp->mb[4] = req->id; @@ -3605,7 +3605,7 @@ qla25xx_init_rsp_que(struct scsi_qla_host *vha, struct rsp_que *rsp) if (IS_QLA83XX(ha)) mcp->mb[15] = 0; - reg = (struct device_reg_25xxmq *)((void *)(ha->mqiobase) + + reg = (struct device_reg_25xxmq __iomem *)((ha->mqiobase) + QLA_QUE_PAGE * rsp->id); mcp->mb[4] = rsp->id; diff --git a/drivers/scsi/qla2xxx/qla_mid.c b/drivers/scsi/qla2xxx/qla_mid.c index bd4708a422c..20fd974f903 100644 --- a/drivers/scsi/qla2xxx/qla_mid.c +++ b/drivers/scsi/qla2xxx/qla_mid.c @@ -149,6 +149,7 @@ qla2x00_mark_vp_devices_dead(scsi_qla_host_t *vha) int qla24xx_disable_vp(scsi_qla_host_t *vha) { + unsigned long flags; int ret; ret = qla24xx_control_vp(vha, VCE_COMMAND_DISABLE_VPS_LOGO_ALL); @@ -156,7 +157,9 @@ qla24xx_disable_vp(scsi_qla_host_t *vha) atomic_set(&vha->loop_down_timer, LOOP_DOWN_TIME); /* Remove port id from vp target map */ + spin_lock_irqsave(&vha->hw->vport_slock, flags); qlt_update_vp_map(vha, RESET_AL_PA); + spin_unlock_irqrestore(&vha->hw->vport_slock, flags); qla2x00_mark_vp_devices_dead(vha); atomic_set(&vha->vp_state, VP_FAILED); diff --git a/drivers/scsi/qla2xxx/qla_nx.c b/drivers/scsi/qla2xxx/qla_nx.c index f5e297c6b68..3e3f593bada 100644 --- a/drivers/scsi/qla2xxx/qla_nx.c +++ b/drivers/scsi/qla2xxx/qla_nx.c @@ -36,7 +36,7 @@ #define MAX_CRB_XFORM 60 static unsigned long crb_addr_xform[MAX_CRB_XFORM]; -int qla82xx_crb_table_initialized; +static int qla82xx_crb_table_initialized; #define qla82xx_crb_addr_transform(name) \ (crb_addr_xform[QLA82XX_HW_PX_MAP_CRB_##name] = \ @@ -102,7 +102,7 @@ static void qla82xx_crb_addr_transform_setup(void) qla82xx_crb_table_initialized = 1; } -struct crb_128M_2M_block_map crb_128M_2M_map[64] = { +static struct crb_128M_2M_block_map crb_128M_2M_map[64] = { {{{0, 0, 0, 0} } }, {{{1, 0x0100000, 0x0102000, 0x120000}, {1, 0x0110000, 0x0120000, 0x130000}, @@ -262,7 +262,7 @@ struct crb_128M_2M_block_map crb_128M_2M_map[64] = { /* * top 12 bits of crb internal address (hub, agent) */ -unsigned qla82xx_crb_hub_agt[64] = { +static unsigned qla82xx_crb_hub_agt[64] = { 0, QLA82XX_HW_CRB_HUB_AGT_ADR_PS, QLA82XX_HW_CRB_HUB_AGT_ADR_MN, @@ -330,7 +330,7 @@ unsigned qla82xx_crb_hub_agt[64] = { }; /* Device states */ -char *q_dev_state[] = { +static char *q_dev_state[] = { "Unknown", "Cold", "Initializing", @@ -359,12 +359,13 @@ qla82xx_pci_set_crbwindow_2M(struct qla_hw_data *ha, ulong *off) ha->crb_win = CRB_HI(*off); writel(ha->crb_win, - (void *)(CRB_WINDOW_2M + ha->nx_pcibase)); + (void __iomem *)(CRB_WINDOW_2M + ha->nx_pcibase)); /* Read back value to make sure write has gone through before trying * to use it. */ - win_read = RD_REG_DWORD((void *)(CRB_WINDOW_2M + ha->nx_pcibase)); + win_read = RD_REG_DWORD((void __iomem *) + (CRB_WINDOW_2M + ha->nx_pcibase)); if (win_read != ha->crb_win) { ql_dbg(ql_dbg_p3p, vha, 0xb000, "%s: Written crbwin (0x%x) " @@ -567,7 +568,7 @@ qla82xx_pci_mem_bound_check(struct qla_hw_data *ha, return 1; } -int qla82xx_pci_set_window_warning_count; +static int qla82xx_pci_set_window_warning_count; static unsigned long qla82xx_pci_set_window(struct qla_hw_data *ha, unsigned long long addr) @@ -677,10 +678,10 @@ static int qla82xx_pci_mem_read_direct(struct qla_hw_data *ha, u64 off, void *data, int size) { unsigned long flags; - void *addr = NULL; + void __iomem *addr = NULL; int ret = 0; u64 start; - uint8_t *mem_ptr = NULL; + uint8_t __iomem *mem_ptr = NULL; unsigned long mem_base; unsigned long mem_page; scsi_qla_host_t *vha = pci_get_drvdata(ha->pdev); @@ -712,7 +713,7 @@ static int qla82xx_pci_mem_read_direct(struct qla_hw_data *ha, mem_ptr = ioremap(mem_base + mem_page, PAGE_SIZE * 2); else mem_ptr = ioremap(mem_base + mem_page, PAGE_SIZE); - if (mem_ptr == 0UL) { + if (mem_ptr == NULL) { *(u8 *)data = 0; return -1; } @@ -749,10 +750,10 @@ qla82xx_pci_mem_write_direct(struct qla_hw_data *ha, u64 off, void *data, int size) { unsigned long flags; - void *addr = NULL; + void __iomem *addr = NULL; int ret = 0; u64 start; - uint8_t *mem_ptr = NULL; + uint8_t __iomem *mem_ptr = NULL; unsigned long mem_base; unsigned long mem_page; scsi_qla_host_t *vha = pci_get_drvdata(ha->pdev); @@ -784,7 +785,7 @@ qla82xx_pci_mem_write_direct(struct qla_hw_data *ha, mem_ptr = ioremap(mem_base + mem_page, PAGE_SIZE*2); else mem_ptr = ioremap(mem_base + mem_page, PAGE_SIZE); - if (mem_ptr == 0UL) + if (mem_ptr == NULL) return -1; addr = mem_ptr; @@ -908,24 +909,24 @@ qla82xx_wait_rom_done(struct qla_hw_data *ha) return 0; } -int +static int qla82xx_md_rw_32(struct qla_hw_data *ha, uint32_t off, u32 data, uint8_t flag) { uint32_t off_value, rval = 0; - WRT_REG_DWORD((void *)(CRB_WINDOW_2M + ha->nx_pcibase), + WRT_REG_DWORD((void __iomem *)(CRB_WINDOW_2M + ha->nx_pcibase), (off & 0xFFFF0000)); /* Read back value to make sure write has gone through */ - RD_REG_DWORD((void *)(CRB_WINDOW_2M + ha->nx_pcibase)); + RD_REG_DWORD((void __iomem *)(CRB_WINDOW_2M + ha->nx_pcibase)); off_value = (off & 0x0000FFFF); if (flag) - WRT_REG_DWORD((void *) + WRT_REG_DWORD((void __iomem *) (off_value + CRB_INDIRECT_2M + ha->nx_pcibase), data); else - rval = RD_REG_DWORD((void *) + rval = RD_REG_DWORD((void __iomem *) (off_value + CRB_INDIRECT_2M + ha->nx_pcibase)); return rval; @@ -1654,7 +1655,6 @@ qla82xx_iospace_config(struct qla_hw_data *ha) if (!ha->nx_pcibase) { ql_log_pci(ql_log_fatal, ha->pdev, 0x000e, "Cannot remap pcibase MMIO, aborting.\n"); - pci_release_regions(ha->pdev); goto iospace_error_exit; } @@ -1669,7 +1669,6 @@ qla82xx_iospace_config(struct qla_hw_data *ha) if (!ha->nxdb_wr_ptr) { ql_log_pci(ql_log_fatal, ha->pdev, 0x000f, "Cannot remap MMIO, aborting.\n"); - pci_release_regions(ha->pdev); goto iospace_error_exit; } @@ -1764,14 +1763,6 @@ void qla82xx_config_rings(struct scsi_qla_host *vha) WRT_REG_DWORD((unsigned long __iomem *)®->rsp_q_out[0], 0); } -void qla82xx_reset_adapter(struct scsi_qla_host *vha) -{ - struct qla_hw_data *ha = vha->hw; - vha->flags.online = 0; - qla2x00_try_to_stop_firmware(vha); - ha->isp_ops->disable_intrs(ha); -} - static int qla82xx_fw_load_from_blob(struct qla_hw_data *ha) { @@ -1856,7 +1847,7 @@ qla82xx_set_product_offset(struct qla_hw_data *ha) return -1; } -int +static int qla82xx_validate_firmware_blob(scsi_qla_host_t *vha, uint8_t fw_type) { __le32 val; @@ -1961,20 +1952,6 @@ qla82xx_check_rcvpeg_state(struct qla_hw_data *ha) } /* ISR related functions */ -uint32_t qla82xx_isr_int_target_mask_enable[8] = { - ISR_INT_TARGET_MASK, ISR_INT_TARGET_MASK_F1, - ISR_INT_TARGET_MASK_F2, ISR_INT_TARGET_MASK_F3, - ISR_INT_TARGET_MASK_F4, ISR_INT_TARGET_MASK_F5, - ISR_INT_TARGET_MASK_F7, ISR_INT_TARGET_MASK_F7 -}; - -uint32_t qla82xx_isr_int_target_status[8] = { - ISR_INT_TARGET_STATUS, ISR_INT_TARGET_STATUS_F1, - ISR_INT_TARGET_STATUS_F2, ISR_INT_TARGET_STATUS_F3, - ISR_INT_TARGET_STATUS_F4, ISR_INT_TARGET_STATUS_F5, - ISR_INT_TARGET_STATUS_F7, ISR_INT_TARGET_STATUS_F7 -}; - static struct qla82xx_legacy_intr_set legacy_intr[] = \ QLA82XX_LEGACY_INTR_CONFIG; @@ -2813,7 +2790,7 @@ qla82xx_start_iocbs(scsi_qla_host_t *vha) else { WRT_REG_DWORD((unsigned long __iomem *)ha->nxdb_wr_ptr, dbval); wmb(); - while (RD_REG_DWORD(ha->nxdb_rd_ptr) != dbval) { + while (RD_REG_DWORD((void __iomem *)ha->nxdb_rd_ptr) != dbval) { WRT_REG_DWORD((unsigned long __iomem *)ha->nxdb_wr_ptr, dbval); wmb(); @@ -2821,7 +2798,8 @@ qla82xx_start_iocbs(scsi_qla_host_t *vha) } } -void qla82xx_rom_lock_recovery(struct qla_hw_data *ha) +static void +qla82xx_rom_lock_recovery(struct qla_hw_data *ha) { scsi_qla_host_t *vha = pci_get_drvdata(ha->pdev); @@ -3177,7 +3155,7 @@ qla82xx_check_md_needed(scsi_qla_host_t *vha) } -int +static int qla82xx_check_fw_alive(scsi_qla_host_t *vha) { uint32_t fw_heartbeat_counter; @@ -3817,7 +3795,8 @@ qla82xx_minidump_process_rdocm(scsi_qla_host_t *vha, loop_cnt = ocm_hdr->op_count; for (i = 0; i < loop_cnt; i++) { - r_value = RD_REG_DWORD((void *)(r_addr + ha->nx_pcibase)); + r_value = RD_REG_DWORD((void __iomem *) + (r_addr + ha->nx_pcibase)); *data_ptr++ = cpu_to_le32(r_value); r_addr += r_stride; } @@ -4376,7 +4355,7 @@ qla82xx_md_free(scsi_qla_host_t *vha) ha->md_tmplt_hdr, ha->md_template_size / 1024); dma_free_coherent(&ha->pdev->dev, ha->md_template_size, ha->md_tmplt_hdr, ha->md_tmplt_hdr_dma); - ha->md_tmplt_hdr = 0; + ha->md_tmplt_hdr = NULL; } /* Release the template data buffer allocated */ @@ -4386,7 +4365,7 @@ qla82xx_md_free(scsi_qla_host_t *vha) ha->md_dump, ha->md_dump_size / 1024); vfree(ha->md_dump); ha->md_dump_size = 0; - ha->md_dump = 0; + ha->md_dump = NULL; } } @@ -4423,7 +4402,7 @@ qla82xx_md_prep(scsi_qla_host_t *vha) dma_free_coherent(&ha->pdev->dev, ha->md_template_size, ha->md_tmplt_hdr, ha->md_tmplt_hdr_dma); - ha->md_tmplt_hdr = 0; + ha->md_tmplt_hdr = NULL; } } diff --git a/drivers/scsi/qla2xxx/qla_os.c b/drivers/scsi/qla2xxx/qla_os.c index d501bf5f806..10d23f8b703 100644 --- a/drivers/scsi/qla2xxx/qla_os.c +++ b/drivers/scsi/qla2xxx/qla_os.c @@ -41,7 +41,7 @@ static struct kmem_cache *ctx_cachep; */ int ql_errlev = ql_log_all; -int ql2xenableclass2; +static int ql2xenableclass2; module_param(ql2xenableclass2, int, S_IRUGO|S_IRUSR); MODULE_PARM_DESC(ql2xenableclass2, "Specify if Class 2 operations are supported from the very " @@ -89,6 +89,8 @@ MODULE_PARM_DESC(ql2xextended_error_logging, "\t\t0x00200000 - AER/EEH. 0x00100000 - Multi Q.\n" "\t\t0x00080000 - P3P Specific. 0x00040000 - Virtual Port.\n" "\t\t0x00020000 - Buffer Dump. 0x00010000 - Misc.\n" + "\t\t0x00008000 - Verbose. 0x00004000 - Target.\n" + "\t\t0x00002000 - Target Mgmt. 0x00001000 - Target TMF.\n" "\t\t0x7fffffff - For enabling all logs, can be too many logs.\n" "\t\t0x1e400000 - Preferred value for capturing essential " "debug information (equivalent to old " @@ -494,12 +496,20 @@ qla24xx_pci_info_str(struct scsi_qla_host *vha, char *str) (BIT_4 | BIT_5 | BIT_6 | BIT_7 | BIT_8 | BIT_9)) >> 4; strcpy(str, "PCIe ("); - if (lspeed == 1) + switch (lspeed) { + case 1: strcat(str, "2.5GT/s "); - else if (lspeed == 2) + break; + case 2: strcat(str, "5.0GT/s "); - else + break; + case 3: + strcat(str, "8.0GT/s "); + break; + default: strcat(str, "<unknown> "); + break; + } snprintf(lwstr, sizeof(lwstr), "x%d)", lwidth); strcat(str, lwstr); @@ -719,7 +729,7 @@ qla2xxx_queuecommand(struct Scsi_Host *host, struct scsi_cmnd *cmd) rval = ha->isp_ops->start_scsi(sp); if (rval != QLA_SUCCESS) { - ql_dbg(ql_dbg_io, vha, 0x3013, + ql_dbg(ql_dbg_io + ql_dbg_verbose, vha, 0x3013, "Start scsi failed rval=%d for cmd=%p.\n", rval, cmd); goto qc24_host_busy_free_sp; } @@ -2144,7 +2154,7 @@ qla2xxx_scan_finished(struct Scsi_Host *shost, unsigned long time) /* * PCI driver interface */ -static int __devinit +static int qla2x00_probe_one(struct pci_dev *pdev, const struct pci_device_id *id) { int ret = -ENODEV; @@ -2357,7 +2367,7 @@ qla2x00_probe_one(struct pci_dev *pdev, const struct pci_device_id *id) /* Configure PCI I/O space */ ret = ha->isp_ops->iospace_config(ha); if (ret) - goto probe_hw_failed; + goto iospace_config_failed; ql_log_pci(ql_log_info, pdev, 0x001d, "Found an ISP%04X irq %d iobase 0x%p.\n", @@ -2668,7 +2678,11 @@ probe_hw_failed: qla82xx_idc_lock(ha); qla82xx_clear_drv_active(ha); qla82xx_idc_unlock(ha); - iounmap((device_reg_t __iomem *)ha->nx_pcibase); + } +iospace_config_failed: + if (IS_QLA82XX(ha)) { + if (!ha->nx_pcibase) + iounmap((device_reg_t __iomem *)ha->nx_pcibase); if (!ql2xdbwr) iounmap((device_reg_t __iomem *)ha->nxdb_wr_ptr); } else { @@ -2755,6 +2769,7 @@ qla2x00_remove_one(struct pci_dev *pdev) ha->flags.host_shutting_down = 1; + set_bit(UNLOADING, &base_vha->dpc_flags); mutex_lock(&ha->vport_lock); while (ha->cur_vport_count) { struct Scsi_Host *scsi_host; @@ -2784,8 +2799,6 @@ qla2x00_remove_one(struct pci_dev *pdev) "Error while clearing DRV-Presence.\n"); } - set_bit(UNLOADING, &base_vha->dpc_flags); - qla2x00_abort_all_cmds(base_vha, DID_NO_CONNECT << 16); qla2x00_dfs_remove(base_vha); @@ -3721,10 +3734,9 @@ void qla2x00_relogin(struct scsi_qla_host *vha) if (fcport->flags & FCF_FCP2_DEVICE) opts |= BIT_1; - status2 = - qla2x00_get_port_database( - vha, fcport, - opts); + status2 = + qla2x00_get_port_database( + vha, fcport, opts); if (status2 != QLA_SUCCESS) status = 1; } @@ -3836,7 +3848,7 @@ qla83xx_idc_state_handler_work(struct work_struct *work) qla83xx_idc_unlock(base_vha, 0); } -int +static int qla83xx_check_nic_core_fw_alive(scsi_qla_host_t *base_vha) { int rval = QLA_SUCCESS; @@ -3954,7 +3966,7 @@ qla83xx_wait_logic(void) } } -int +static int qla83xx_force_lock_recovery(scsi_qla_host_t *base_vha) { int rval; @@ -4013,7 +4025,7 @@ qla83xx_force_lock_recovery(scsi_qla_host_t *base_vha) return rval; } -int +static int qla83xx_idc_lock_recovery(scsi_qla_host_t *base_vha) { int rval = QLA_SUCCESS; @@ -4212,7 +4224,7 @@ qla83xx_clear_drv_presence(scsi_qla_host_t *vha) return rval; } -void +static void qla83xx_need_reset_handler(scsi_qla_host_t *vha) { struct qla_hw_data *ha = vha->hw; @@ -4224,7 +4236,7 @@ qla83xx_need_reset_handler(scsi_qla_host_t *vha) while (1) { qla83xx_rd_reg(vha, QLA83XX_IDC_DRIVER_ACK, &drv_ack); qla83xx_rd_reg(vha, QLA83XX_IDC_DRV_PRESENCE, &drv_presence); - if (drv_ack == drv_presence) + if ((drv_ack & drv_presence) == drv_presence) break; if (time_after_eq(jiffies, ack_timeout)) { @@ -4251,7 +4263,7 @@ qla83xx_need_reset_handler(scsi_qla_host_t *vha) ql_log(ql_log_info, vha, 0xb068, "HW State: COLD/RE-INIT.\n"); } -int +static int qla83xx_device_bootstrap(scsi_qla_host_t *vha) { int rval = QLA_SUCCESS; @@ -4505,9 +4517,9 @@ qla2x00_do_dpc(void *data) "ISP abort end.\n"); } - if (test_bit(FCPORT_UPDATE_NEEDED, &base_vha->dpc_flags)) { + if (test_and_clear_bit(FCPORT_UPDATE_NEEDED, + &base_vha->dpc_flags)) { qla2x00_update_fcports(base_vha); - clear_bit(FCPORT_UPDATE_NEEDED, &base_vha->dpc_flags); } if (test_bit(SCR_PENDING, &base_vha->dpc_flags)) { @@ -4987,7 +4999,8 @@ qla2xxx_pci_mmio_enabled(struct pci_dev *pdev) return PCI_ERS_RESULT_RECOVERED; } -uint32_t qla82xx_error_recovery(scsi_qla_host_t *base_vha) +static uint32_t +qla82xx_error_recovery(scsi_qla_host_t *base_vha) { uint32_t rval = QLA_FUNCTION_FAILED; uint32_t drv_active = 0; diff --git a/drivers/scsi/qla2xxx/qla_target.c b/drivers/scsi/qla2xxx/qla_target.c index 5b496d0a631..80f4b849e2b 100644 --- a/drivers/scsi/qla2xxx/qla_target.c +++ b/drivers/scsi/qla2xxx/qla_target.c @@ -557,6 +557,7 @@ static bool qlt_check_fcport_exist(struct scsi_qla_host *vha, int pmap_len; fc_port_t *fcport; int global_resets; + unsigned long flags; retry: global_resets = atomic_read(&ha->tgt.qla_tgt->tgt_global_resets_count); @@ -625,10 +626,10 @@ retry: sess->s_id.b.area, sess->loop_id, fcport->d_id.b.domain, fcport->d_id.b.al_pa, fcport->d_id.b.area, fcport->loop_id); - sess->s_id = fcport->d_id; - sess->loop_id = fcport->loop_id; - sess->conf_compl_supported = !!(fcport->flags & - FCF_CONF_COMP_SUPPORTED); + spin_lock_irqsave(&ha->hardware_lock, flags); + ha->tgt.tgt_ops->update_sess(sess, fcport->d_id, fcport->loop_id, + (fcport->flags & FCF_CONF_COMP_SUPPORTED)); + spin_unlock_irqrestore(&ha->hardware_lock, flags); res = true; @@ -740,10 +741,9 @@ static struct qla_tgt_sess *qlt_create_sess( qlt_undelete_sess(sess); kref_get(&sess->se_sess->sess_kref); - sess->s_id = fcport->d_id; - sess->loop_id = fcport->loop_id; - sess->conf_compl_supported = !!(fcport->flags & - FCF_CONF_COMP_SUPPORTED); + ha->tgt.tgt_ops->update_sess(sess, fcport->d_id, fcport->loop_id, + (fcport->flags & FCF_CONF_COMP_SUPPORTED)); + if (sess->local && !local) sess->local = 0; spin_unlock_irqrestore(&ha->hardware_lock, flags); @@ -796,8 +796,7 @@ static struct qla_tgt_sess *qlt_create_sess( */ kref_get(&sess->se_sess->sess_kref); - sess->conf_compl_supported = !!(fcport->flags & - FCF_CONF_COMP_SUPPORTED); + sess->conf_compl_supported = (fcport->flags & FCF_CONF_COMP_SUPPORTED); BUILD_BUG_ON(sizeof(sess->port_name) != sizeof(fcport->port_name)); memcpy(sess->port_name, fcport->port_name, sizeof(sess->port_name)); @@ -869,10 +868,8 @@ void qlt_fc_port_added(struct scsi_qla_host *vha, fc_port_t *fcport) ql_dbg(ql_dbg_tgt_mgt, vha, 0xf007, "Reappeared sess %p\n", sess); } - sess->s_id = fcport->d_id; - sess->loop_id = fcport->loop_id; - sess->conf_compl_supported = !!(fcport->flags & - FCF_CONF_COMP_SUPPORTED); + ha->tgt.tgt_ops->update_sess(sess, fcport->d_id, fcport->loop_id, + (fcport->flags & FCF_CONF_COMP_SUPPORTED)); } if (sess && sess->local) { @@ -1032,7 +1029,7 @@ void qlt_stop_phase2(struct qla_tgt *tgt) EXPORT_SYMBOL(qlt_stop_phase2); /* Called from qlt_remove_target() -> qla2x00_remove_one() */ -void qlt_release(struct qla_tgt *tgt) +static void qlt_release(struct qla_tgt *tgt) { struct qla_hw_data *ha = tgt->ha; @@ -1267,8 +1264,27 @@ static int __qlt_24xx_handle_abts(struct scsi_qla_host *vha, struct abts_recv_from_24xx *abts, struct qla_tgt_sess *sess) { struct qla_hw_data *ha = vha->hw; + struct se_session *se_sess = sess->se_sess; struct qla_tgt_mgmt_cmd *mcmd; + struct se_cmd *se_cmd; + u32 lun = 0; int rc; + bool found_lun = false; + + spin_lock(&se_sess->sess_cmd_lock); + list_for_each_entry(se_cmd, &se_sess->sess_cmd_list, se_cmd_list) { + struct qla_tgt_cmd *cmd = + container_of(se_cmd, struct qla_tgt_cmd, se_cmd); + if (cmd->tag == abts->exchange_addr_to_abort) { + lun = cmd->unpacked_lun; + found_lun = true; + break; + } + } + spin_unlock(&se_sess->sess_cmd_lock); + + if (!found_lun) + return -ENOENT; ql_dbg(ql_dbg_tgt_mgt, vha, 0xf00f, "qla_target(%d): task abort (tag=%d)\n", @@ -1286,7 +1302,7 @@ static int __qlt_24xx_handle_abts(struct scsi_qla_host *vha, mcmd->sess = sess; memcpy(&mcmd->orig_iocb.abts, abts, sizeof(mcmd->orig_iocb.abts)); - rc = ha->tgt.tgt_ops->handle_tmr(mcmd, 0, TMR_ABORT_TASK, + rc = ha->tgt.tgt_ops->handle_tmr(mcmd, lun, TMR_ABORT_TASK, abts->exchange_addr_to_abort); if (rc != 0) { ql_dbg(ql_dbg_tgt_mgt, vha, 0xf052, diff --git a/drivers/scsi/qla2xxx/qla_target.h b/drivers/scsi/qla2xxx/qla_target.h index 170af157121..bad749561ec 100644 --- a/drivers/scsi/qla2xxx/qla_target.h +++ b/drivers/scsi/qla2xxx/qla_target.h @@ -648,6 +648,7 @@ struct qla_tgt_func_tmpl { int (*check_initiator_node_acl)(struct scsi_qla_host *, unsigned char *, void *, uint8_t *, uint16_t); + void (*update_sess)(struct qla_tgt_sess *, port_id_t, uint16_t, bool); struct qla_tgt_sess *(*find_sess_by_loop_id)(struct scsi_qla_host *, const uint16_t); struct qla_tgt_sess *(*find_sess_by_s_id)(struct scsi_qla_host *, diff --git a/drivers/scsi/qla2xxx/qla_version.h b/drivers/scsi/qla2xxx/qla_version.h index cfe934e1af4..49697ca41e7 100644 --- a/drivers/scsi/qla2xxx/qla_version.h +++ b/drivers/scsi/qla2xxx/qla_version.h @@ -7,7 +7,7 @@ /* * Driver version */ -#define QLA2XXX_VERSION "8.04.00.07-k" +#define QLA2XXX_VERSION "8.04.00.08-k" #define QLA_DRIVER_MAJOR_VER 8 #define QLA_DRIVER_MINOR_VER 4 diff --git a/drivers/scsi/qla2xxx/tcm_qla2xxx.c b/drivers/scsi/qla2xxx/tcm_qla2xxx.c index c0b682c75ee..d182c96e17e 100644 --- a/drivers/scsi/qla2xxx/tcm_qla2xxx.c +++ b/drivers/scsi/qla2xxx/tcm_qla2xxx.c @@ -237,7 +237,7 @@ static char *tcm_qla2xxx_get_fabric_wwn(struct se_portal_group *se_tpg) struct tcm_qla2xxx_tpg, se_tpg); struct tcm_qla2xxx_lport *lport = tpg->lport; - return &lport->lport_name[0]; + return lport->lport_naa_name; } static char *tcm_qla2xxx_npiv_get_fabric_wwn(struct se_portal_group *se_tpg) @@ -620,8 +620,8 @@ static void tcm_qla2xxx_handle_data_work(struct work_struct *work) return; } - cmd->se_cmd.scsi_sense_reason = TCM_CHECK_CONDITION_ABORT_CMD; - transport_generic_request_failure(&cmd->se_cmd); + transport_generic_request_failure(&cmd->se_cmd, + TCM_CHECK_CONDITION_ABORT_CMD); return; } @@ -1457,6 +1457,78 @@ static int tcm_qla2xxx_check_initiator_node_acl( return 0; } +static void tcm_qla2xxx_update_sess(struct qla_tgt_sess *sess, port_id_t s_id, + uint16_t loop_id, bool conf_compl_supported) +{ + struct qla_tgt *tgt = sess->tgt; + struct qla_hw_data *ha = tgt->ha; + struct tcm_qla2xxx_lport *lport = ha->tgt.target_lport_ptr; + struct se_node_acl *se_nacl = sess->se_sess->se_node_acl; + struct tcm_qla2xxx_nacl *nacl = container_of(se_nacl, + struct tcm_qla2xxx_nacl, se_node_acl); + u32 key; + + + if (sess->loop_id != loop_id || sess->s_id.b24 != s_id.b24) + pr_info("Updating session %p from port %02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x loop_id %d -> %d s_id %x:%x:%x -> %x:%x:%x\n", + sess, + sess->port_name[0], sess->port_name[1], + sess->port_name[2], sess->port_name[3], + sess->port_name[4], sess->port_name[5], + sess->port_name[6], sess->port_name[7], + sess->loop_id, loop_id, + sess->s_id.b.domain, sess->s_id.b.area, sess->s_id.b.al_pa, + s_id.b.domain, s_id.b.area, s_id.b.al_pa); + + if (sess->loop_id != loop_id) { + /* + * Because we can shuffle loop IDs around and we + * update different sessions non-atomically, we might + * have overwritten this session's old loop ID + * already, and we might end up overwriting some other + * session that will be updated later. So we have to + * be extra careful and we can't warn about those things... + */ + if (lport->lport_loopid_map[sess->loop_id].se_nacl == se_nacl) + lport->lport_loopid_map[sess->loop_id].se_nacl = NULL; + + lport->lport_loopid_map[loop_id].se_nacl = se_nacl; + + sess->loop_id = loop_id; + } + + if (sess->s_id.b24 != s_id.b24) { + key = (((u32) sess->s_id.b.domain << 16) | + ((u32) sess->s_id.b.area << 8) | + ((u32) sess->s_id.b.al_pa)); + + if (btree_lookup32(&lport->lport_fcport_map, key)) + WARN(btree_remove32(&lport->lport_fcport_map, key) != se_nacl, + "Found wrong se_nacl when updating s_id %x:%x:%x\n", + sess->s_id.b.domain, sess->s_id.b.area, sess->s_id.b.al_pa); + else + WARN(1, "No lport_fcport_map entry for s_id %x:%x:%x\n", + sess->s_id.b.domain, sess->s_id.b.area, sess->s_id.b.al_pa); + + key = (((u32) s_id.b.domain << 16) | + ((u32) s_id.b.area << 8) | + ((u32) s_id.b.al_pa)); + + if (btree_lookup32(&lport->lport_fcport_map, key)) { + WARN(1, "Already have lport_fcport_map entry for s_id %x:%x:%x\n", + s_id.b.domain, s_id.b.area, s_id.b.al_pa); + btree_update32(&lport->lport_fcport_map, key, se_nacl); + } else { + btree_insert32(&lport->lport_fcport_map, key, se_nacl, GFP_ATOMIC); + } + + sess->s_id = s_id; + nacl->nport_id = key; + } + + sess->conf_compl_supported = conf_compl_supported; +} + /* * Calls into tcm_qla2xxx used by qla2xxx LLD I/O path. */ @@ -1467,6 +1539,7 @@ static struct qla_tgt_func_tmpl tcm_qla2xxx_template = { .free_cmd = tcm_qla2xxx_free_cmd, .free_mcmd = tcm_qla2xxx_free_mcmd, .free_session = tcm_qla2xxx_free_session, + .update_sess = tcm_qla2xxx_update_sess, .check_initiator_node_acl = tcm_qla2xxx_check_initiator_node_acl, .find_sess_by_s_id = tcm_qla2xxx_find_sess_by_s_id, .find_sess_by_loop_id = tcm_qla2xxx_find_sess_by_loop_id, @@ -1534,6 +1607,7 @@ static struct se_wwn *tcm_qla2xxx_make_lport( lport->lport_wwpn = wwpn; tcm_qla2xxx_format_wwn(&lport->lport_name[0], TCM_QLA2XXX_NAMELEN, wwpn); + sprintf(lport->lport_naa_name, "naa.%016llx", (unsigned long long) wwpn); ret = tcm_qla2xxx_init_lport(lport); if (ret != 0) @@ -1601,6 +1675,7 @@ static struct se_wwn *tcm_qla2xxx_npiv_make_lport( lport->lport_npiv_wwnn = npiv_wwnn; tcm_qla2xxx_npiv_format_wwn(&lport->lport_npiv_name[0], TCM_QLA2XXX_NAMELEN, npiv_wwpn, npiv_wwnn); + sprintf(lport->lport_naa_name, "naa.%016llx", (unsigned long long) npiv_wwpn); /* FIXME: tcm_qla2xxx_npiv_make_lport */ ret = -ENOSYS; diff --git a/drivers/scsi/qla2xxx/tcm_qla2xxx.h b/drivers/scsi/qla2xxx/tcm_qla2xxx.h index 82549810335..9ba075fe978 100644 --- a/drivers/scsi/qla2xxx/tcm_qla2xxx.h +++ b/drivers/scsi/qla2xxx/tcm_qla2xxx.h @@ -61,6 +61,8 @@ struct tcm_qla2xxx_lport { u64 lport_npiv_wwnn; /* ASCII formatted WWPN for FC Target Lport */ char lport_name[TCM_QLA2XXX_NAMELEN]; + /* ASCII formatted naa WWPN for VPD page 83 etc */ + char lport_naa_name[TCM_QLA2XXX_NAMELEN]; /* ASCII formatted WWPN+WWNN for NPIV FC Target Lport */ char lport_npiv_name[TCM_QLA2XXX_NPIV_NAMELEN]; /* map for fc_port pointers in 24-bit FC Port ID space */ |