summaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorVikas Chaudhary <vikas.chaudhary@qlogic.com>2013-12-16 12:49:45 +0100
committerJames Bottomley <JBottomley@Parallels.com>2014-03-15 18:19:14 +0100
commit4ebbb5cf640c5240cafde732c56fe24a5514bf8d (patch)
tree9a588617ff7978c2ded8e777feb85c4cd6d473c5 /drivers
parent[SCSI] qla4xxx: Driver not able to collect minidump for ISP84xx (diff)
downloadlinux-4ebbb5cf640c5240cafde732c56fe24a5514bf8d.tar.xz
linux-4ebbb5cf640c5240cafde732c56fe24a5514bf8d.zip
[SCSI] qla4xxx: Reduce rom-lock contention during reset recovery.
Issue: Driver holds rom-lock for too long during reset recovery. During adapter reset testing, it was found that the driver holds the rom-lock for too long, because of which other drivers fail to acquire the rom-lock, leading to reset failures. The primary cause is, in the bootstrap code, while holding the rom-lock, the driver checks if the peg is halted, causing a 2 second contention. Fix: When a reset recovery starts, the driver deduces the cause, and sets appropriate flags in watchdog & recover_adapter routines. This flag should be used to determine if bootstrap is invoked from probe or reset context, reducing the rom-lock footprint of the drivers. Signed-off-by: Vikas Chaudhary <vikas.chaudhary@qlogic.com> Reviewed-by: Mike Christie <michaelc@cs.wisc.edu> Signed-off-by: James Bottomley <JBottomley@Parallels.com>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/scsi/qla4xxx/ql4_nx.c33
1 files changed, 12 insertions, 21 deletions
diff --git a/drivers/scsi/qla4xxx/ql4_nx.c b/drivers/scsi/qla4xxx/ql4_nx.c
index d2040b49120a..63328c812b70 100644
--- a/drivers/scsi/qla4xxx/ql4_nx.c
+++ b/drivers/scsi/qla4xxx/ql4_nx.c
@@ -2828,37 +2828,28 @@ int qla4_8xxx_device_bootstrap(struct scsi_qla_host *ha)
int rval = QLA_ERROR;
int i;
uint32_t old_count, count;
- int need_reset = 0, peg_stuck = 1;
+ int need_reset = 0;
need_reset = ha->isp_ops->need_reset(ha);
- old_count = qla4_8xxx_rd_direct(ha, QLA8XXX_PEG_ALIVE_COUNTER);
-
- for (i = 0; i < 10; i++) {
- msleep(200);
- count = qla4_8xxx_rd_direct(ha, QLA8XXX_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 (test_bit(AF_FW_RECOVERY, &ha->flags))
ha->isp_ops->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. */
- ha->isp_ops->rom_lock_recovery(ha);
- goto dev_initialize;
- } else {
- /* Firmware already running. */
- rval = QLA_SUCCESS;
- goto dev_ready;
+ old_count = qla4_8xxx_rd_direct(ha, QLA8XXX_PEG_ALIVE_COUNTER);
+ for (i = 0; i < 10; i++) {
+ msleep(200);
+ count = qla4_8xxx_rd_direct(ha,
+ QLA8XXX_PEG_ALIVE_COUNTER);
+ if (count != old_count) {
+ rval = QLA_SUCCESS;
+ goto dev_ready;
+ }
}
+ ha->isp_ops->rom_lock_recovery(ha);
}
-dev_initialize:
/* set to DEV_INITIALIZING */
ql4_printk(KERN_INFO, ha, "HW State: INITIALIZING\n");
qla4_8xxx_wr_direct(ha, QLA8XXX_CRB_DEV_STATE,