summaryrefslogtreecommitdiffstats
path: root/drivers/scsi/mpt3sas/mpt3sas_transport.c
diff options
context:
space:
mode:
authorSreekanth Reddy2015-11-11 13:00:30 +0100
committerMartin K. Petersen2015-11-12 00:57:38 +0100
commitd1cb5e495e5384f6d90a8573f1be9cc79b85c862 (patch)
tree1600d3477752a7f90e2e8812a80eef0511393d4d /drivers/scsi/mpt3sas/mpt3sas_transport.c
parentmpt3sas: sysfs attribute to report Backup Rail Monitor Status (diff)
downloadkernel-qcow2-linux-d1cb5e495e5384f6d90a8573f1be9cc79b85c862.tar.gz
kernel-qcow2-linux-d1cb5e495e5384f6d90a8573f1be9cc79b85c862.tar.xz
kernel-qcow2-linux-d1cb5e495e5384f6d90a8573f1be9cc79b85c862.zip
mpt3sas: Refcount sas_device objects and fix unsafe list usage
sas_device objects can be referenced concurrently throughout the driver. We need a way to make sure threads can't delete them out from under each other. This patch adds the refcount and refactors the code to use it. Additionally, we cannot iterate over the sas_device_list without holding the lock or we risk corrupting random memory if items are added or deleted as we iterate. This patch refactors _scsih_probe_sas() to use the sas_device_list in a safe way. This patch is ported from the following mpt2sas driver commit d224fe0d6097 ("mpt2sas: Refcount sas_device objects and fix unsafe list usage"). Signed-off-by: Sreekanth Reddy <Sreekanth.Reddy@avagotech.com> Acked-by: Christoph Hellwig <hch@lst.de> Reviewed-by: Hannes Reinecke <hare@suse.de> Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
Diffstat (limited to 'drivers/scsi/mpt3sas/mpt3sas_transport.c')
-rw-r--r--drivers/scsi/mpt3sas/mpt3sas_transport.c18
1 files changed, 12 insertions, 6 deletions
diff --git a/drivers/scsi/mpt3sas/mpt3sas_transport.c b/drivers/scsi/mpt3sas/mpt3sas_transport.c
index 70fd019e7ee5..ca36d7ea0964 100644
--- a/drivers/scsi/mpt3sas/mpt3sas_transport.c
+++ b/drivers/scsi/mpt3sas/mpt3sas_transport.c
@@ -734,7 +734,7 @@ mpt3sas_transport_port_add(struct MPT3SAS_ADAPTER *ioc, u16 handle,
rphy->identify = mpt3sas_port->remote_identify;
if (mpt3sas_port->remote_identify.device_type == SAS_END_DEVICE) {
- sas_device = mpt3sas_scsih_sas_device_find_by_sas_address(ioc,
+ sas_device = mpt3sas_get_sdev_by_addr(ioc,
mpt3sas_port->remote_identify.sas_address);
if (!sas_device) {
dfailprintk(ioc, printk(MPT3SAS_FMT
@@ -750,8 +750,10 @@ mpt3sas_transport_port_add(struct MPT3SAS_ADAPTER *ioc, u16 handle,
ioc->name, __FILE__, __LINE__, __func__);
}
- if (mpt3sas_port->remote_identify.device_type == SAS_END_DEVICE)
+ if (mpt3sas_port->remote_identify.device_type == SAS_END_DEVICE) {
sas_device->pend_sas_rphy_add = 0;
+ sas_device_put(sas_device);
+ }
if ((ioc->logging_level & MPT_DEBUG_TRANSPORT))
dev_printk(KERN_INFO, &rphy->dev,
@@ -1324,15 +1326,17 @@ _transport_get_enclosure_identifier(struct sas_rphy *rphy, u64 *identifier)
int rc;
spin_lock_irqsave(&ioc->sas_device_lock, flags);
- sas_device = mpt3sas_scsih_sas_device_find_by_sas_address(ioc,
+ sas_device = __mpt3sas_get_sdev_by_addr(ioc,
rphy->identify.sas_address);
if (sas_device) {
*identifier = sas_device->enclosure_logical_id;
rc = 0;
+ sas_device_put(sas_device);
} else {
*identifier = 0;
rc = -ENXIO;
}
+
spin_unlock_irqrestore(&ioc->sas_device_lock, flags);
return rc;
}
@@ -1352,12 +1356,14 @@ _transport_get_bay_identifier(struct sas_rphy *rphy)
int rc;
spin_lock_irqsave(&ioc->sas_device_lock, flags);
- sas_device = mpt3sas_scsih_sas_device_find_by_sas_address(ioc,
+ sas_device = __mpt3sas_get_sdev_by_addr(ioc,
rphy->identify.sas_address);
- if (sas_device)
+ if (sas_device) {
rc = sas_device->slot;
- else
+ sas_device_put(sas_device);
+ } else {
rc = -ENXIO;
+ }
spin_unlock_irqrestore(&ioc->sas_device_lock, flags);
return rc;
}