aboutsummaryrefslogtreecommitdiff
path: root/drivers/scsi/qla2xxx/qla_nx.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/scsi/qla2xxx/qla_nx.c')
-rw-r--r--drivers/scsi/qla2xxx/qla_nx.c490
1 files changed, 274 insertions, 216 deletions
diff --git a/drivers/scsi/qla2xxx/qla_nx.c b/drivers/scsi/qla2xxx/qla_nx.c
index caf627ba7fa..58f3c912d96 100644
--- a/drivers/scsi/qla2xxx/qla_nx.c
+++ b/drivers/scsi/qla2xxx/qla_nx.c
@@ -1,6 +1,6 @@
/*
* QLogic Fibre Channel HBA Driver
- * Copyright (c) 2003-2011 QLogic Corporation
+ * Copyright (c) 2003-2014 QLogic Corporation
*
* See LICENSE.qla2xxx for copyright and licensing details.
*/
@@ -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;
@@ -846,23 +847,31 @@ static int
qla82xx_rom_lock(struct qla_hw_data *ha)
{
int done = 0, timeout = 0;
+ uint32_t lock_owner = 0;
+ scsi_qla_host_t *vha = pci_get_drvdata(ha->pdev);
while (!done) {
/* acquire semaphore2 from PCI HW block */
done = qla82xx_rd_32(ha, QLA82XX_PCIE_REG(PCIE_SEM2_LOCK));
if (done == 1)
break;
- if (timeout >= qla82xx_rom_lock_timeout)
+ if (timeout >= qla82xx_rom_lock_timeout) {
+ lock_owner = qla82xx_rd_32(ha, QLA82XX_ROM_LOCK_ID);
+ ql_log(ql_log_warn, vha, 0xb157,
+ "%s: Simultaneous flash access by following ports, active port = %d: accessing port = %d",
+ __func__, ha->portnum, lock_owner);
return -1;
+ }
timeout++;
}
- qla82xx_wr_32(ha, QLA82XX_ROM_LOCK_ID, ROM_LOCK_DRIVER);
+ qla82xx_wr_32(ha, QLA82XX_ROM_LOCK_ID, ha->portnum);
return 0;
}
static void
qla82xx_rom_unlock(struct qla_hw_data *ha)
{
+ qla82xx_wr_32(ha, QLA82XX_ROM_LOCK_ID, 0xffffffff);
qla82xx_rd_32(ha, QLA82XX_PCIE_REG(PCIE_SEM2_UNLOCK));
}
@@ -908,24 +917,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;
@@ -946,6 +955,7 @@ static int
qla82xx_rom_fast_read(struct qla_hw_data *ha, int addr, int *valp)
{
int ret, loops = 0;
+ uint32_t lock_owner = 0;
scsi_qla_host_t *vha = pci_get_drvdata(ha->pdev);
while ((qla82xx_rom_lock(ha) != 0) && (loops < 50000)) {
@@ -954,8 +964,10 @@ qla82xx_rom_fast_read(struct qla_hw_data *ha, int addr, int *valp)
loops++;
}
if (loops >= 50000) {
+ lock_owner = qla82xx_rd_32(ha, QLA82XX_ROM_LOCK_ID);
ql_log(ql_log_fatal, vha, 0x00b9,
- "Failed to aquire SEM2 lock.\n");
+ "Failed to acquire SEM2 lock, Lock Owner %u.\n",
+ lock_owner);
return -1;
}
ret = qla82xx_do_rom_fast_read(ha, addr, valp);
@@ -1053,6 +1065,7 @@ static int
ql82xx_rom_lock_d(struct qla_hw_data *ha)
{
int loops = 0;
+ uint32_t lock_owner = 0;
scsi_qla_host_t *vha = pci_get_drvdata(ha->pdev);
while ((qla82xx_rom_lock(ha) != 0) && (loops < 50000)) {
@@ -1061,8 +1074,9 @@ ql82xx_rom_lock_d(struct qla_hw_data *ha)
loops++;
}
if (loops >= 50000) {
+ lock_owner = qla82xx_rd_32(ha, QLA82XX_ROM_LOCK_ID);
ql_log(ql_log_warn, vha, 0xb010,
- "ROM lock failed.\n");
+ "ROM lock failed, Lock Owner %u.\n", lock_owner);
return -1;
}
return 0;
@@ -1122,7 +1136,7 @@ qla82xx_pinit_from_rom(scsi_qla_host_t *vha)
long data;
};
- /* Halt all the indiviual PEGs and other blocks of the ISP */
+ /* Halt all the individual PEGs and other blocks of the ISP */
qla82xx_rom_lock(ha);
/* disable all I2Q */
@@ -1612,25 +1626,6 @@ qla82xx_get_fw_offs(struct qla_hw_data *ha)
}
/* PCI related functions */
-char *
-qla82xx_pci_info_str(struct scsi_qla_host *vha, char *str)
-{
- int pcie_reg;
- struct qla_hw_data *ha = vha->hw;
- char lwstr[6];
- uint16_t lnk;
-
- pcie_reg = pci_find_capability(ha->pdev, PCI_CAP_ID_EXP);
- pci_read_config_word(ha->pdev, pcie_reg + PCI_EXP_LNKSTA, &lnk);
- ha->link_width = (lnk >> 4) & 0x3f;
-
- strcpy(str, "PCIe (");
- strcat(str, "2.5Gb/s ");
- snprintf(lwstr, sizeof(lwstr), "x%d)", ha->link_width);
- strcat(str, lwstr);
- return str;
-}
-
int qla82xx_pci_region_offset(struct pci_dev *pdev, int region)
{
unsigned long val = 0;
@@ -1673,13 +1668,18 @@ 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;
}
/* Mapping of IO base pointer */
- ha->iobase = (device_reg_t __iomem *)((uint8_t *)ha->nx_pcibase +
- 0xbc000 + (ha->pdev->devfn << 11));
+ if (IS_QLA8044(ha)) {
+ ha->iobase =
+ (device_reg_t *)((uint8_t *)ha->nx_pcibase);
+ } else if (IS_QLA82XX(ha)) {
+ ha->iobase =
+ (device_reg_t *)((uint8_t *)ha->nx_pcibase +
+ 0xbc000 + (ha->pdev->devfn << 11));
+ }
if (!ql2xdbwr) {
ha->nxdb_wr_ptr =
@@ -1688,7 +1688,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;
}
@@ -1783,14 +1782,6 @@ void qla82xx_config_rings(struct scsi_qla_host *vha)
WRT_REG_DWORD((unsigned long __iomem *)&reg->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)
{
@@ -1875,7 +1866,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;
@@ -1980,20 +1971,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;
@@ -2002,7 +1979,7 @@ static struct qla82xx_legacy_intr_set legacy_intr[] = \
* @ha: SCSI driver HA context
* @mb0: Mailbox0 register
*/
-static void
+void
qla82xx_mbx_completion(scsi_qla_host_t *vha, uint16_t mb0)
{
uint16_t cnt;
@@ -2109,22 +2086,13 @@ qla82xx_intr_handler(int irq, void *dev_id)
}
WRT_REG_DWORD(&reg->host_int, 0);
}
+
+ qla2x00_handle_mbx_completion(ha, status);
spin_unlock_irqrestore(&ha->hardware_lock, flags);
+
if (!ha->flags.msi_enabled)
qla82xx_wr_32(ha, ha->nx_legacy_intr.tgt_mask_reg, 0xfbff);
-#ifdef QL_DEBUG_LEVEL_17
- if (!irq && ha->flags.eeh_busy)
- ql_log(ql_log_warn, vha, 0x503d,
- "isr:status %x, cmd_flags %lx, mbox_int %x, stat %x.\n",
- status, ha->mbx_cmd_flags, ha->flags.mbox_int, stat);
-#endif
-
- if (test_bit(MBX_INTR_WAIT, &ha->mbx_cmd_flags) &&
- (status & MBX_INTERRUPT) && ha->flags.mbox_int) {
- set_bit(MBX_INTERRUPT, &ha->mbx_cmd_flags);
- complete(&ha->mbx_intr_comp);
- }
return IRQ_HANDLED;
}
@@ -2138,6 +2106,7 @@ qla82xx_msix_default(int irq, void *dev_id)
int status = 0;
unsigned long flags;
uint32_t stat = 0;
+ uint32_t host_int = 0;
uint16_t mb[4];
rsp = (struct rsp_que *) dev_id;
@@ -2153,7 +2122,10 @@ qla82xx_msix_default(int irq, void *dev_id)
spin_lock_irqsave(&ha->hardware_lock, flags);
vha = pci_get_drvdata(ha->pdev);
do {
- if (RD_REG_DWORD(&reg->host_int)) {
+ host_int = RD_REG_DWORD(&reg->host_int);
+ if (qla2x00_check_reg_for_disconnect(vha, host_int))
+ break;
+ if (host_int) {
stat = RD_REG_DWORD(&reg->host_status);
switch (stat & 0xff) {
@@ -2184,20 +2156,9 @@ qla82xx_msix_default(int irq, void *dev_id)
WRT_REG_DWORD(&reg->host_int, 0);
} while (0);
+ qla2x00_handle_mbx_completion(ha, status);
spin_unlock_irqrestore(&ha->hardware_lock, flags);
-#ifdef QL_DEBUG_LEVEL_17
- if (!irq && ha->flags.eeh_busy)
- ql_log(ql_log_warn, vha, 0x5044,
- "isr:status %x, cmd_flags %lx, mbox_int %x, stat %x.\n",
- status, ha->mbx_cmd_flags, ha->flags.mbox_int, stat);
-#endif
-
- if (test_bit(MBX_INTR_WAIT, &ha->mbx_cmd_flags) &&
- (status & MBX_INTERRUPT) && ha->flags.mbox_int) {
- set_bit(MBX_INTERRUPT, &ha->mbx_cmd_flags);
- complete(&ha->mbx_intr_comp);
- }
return IRQ_HANDLED;
}
@@ -2209,6 +2170,7 @@ qla82xx_msix_rsp_q(int irq, void *dev_id)
struct rsp_que *rsp;
struct device_reg_82xx __iomem *reg;
unsigned long flags;
+ uint32_t host_int = 0;
rsp = (struct rsp_que *) dev_id;
if (!rsp) {
@@ -2221,8 +2183,12 @@ qla82xx_msix_rsp_q(int irq, void *dev_id)
reg = &ha->iobase->isp82;
spin_lock_irqsave(&ha->hardware_lock, flags);
vha = pci_get_drvdata(ha->pdev);
+ host_int = RD_REG_DWORD(&reg->host_int);
+ if (qla2x00_check_reg_for_disconnect(vha, host_int))
+ goto out;
qla24xx_process_response_queue(vha, rsp);
WRT_REG_DWORD(&reg->host_int, 0);
+out:
spin_unlock_irqrestore(&ha->hardware_lock, flags);
return IRQ_HANDLED;
}
@@ -2236,6 +2202,7 @@ qla82xx_poll(int irq, void *dev_id)
struct device_reg_82xx __iomem *reg;
int status = 0;
uint32_t stat;
+ uint32_t host_int = 0;
uint16_t mb[4];
unsigned long flags;
@@ -2251,7 +2218,10 @@ qla82xx_poll(int irq, void *dev_id)
spin_lock_irqsave(&ha->hardware_lock, flags);
vha = pci_get_drvdata(ha->pdev);
- if (RD_REG_DWORD(&reg->host_int)) {
+ host_int = RD_REG_DWORD(&reg->host_int);
+ if (qla2x00_check_reg_for_disconnect(vha, host_int))
+ goto out;
+ if (host_int) {
stat = RD_REG_DWORD(&reg->host_status);
switch (stat & 0xff) {
case 0x1:
@@ -2277,8 +2247,9 @@ qla82xx_poll(int irq, void *dev_id)
stat * 0xff);
break;
}
+ WRT_REG_DWORD(&reg->host_int, 0);
}
- WRT_REG_DWORD(&reg->host_int, 0);
+out:
spin_unlock_irqrestore(&ha->hardware_lock, flags);
}
@@ -2288,7 +2259,10 @@ qla82xx_enable_intrs(struct qla_hw_data *ha)
scsi_qla_host_t *vha = pci_get_drvdata(ha->pdev);
qla82xx_mbx_intr_enable(vha);
spin_lock_irq(&ha->hardware_lock);
- qla82xx_wr_32(ha, ha->nx_legacy_intr.tgt_mask_reg, 0xfbff);
+ if (IS_QLA8044(ha))
+ qla8044_wr_reg(ha, LEG_INTR_MASK_OFFSET, 0);
+ else
+ qla82xx_wr_32(ha, ha->nx_legacy_intr.tgt_mask_reg, 0xfbff);
spin_unlock_irq(&ha->hardware_lock);
ha->interrupts_on = 1;
}
@@ -2299,7 +2273,10 @@ qla82xx_disable_intrs(struct qla_hw_data *ha)
scsi_qla_host_t *vha = pci_get_drvdata(ha->pdev);
qla82xx_mbx_intr_disable(vha);
spin_lock_irq(&ha->hardware_lock);
- qla82xx_wr_32(ha, ha->nx_legacy_intr.tgt_mask_reg, 0x0400);
+ if (IS_QLA8044(ha))
+ qla8044_wr_reg(ha, LEG_INTR_MASK_OFFSET, 1);
+ else
+ qla82xx_wr_32(ha, ha->nx_legacy_intr.tgt_mask_reg, 0x0400);
spin_unlock_irq(&ha->hardware_lock);
ha->interrupts_on = 0;
}
@@ -2322,6 +2299,29 @@ void qla82xx_init_flags(struct qla_hw_data *ha)
}
inline void
+qla82xx_set_idc_version(scsi_qla_host_t *vha)
+{
+ int idc_ver;
+ uint32_t drv_active;
+ struct qla_hw_data *ha = vha->hw;
+
+ drv_active = qla82xx_rd_32(ha, QLA82XX_CRB_DRV_ACTIVE);
+ if (drv_active == (QLA82XX_DRV_ACTIVE << (ha->portnum * 4))) {
+ qla82xx_wr_32(ha, QLA82XX_CRB_DRV_IDC_VERSION,
+ QLA82XX_IDC_VERSION);
+ ql_log(ql_log_info, vha, 0xb082,
+ "IDC version updated to %d\n", QLA82XX_IDC_VERSION);
+ } else {
+ idc_ver = qla82xx_rd_32(ha, QLA82XX_CRB_DRV_IDC_VERSION);
+ if (idc_ver != QLA82XX_IDC_VERSION)
+ ql_log(ql_log_info, vha, 0xb083,
+ "qla2xxx driver IDC version %d is not compatible "
+ "with IDC version %d of the other drivers\n",
+ QLA82XX_IDC_VERSION, idc_ver);
+ }
+}
+
+inline void
qla82xx_set_drv_active(scsi_qla_host_t *vha)
{
uint32_t drv_active;
@@ -2355,7 +2355,7 @@ qla82xx_need_reset(struct qla_hw_data *ha)
uint32_t drv_state;
int rval;
- if (ha->flags.isp82xx_reset_owner)
+ if (ha->flags.nic_core_reset_owner)
return 1;
else {
drv_state = qla82xx_rd_32(ha, QLA82XX_CRB_DRV_STATE);
@@ -2497,7 +2497,6 @@ fw_load_failed:
int
qla82xx_start_firmware(scsi_qla_host_t *vha)
{
- int pcie_cap;
uint16_t lnk;
struct qla_hw_data *ha = vha->hw;
@@ -2528,8 +2527,7 @@ qla82xx_start_firmware(scsi_qla_host_t *vha)
}
/* Negotiated Link width */
- pcie_cap = pci_find_capability(ha->pdev, PCI_CAP_ID_EXP);
- pci_read_config_word(ha->pdev, pcie_cap + PCI_EXP_LNKSTA, &lnk);
+ pcie_capability_read_word(ha->pdev, PCI_EXP_LNKSTA, &lnk);
ha->link_width = (lnk >> 4) & 0x3f;
/* Synchronize with Receive peg */
@@ -2811,7 +2809,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();
@@ -2819,15 +2817,18 @@ 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);
+ uint32_t lock_owner = 0;
- if (qla82xx_rom_lock(ha))
+ if (qla82xx_rom_lock(ha)) {
+ lock_owner = qla82xx_rd_32(ha, QLA82XX_ROM_LOCK_ID);
/* Someone else is holding the lock. */
ql_log(ql_log_info, vha, 0xb022,
- "Resetting rom_lock.\n");
-
+ "Resetting rom_lock, Lock Owner %u.\n", lock_owner);
+ }
/*
* Either we got the lock, or someone
* else died while holding it.
@@ -2851,54 +2852,34 @@ static int
qla82xx_device_bootstrap(scsi_qla_host_t *vha)
{
int rval = QLA_SUCCESS;
- int i, timeout;
+ int i;
uint32_t old_count, count;
struct qla_hw_data *ha = vha->hw;
- int need_reset = 0, peg_stuck = 1;
+ int need_reset = 0;
need_reset = qla82xx_need_reset(ha);
- old_count = qla82xx_rd_32(ha, QLA82XX_PEG_ALIVE_COUNTER);
-
- for (i = 0; i < 10; i++) {
- timeout = msleep_interruptible(200);
- if (timeout) {
- qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE,
- QLA82XX_DEV_FAILED);
- return QLA_FUNCTION_FAILED;
- }
-
- count = qla82xx_rd_32(ha, QLA82XX_PEG_ALIVE_COUNTER);
- if (count != old_count)
- peg_stuck = 0;
- }
-
if (need_reset) {
/* We are trying to perform a recovery here. */
- if (peg_stuck)
+ if (ha->flags.isp82xx_fw_hung)
qla82xx_rom_lock_recovery(ha);
- goto dev_initialize;
} else {
- /* Start of day for this ha context. */
- if (peg_stuck) {
- /* Either we are the first or recovery in progress. */
- qla82xx_rom_lock_recovery(ha);
- goto dev_initialize;
- } else
- /* Firmware already running. */
- goto dev_ready;
+ old_count = qla82xx_rd_32(ha, QLA82XX_PEG_ALIVE_COUNTER);
+ for (i = 0; i < 10; i++) {
+ msleep(200);
+ count = qla82xx_rd_32(ha, QLA82XX_PEG_ALIVE_COUNTER);
+ if (count != old_count) {
+ rval = QLA_SUCCESS;
+ goto dev_ready;
+ }
+ }
+ qla82xx_rom_lock_recovery(ha);
}
- return rval;
-
-dev_initialize:
/* set to DEV_INITIALIZING */
ql_log(ql_log_info, vha, 0x009e,
"HW State: INITIALIZING.\n");
- qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE, QLA82XX_DEV_INITIALIZING);
-
- /* Driver that sets device state to initializating sets IDC version */
- qla82xx_wr_32(ha, QLA82XX_CRB_DRV_IDC_VERSION, QLA82XX_IDC_VERSION);
+ qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE, QLA8XXX_DEV_INITIALIZING);
qla82xx_idc_unlock(ha);
rval = qla82xx_start_firmware(vha);
@@ -2908,14 +2889,14 @@ dev_initialize:
ql_log(ql_log_fatal, vha, 0x00ad,
"HW State: FAILED.\n");
qla82xx_clear_drv_active(ha);
- qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE, QLA82XX_DEV_FAILED);
+ qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE, QLA8XXX_DEV_FAILED);
return rval;
}
dev_ready:
ql_log(ql_log_info, vha, 0x00ae,
"HW State: READY.\n");
- qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE, QLA82XX_DEV_READY);
+ qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE, QLA8XXX_DEV_READY);
return QLA_SUCCESS;
}
@@ -2939,7 +2920,7 @@ qla82xx_need_qsnt_handler(scsi_qla_host_t *vha)
if (vha->flags.online) {
/*Block any further I/O and wait for pending cmnds to complete*/
- qla82xx_quiescent_state_cleanup(vha);
+ qla2x00_quiesce_io(vha);
}
/* Set the quiescence ready bit */
@@ -2964,7 +2945,7 @@ qla82xx_need_qsnt_handler(scsi_qla_host_t *vha)
"DRV_STATE:%d.\n", QLA2XXX_DRIVER_NAME,
drv_active, drv_state);
qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE,
- QLA82XX_DEV_READY);
+ QLA8XXX_DEV_READY);
ql_log(ql_log_info, vha, 0xb025,
"HW State: DEV_READY.\n");
qla82xx_idc_unlock(ha);
@@ -2985,10 +2966,10 @@ qla82xx_need_qsnt_handler(scsi_qla_host_t *vha)
}
dev_state = qla82xx_rd_32(ha, QLA82XX_CRB_DEV_STATE);
/* everyone acked so set the state to DEV_QUIESCENCE */
- if (dev_state == QLA82XX_DEV_NEED_QUIESCENT) {
+ if (dev_state == QLA8XXX_DEV_NEED_QUIESCENT) {
ql_log(ql_log_info, vha, 0xb026,
"HW State: DEV_QUIESCENT.\n");
- qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE, QLA82XX_DEV_QUIESCENT);
+ qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE, QLA8XXX_DEV_QUIESCENT);
}
}
@@ -3018,8 +2999,8 @@ qla82xx_wait_for_state_change(scsi_qla_host_t *vha, uint32_t curr_state)
return dev_state;
}
-static void
-qla82xx_dev_failed_handler(scsi_qla_host_t *vha)
+void
+qla8xxx_dev_failed_handler(scsi_qla_host_t *vha)
{
struct qla_hw_data *ha = vha->hw;
@@ -3027,9 +3008,13 @@ qla82xx_dev_failed_handler(scsi_qla_host_t *vha)
ql_log(ql_log_fatal, vha, 0x00b8,
"Disabling the board.\n");
- qla82xx_idc_lock(ha);
- qla82xx_clear_drv_active(ha);
- qla82xx_idc_unlock(ha);
+ if (IS_QLA82XX(ha)) {
+ qla82xx_clear_drv_active(ha);
+ qla82xx_idc_unlock(ha);
+ } else if (IS_QLA8044(ha)) {
+ qla8044_clear_drv_active(ha);
+ qla8044_idc_unlock(ha);
+ }
/* Set DEV_FAILED flag to disable timer */
vha->device_flags |= DFLG_DEV_FAILED;
@@ -3068,7 +3053,7 @@ qla82xx_need_reset_handler(scsi_qla_host_t *vha)
}
drv_active = qla82xx_rd_32(ha, QLA82XX_CRB_DRV_ACTIVE);
- if (!ha->flags.isp82xx_reset_owner) {
+ if (!ha->flags.nic_core_reset_owner) {
ql_dbg(ql_dbg_p3p, vha, 0xb028,
"reset_acknowledged by 0x%x\n", ha->portnum);
qla82xx_set_rst_ready(ha);
@@ -3080,7 +3065,7 @@ qla82xx_need_reset_handler(scsi_qla_host_t *vha)
}
/* wait for 10 seconds for reset ack from all functions */
- reset_timeout = jiffies + (ha->nx_reset_timeout * HZ);
+ reset_timeout = jiffies + (ha->fcoe_reset_timeout * HZ);
drv_state = qla82xx_rd_32(ha, QLA82XX_CRB_DRV_STATE);
drv_active = qla82xx_rd_32(ha, QLA82XX_CRB_DRV_ACTIVE);
@@ -3092,7 +3077,7 @@ qla82xx_need_reset_handler(scsi_qla_host_t *vha)
drv_state, drv_active, dev_state, active_mask);
while (drv_state != drv_active &&
- dev_state != QLA82XX_DEV_INITIALIZING) {
+ dev_state != QLA8XXX_DEV_INITIALIZING) {
if (time_after_eq(jiffies, reset_timeout)) {
ql_log(ql_log_warn, vha, 0x00b5,
"Reset timeout.\n");
@@ -3103,7 +3088,7 @@ qla82xx_need_reset_handler(scsi_qla_host_t *vha)
qla82xx_idc_lock(ha);
drv_state = qla82xx_rd_32(ha, QLA82XX_CRB_DRV_STATE);
drv_active = qla82xx_rd_32(ha, QLA82XX_CRB_DRV_ACTIVE);
- if (ha->flags.isp82xx_reset_owner)
+ if (ha->flags.nic_core_reset_owner)
drv_active &= active_mask;
dev_state = qla82xx_rd_32(ha, QLA82XX_CRB_DEV_STATE);
}
@@ -3119,11 +3104,11 @@ qla82xx_need_reset_handler(scsi_qla_host_t *vha)
dev_state < MAX_STATES ? qdev_state(dev_state) : "Unknown");
/* Force to DEV_COLD unless someone else is starting a reset */
- if (dev_state != QLA82XX_DEV_INITIALIZING &&
- dev_state != QLA82XX_DEV_COLD) {
+ if (dev_state != QLA8XXX_DEV_INITIALIZING &&
+ dev_state != QLA8XXX_DEV_COLD) {
ql_log(ql_log_info, vha, 0x00b7,
"HW State: COLD/RE-INIT.\n");
- qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE, QLA82XX_DEV_COLD);
+ qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE, QLA8XXX_DEV_COLD);
qla82xx_set_rst_ready(ha);
if (ql2xmdenable) {
if (qla82xx_md_collect(vha))
@@ -3152,18 +3137,18 @@ qla82xx_check_md_needed(scsi_qla_host_t *vha)
if (ql2xmdenable) {
if (!ha->fw_dumped) {
- if (fw_major_version != ha->fw_major_version ||
+ if ((fw_major_version != ha->fw_major_version ||
fw_minor_version != ha->fw_minor_version ||
- fw_subminor_version != ha->fw_subminor_version) {
- ql_log(ql_log_info, vha, 0xb02d,
- "Firmware version differs "
- "Previous version: %d:%d:%d - "
- "New version: %d:%d:%d\n",
+ fw_subminor_version != ha->fw_subminor_version) ||
+ (ha->prev_minidump_failed)) {
+ ql_dbg(ql_dbg_p3p, vha, 0xb02d,
+ "Firmware version differs Previous version: %d:%d:%d - New version: %d:%d:%d, prev_minidump_failed: %d.\n",
fw_major_version, fw_minor_version,
fw_subminor_version,
ha->fw_major_version,
ha->fw_minor_version,
- ha->fw_subminor_version);
+ ha->fw_subminor_version,
+ ha->prev_minidump_failed);
/* Release MiniDump resources */
qla82xx_md_free(vha);
/* ALlocate MiniDump resources */
@@ -3177,7 +3162,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;
@@ -3230,8 +3215,10 @@ qla82xx_device_state_handler(scsi_qla_host_t *vha)
int loopcount = 0;
qla82xx_idc_lock(ha);
- if (!vha->flags.init_done)
+ if (!vha->flags.init_done) {
qla82xx_set_drv_active(vha);
+ qla82xx_set_idc_version(vha);
+ }
dev_state = qla82xx_rd_32(ha, QLA82XX_CRB_DEV_STATE);
old_dev_state = dev_state;
@@ -3241,7 +3228,7 @@ qla82xx_device_state_handler(scsi_qla_host_t *vha)
dev_state < MAX_STATES ? qdev_state(dev_state) : "Unknown");
/* wait for 30 seconds for device to go ready */
- dev_init_timeout = jiffies + (ha->nx_dev_init_timeout * HZ);
+ dev_init_timeout = jiffies + (ha->fcoe_dev_init_timeout * HZ);
while (1) {
@@ -3265,18 +3252,18 @@ qla82xx_device_state_handler(scsi_qla_host_t *vha)
}
switch (dev_state) {
- case QLA82XX_DEV_READY:
- ha->flags.isp82xx_reset_owner = 0;
- goto exit;
- case QLA82XX_DEV_COLD:
+ case QLA8XXX_DEV_READY:
+ ha->flags.nic_core_reset_owner = 0;
+ goto rel_lock;
+ case QLA8XXX_DEV_COLD:
rval = qla82xx_device_bootstrap(vha);
break;
- case QLA82XX_DEV_INITIALIZING:
+ case QLA8XXX_DEV_INITIALIZING:
qla82xx_idc_unlock(ha);
msleep(1000);
qla82xx_idc_lock(ha);
break;
- case QLA82XX_DEV_NEED_RESET:
+ case QLA8XXX_DEV_NEED_RESET:
if (!ql2xdontresethba)
qla82xx_need_reset_handler(vha);
else {
@@ -3285,31 +3272,31 @@ qla82xx_device_state_handler(scsi_qla_host_t *vha)
qla82xx_idc_lock(ha);
}
dev_init_timeout = jiffies +
- (ha->nx_dev_init_timeout * HZ);
+ (ha->fcoe_dev_init_timeout * HZ);
break;
- case QLA82XX_DEV_NEED_QUIESCENT:
+ case QLA8XXX_DEV_NEED_QUIESCENT:
qla82xx_need_qsnt_handler(vha);
/* Reset timeout value after quiescence handler */
- dev_init_timeout = jiffies + (ha->nx_dev_init_timeout\
+ dev_init_timeout = jiffies + (ha->fcoe_dev_init_timeout\
* HZ);
break;
- case QLA82XX_DEV_QUIESCENT:
+ case QLA8XXX_DEV_QUIESCENT:
/* Owner will exit and other will wait for the state
* to get changed
*/
if (ha->flags.quiesce_owner)
- goto exit;
+ goto rel_lock;
qla82xx_idc_unlock(ha);
msleep(1000);
qla82xx_idc_lock(ha);
/* Reset timeout value after quiescence handler */
- dev_init_timeout = jiffies + (ha->nx_dev_init_timeout\
+ dev_init_timeout = jiffies + (ha->fcoe_dev_init_timeout\
* HZ);
break;
- case QLA82XX_DEV_FAILED:
- qla82xx_dev_failed_handler(vha);
+ case QLA8XXX_DEV_FAILED:
+ qla8xxx_dev_failed_handler(vha);
rval = QLA_FUNCTION_FAILED;
goto exit;
default:
@@ -3319,8 +3306,9 @@ qla82xx_device_state_handler(scsi_qla_host_t *vha)
}
loopcount++;
}
-exit:
+rel_lock:
qla82xx_idc_unlock(ha);
+exit:
return rval;
}
@@ -3348,6 +3336,14 @@ static int qla82xx_check_temp(scsi_qla_host_t *vha)
return 0;
}
+int qla82xx_read_temperature(scsi_qla_host_t *vha)
+{
+ uint32_t temp;
+
+ temp = qla82xx_rd_32(vha->hw, CRB_TEMP_STATE);
+ return qla82xx_get_temp_val(temp);
+}
+
void qla82xx_clear_pending_mbx(scsi_qla_host_t *vha)
{
struct qla_hw_data *ha = vha->hw;
@@ -3357,7 +3353,7 @@ void qla82xx_clear_pending_mbx(scsi_qla_host_t *vha)
ha->flags.mbox_busy = 0;
ql_log(ql_log_warn, vha, 0x6010,
"Doing premature completion of mbx command.\n");
- if (test_bit(MBX_INTR_WAIT, &ha->mbx_cmd_flags))
+ if (test_and_clear_bit(MBX_INTR_WAIT, &ha->mbx_cmd_flags))
complete(&ha->mbx_intr_comp);
}
}
@@ -3368,22 +3364,30 @@ void qla82xx_watchdog(scsi_qla_host_t *vha)
struct qla_hw_data *ha = vha->hw;
/* don't poll if reset is going on */
- if (!ha->flags.isp82xx_reset_hdlr_active) {
+ if (!ha->flags.nic_core_reset_hdlr_active) {
dev_state = qla82xx_rd_32(ha, QLA82XX_CRB_DEV_STATE);
if (qla82xx_check_temp(vha)) {
set_bit(ISP_UNRECOVERABLE, &vha->dpc_flags);
ha->flags.isp82xx_fw_hung = 1;
qla82xx_clear_pending_mbx(vha);
- } else if (dev_state == QLA82XX_DEV_NEED_RESET &&
+ } else if (dev_state == QLA8XXX_DEV_NEED_RESET &&
!test_bit(ISP_ABORT_NEEDED, &vha->dpc_flags)) {
ql_log(ql_log_warn, vha, 0x6001,
"Adapter reset needed.\n");
set_bit(ISP_ABORT_NEEDED, &vha->dpc_flags);
- } else if (dev_state == QLA82XX_DEV_NEED_QUIESCENT &&
+ } else if (dev_state == QLA8XXX_DEV_NEED_QUIESCENT &&
!test_bit(ISP_QUIESCE_NEEDED, &vha->dpc_flags)) {
ql_log(ql_log_warn, vha, 0x6002,
"Quiescent needed.\n");
set_bit(ISP_QUIESCE_NEEDED, &vha->dpc_flags);
+ } else if (dev_state == QLA8XXX_DEV_FAILED &&
+ !test_bit(ISP_UNRECOVERABLE, &vha->dpc_flags) &&
+ vha->flags.online == 1) {
+ ql_log(ql_log_warn, vha, 0xb055,
+ "Adapter state is failed. Offlining.\n");
+ set_bit(ISP_UNRECOVERABLE, &vha->dpc_flags);
+ ha->flags.isp82xx_fw_hung = 1;
+ qla82xx_clear_pending_mbx(vha);
} else {
if (qla82xx_check_fw_alive(vha)) {
ql_dbg(ql_dbg_timer, vha, 0x6011,
@@ -3433,8 +3437,18 @@ void qla82xx_watchdog(scsi_qla_host_t *vha)
int qla82xx_load_risc(scsi_qla_host_t *vha, uint32_t *srisc_addr)
{
- int rval;
- rval = qla82xx_device_state_handler(vha);
+ int rval = -1;
+ struct qla_hw_data *ha = vha->hw;
+
+ if (IS_QLA82XX(ha))
+ rval = qla82xx_device_state_handler(vha);
+ else if (IS_QLA8044(ha)) {
+ qla8044_idc_lock(ha);
+ /* Decide the reset ownership */
+ qla83xx_reset_ownership(vha);
+ qla8044_idc_unlock(ha);
+ rval = qla8044_device_state_handler(vha);
+ }
return rval;
}
@@ -3442,17 +3456,25 @@ void
qla82xx_set_reset_owner(scsi_qla_host_t *vha)
{
struct qla_hw_data *ha = vha->hw;
- uint32_t dev_state;
+ uint32_t dev_state = 0;
- dev_state = qla82xx_rd_32(ha, QLA82XX_CRB_DEV_STATE);
- if (dev_state == QLA82XX_DEV_READY) {
+ if (IS_QLA82XX(ha))
+ dev_state = qla82xx_rd_32(ha, QLA82XX_CRB_DEV_STATE);
+ else if (IS_QLA8044(ha))
+ dev_state = qla8044_rd_direct(vha, QLA8044_CRB_DEV_STATE_INDEX);
+
+ if (dev_state == QLA8XXX_DEV_READY) {
ql_log(ql_log_info, vha, 0xb02f,
"HW State: NEED RESET\n");
- qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE,
- QLA82XX_DEV_NEED_RESET);
- ha->flags.isp82xx_reset_owner = 1;
- ql_dbg(ql_dbg_p3p, vha, 0xb030,
- "reset_owner is 0x%x\n", ha->portnum);
+ if (IS_QLA82XX(ha)) {
+ qla82xx_wr_32(ha, QLA82XX_CRB_DEV_STATE,
+ QLA8XXX_DEV_NEED_RESET);
+ ha->flags.nic_core_reset_owner = 1;
+ ql_dbg(ql_dbg_p3p, vha, 0xb030,
+ "reset_owner is 0x%x\n", ha->portnum);
+ } else if (IS_QLA8044(ha))
+ qla8044_wr_direct(vha, QLA8044_CRB_DEV_STATE_INDEX,
+ QLA8XXX_DEV_NEED_RESET);
} else
ql_log(ql_log_info, vha, 0xb031,
"Device state is 0x%x = %s.\n",
@@ -3473,7 +3495,7 @@ qla82xx_set_reset_owner(scsi_qla_host_t *vha)
int
qla82xx_abort_isp(scsi_qla_host_t *vha)
{
- int rval;
+ int rval = -1;
struct qla_hw_data *ha = vha->hw;
if (vha->device_flags & DFLG_DEV_FAILED) {
@@ -3481,13 +3503,21 @@ qla82xx_abort_isp(scsi_qla_host_t *vha)
"Device in failed state, exiting.\n");
return QLA_SUCCESS;
}
- ha->flags.isp82xx_reset_hdlr_active = 1;
+ ha->flags.nic_core_reset_hdlr_active = 1;
qla82xx_idc_lock(ha);
qla82xx_set_reset_owner(vha);
qla82xx_idc_unlock(ha);
- rval = qla82xx_device_state_handler(vha);
+ if (IS_QLA82XX(ha))
+ rval = qla82xx_device_state_handler(vha);
+ else if (IS_QLA8044(ha)) {
+ qla8044_idc_lock(ha);
+ /* Decide the reset ownership */
+ qla83xx_reset_ownership(vha);
+ qla8044_idc_unlock(ha);
+ rval = qla8044_device_state_handler(vha);
+ }
qla82xx_idc_lock(ha);
qla82xx_clear_rst_ready(ha);
@@ -3495,7 +3525,7 @@ qla82xx_abort_isp(scsi_qla_host_t *vha)
if (rval == QLA_SUCCESS) {
ha->flags.isp82xx_fw_hung = 0;
- ha->flags.isp82xx_reset_hdlr_active = 0;
+ ha->flags.nic_core_reset_hdlr_active = 0;
qla82xx_restart_isp(vha);
}
@@ -3607,7 +3637,7 @@ int qla2x00_wait_for_fcoe_ctx_reset(scsi_qla_host_t *vha)
void
qla82xx_chip_reset_cleanup(scsi_qla_host_t *vha)
{
- int i;
+ int i, fw_state = 0;
unsigned long flags;
struct qla_hw_data *ha = vha->hw;
@@ -3618,7 +3648,11 @@ qla82xx_chip_reset_cleanup(scsi_qla_host_t *vha)
if (!ha->flags.isp82xx_fw_hung) {
for (i = 0; i < 2; i++) {
msleep(1000);
- if (qla82xx_check_fw_alive(vha)) {
+ if (IS_QLA82XX(ha))
+ fw_state = qla82xx_check_fw_alive(vha);
+ else if (IS_QLA8044(ha))
+ fw_state = qla8044_check_fw_alive(vha);
+ if (fw_state) {
ha->flags.isp82xx_fw_hung = 1;
qla82xx_clear_pending_mbx(vha);
break;
@@ -3640,11 +3674,13 @@ qla82xx_chip_reset_cleanup(scsi_qla_host_t *vha)
req = ha->req_q_map[que];
if (!req)
continue;
- for (cnt = 1; cnt < MAX_OUTSTANDING_COMMANDS; cnt++) {
+ for (cnt = 1; cnt < req->num_outstanding_cmds; cnt++) {
sp = req->outstanding_cmds[cnt];
if (sp) {
- if (!sp->u.scmd.ctx ||
- (sp->flags & SRB_FCP_CMND_DMA_VALID)) {
+ if ((!sp->u.scmd.ctx ||
+ (sp->flags &
+ SRB_FCP_CMND_DMA_VALID)) &&
+ !ha->flags.isp82xx_fw_hung) {
spin_unlock_irqrestore(
&ha->hardware_lock, flags);
if (ha->isp_ops->abort_command(sp)) {
@@ -3806,7 +3842,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;
}
@@ -4030,7 +4067,7 @@ qla82xx_minidump_process_rdmem(scsi_qla_host_t *vha,
if (r_addr & 0xf) {
ql_log(ql_log_warn, vha, 0xb033,
- "Read addr 0x%x not 16 bytes alligned\n", r_addr);
+ "Read addr 0x%x not 16 bytes aligned\n", r_addr);
return rval;
}
@@ -4081,7 +4118,7 @@ qla82xx_minidump_process_rdmem(scsi_qla_host_t *vha,
return QLA_SUCCESS;
}
-static int
+int
qla82xx_validate_template_chksum(scsi_qla_host_t *vha)
{
struct qla_hw_data *ha = vha->hw;
@@ -4365,7 +4402,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 */
@@ -4375,7 +4412,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;
}
}
@@ -4393,7 +4430,11 @@ qla82xx_md_prep(scsi_qla_host_t *vha)
ha->md_template_size / 1024);
/* Get Minidump template */
- rval = qla82xx_md_get_template(vha);
+ if (IS_QLA8044(ha))
+ rval = qla8044_md_get_template(vha);
+ else
+ rval = qla82xx_md_get_template(vha);
+
if (rval == QLA_SUCCESS) {
ql_dbg(ql_dbg_p3p, vha, 0xb04b,
"MiniDump Template obtained\n");
@@ -4412,7 +4453,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;
}
}
@@ -4458,3 +4499,20 @@ exit:
qla82xx_idc_unlock(ha);
return rval;
}
+
+void
+qla82xx_fw_dump(scsi_qla_host_t *vha, int hardware_locked)
+{
+ struct qla_hw_data *ha = vha->hw;
+
+ if (!ha->allow_cna_fw_dump)
+ return;
+
+ scsi_block_requests(vha->host);
+ ha->flags.isp82xx_no_md_cap = 1;
+ qla82xx_idc_lock(ha);
+ qla82xx_set_reset_owner(vha);
+ qla82xx_idc_unlock(ha);
+ qla2x00_wait_for_chip_reset(vha);
+ scsi_unblock_requests(vha->host);
+}