diff options
| author | nagalakshmi.nandigama@lsi.com <nagalakshmi.nandigama@lsi.com> | 2011-10-19 15:37:14 +0530 | 
|---|---|---|
| committer | James Bottomley <JBottomley@Parallels.com> | 2011-10-30 12:53:45 +0400 | 
| commit | f3db032f1af6dd3280037ea526fee7cddcc36c41 (patch) | |
| tree | 3e81bec7fcc23e0f4bb8b795f3f003d0b5f530aa /drivers/scsi/mpt2sas/mpt2sas_scsih.c | |
| parent | f881ceadd4d6afafb227bcf8165c1b63ba90065b (diff) | |
| download | olio-linux-3.10-f3db032f1af6dd3280037ea526fee7cddcc36c41.tar.xz olio-linux-3.10-f3db032f1af6dd3280037ea526fee7cddcc36c41.zip  | |
[SCSI] mpt2sas: Fix for dead lock occurring between host_lock and sas_device_lock
Fix for dead lock occurring between host_lock and sas_device_lock.
The deadlock is between two spin locks, between the shost->host_lock
and driver ioc->sas_device_lock.
The fix is to rearrange the code in the  FW/Driver device removal
handshake so the ioc->sas_device_lock is not occurring when the
shost->host_lock is taken.
[jejb: zero initialise sas_address to fix spurious compiler warning]
Signed-off-by: Nagalakshmi Nandigama <nagalakshmi.nandigama@lsi.com>
Signed-off-by: James Bottomley <JBottomley@Parallels.com>
Diffstat (limited to 'drivers/scsi/mpt2sas/mpt2sas_scsih.c')
| -rw-r--r-- | drivers/scsi/mpt2sas/mpt2sas_scsih.c | 15 | 
1 files changed, 10 insertions, 5 deletions
diff --git a/drivers/scsi/mpt2sas/mpt2sas_scsih.c b/drivers/scsi/mpt2sas/mpt2sas_scsih.c index cd89f42440f..f9ce3195031 100644 --- a/drivers/scsi/mpt2sas/mpt2sas_scsih.c +++ b/drivers/scsi/mpt2sas/mpt2sas_scsih.c @@ -3016,7 +3016,8 @@ _scsih_tm_tr_send(struct MPT2SAS_ADAPTER *ioc, u16 handle)  	Mpi2SCSITaskManagementRequest_t *mpi_request;  	u16 smid;  	struct _sas_device *sas_device; -	struct MPT2SAS_TARGET *sas_target_priv_data; +	struct MPT2SAS_TARGET *sas_target_priv_data = NULL; +	u64 sas_address = 0;  	unsigned long flags;  	struct _tr_list *delayed_tr;  	u32 ioc_state; @@ -3049,13 +3050,17 @@ _scsih_tm_tr_send(struct MPT2SAS_ADAPTER *ioc, u16 handle)  	     sas_device->starget->hostdata) {  		sas_target_priv_data = sas_device->starget->hostdata;  		sas_target_priv_data->deleted = 1; -		dewtprintk(ioc, printk(MPT2SAS_INFO_FMT -		    "setting delete flag: handle(0x%04x), " -		    "sas_addr(0x%016llx)\n", ioc->name, handle, -		    (unsigned long long) sas_device->sas_address)); +		sas_address = sas_device->sas_address;  	}  	spin_unlock_irqrestore(&ioc->sas_device_lock, flags); +	if (sas_target_priv_data) { +		dewtprintk(ioc, printk(MPT2SAS_INFO_FMT "setting delete flag: " +		"handle(0x%04x), sas_addr(0x%016llx)\n", ioc->name, handle, +			(unsigned long long)sas_address)); +		_scsih_ublock_io_device(ioc, handle); +	} +  	smid = mpt2sas_base_get_smid_hpr(ioc, ioc->tm_tr_cb_idx);  	if (!smid) {  		delayed_tr = kzalloc(sizeof(*delayed_tr), GFP_ATOMIC);  |