mirror of
https://github.com/torvalds/linux.git
synced 2024-11-19 10:31:48 +00:00
[SCSI] qla4xxx: Fix failure of mbox 0x31
Issue: While unloading driver MBOX 0x31 fail as DDB logout (MBOX 0x56) operation is not completed. Fix: Wait for DDB Logout completion before MBOX 0x31 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>
This commit is contained in:
parent
4ebbb5cf64
commit
28d958bad8
@ -8886,10 +8886,56 @@ static void qla4xxx_prevent_other_port_reinit(struct scsi_qla_host *ha)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void qla4xxx_destroy_ddb(struct scsi_qla_host *ha,
|
||||||
|
struct ddb_entry *ddb_entry)
|
||||||
|
{
|
||||||
|
struct dev_db_entry *fw_ddb_entry = NULL;
|
||||||
|
dma_addr_t fw_ddb_entry_dma;
|
||||||
|
unsigned long wtime;
|
||||||
|
uint32_t ddb_state;
|
||||||
|
int options;
|
||||||
|
int status;
|
||||||
|
|
||||||
|
options = LOGOUT_OPTION_CLOSE_SESSION;
|
||||||
|
if (qla4xxx_session_logout_ddb(ha, ddb_entry, options) == QLA_ERROR) {
|
||||||
|
ql4_printk(KERN_ERR, ha, "%s: Logout failed\n", __func__);
|
||||||
|
goto clear_ddb;
|
||||||
|
}
|
||||||
|
|
||||||
|
fw_ddb_entry = dma_alloc_coherent(&ha->pdev->dev, sizeof(*fw_ddb_entry),
|
||||||
|
&fw_ddb_entry_dma, GFP_KERNEL);
|
||||||
|
if (!fw_ddb_entry) {
|
||||||
|
ql4_printk(KERN_ERR, ha,
|
||||||
|
"%s: Unable to allocate dma buffer\n", __func__);
|
||||||
|
goto clear_ddb;
|
||||||
|
}
|
||||||
|
|
||||||
|
wtime = jiffies + (HZ * LOGOUT_TOV);
|
||||||
|
do {
|
||||||
|
status = qla4xxx_get_fwddb_entry(ha, ddb_entry->fw_ddb_index,
|
||||||
|
fw_ddb_entry, fw_ddb_entry_dma,
|
||||||
|
NULL, NULL, &ddb_state, NULL,
|
||||||
|
NULL, NULL);
|
||||||
|
if (status == QLA_ERROR)
|
||||||
|
goto free_ddb;
|
||||||
|
|
||||||
|
if ((ddb_state == DDB_DS_NO_CONNECTION_ACTIVE) ||
|
||||||
|
(ddb_state == DDB_DS_SESSION_FAILED))
|
||||||
|
goto free_ddb;
|
||||||
|
|
||||||
|
schedule_timeout_uninterruptible(HZ);
|
||||||
|
} while ((time_after(wtime, jiffies)));
|
||||||
|
|
||||||
|
free_ddb:
|
||||||
|
dma_free_coherent(&ha->pdev->dev, sizeof(*fw_ddb_entry),
|
||||||
|
fw_ddb_entry, fw_ddb_entry_dma);
|
||||||
|
clear_ddb:
|
||||||
|
qla4xxx_clear_ddb_entry(ha, ddb_entry->fw_ddb_index);
|
||||||
|
}
|
||||||
|
|
||||||
static void qla4xxx_destroy_fw_ddb_session(struct scsi_qla_host *ha)
|
static void qla4xxx_destroy_fw_ddb_session(struct scsi_qla_host *ha)
|
||||||
{
|
{
|
||||||
struct ddb_entry *ddb_entry;
|
struct ddb_entry *ddb_entry;
|
||||||
int options;
|
|
||||||
int idx;
|
int idx;
|
||||||
|
|
||||||
for (idx = 0; idx < MAX_DDB_ENTRIES; idx++) {
|
for (idx = 0; idx < MAX_DDB_ENTRIES; idx++) {
|
||||||
@ -8898,13 +8944,7 @@ static void qla4xxx_destroy_fw_ddb_session(struct scsi_qla_host *ha)
|
|||||||
if ((ddb_entry != NULL) &&
|
if ((ddb_entry != NULL) &&
|
||||||
(ddb_entry->ddb_type == FLASH_DDB)) {
|
(ddb_entry->ddb_type == FLASH_DDB)) {
|
||||||
|
|
||||||
options = LOGOUT_OPTION_CLOSE_SESSION;
|
qla4xxx_destroy_ddb(ha, ddb_entry);
|
||||||
if (qla4xxx_session_logout_ddb(ha, ddb_entry, options)
|
|
||||||
== QLA_ERROR)
|
|
||||||
ql4_printk(KERN_ERR, ha, "%s: Logout failed\n",
|
|
||||||
__func__);
|
|
||||||
|
|
||||||
qla4xxx_clear_ddb_entry(ha, ddb_entry->fw_ddb_index);
|
|
||||||
/*
|
/*
|
||||||
* we have decremented the reference count of the driver
|
* we have decremented the reference count of the driver
|
||||||
* when we setup the session to have the driver unload
|
* when we setup the session to have the driver unload
|
||||||
|
Loading…
Reference in New Issue
Block a user