[PATCH 1/1] scsi: scsi_dh_alua: remove the list entry before assigning the pointer and sdev to NULL

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



A race exists where the BUG_ON(!h->sdev) will fire if the detach device handler
from one thread runs removing a list entry while another thread is trying to
evaluate the target portal group state.

The order of the detach operation is now changed to delete the list entry
before modifying the pointer and setting h->sdev to NULL.

Signed-off-by: Brian Bunker <brian@xxxxxxxxxxxxxxx>
Acked-by: Krishna Kant <krishna.kant@xxxxxxxxxxxxxxx>
___
diff -Naur a/scsi/drivers/scsi/device_handler/scsi_dh_alua.c b/scsi/drivers/scsi/device_handler/scsi_dh_alua.c
--- a/scsi/drivers/scsi/device_handler/scsi_dh_alua.c	2020-09-10 12:29:03.000000000 -0700
+++ b/scsi/drivers/scsi/device_handler/scsi_dh_alua.c	2020-09-10 12:41:34.000000000 -0700
@@ -1146,16 +1146,18 @@

 	spin_lock(&h->pg_lock);
 	pg = rcu_dereference_protected(h->pg, lockdep_is_held(&h->pg_lock));
-	rcu_assign_pointer(h->pg, NULL);
-	h->sdev = NULL;
-	spin_unlock(&h->pg_lock);
 	if (pg) {
 		spin_lock_irq(&pg->lock);
 		list_del_rcu(&h->node);
 		spin_unlock_irq(&pg->lock);
-		kref_put(&pg->kref, release_port_group);
 	}
+	rcu_assign_pointer(h->pg, NULL);
+	h->sdev = NULL;
+	spin_unlock(&h->pg_lock);
 	sdev->handler_data = NULL;
+	if (pg) {
+		kref_put(&pg->kref, release_port_group);
+	}
 	kfree(h);
 }



[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Index of Archives]     [SCSI Target Devel]     [Linux SCSI Target Infrastructure]     [Kernel Newbies]     [IDE]     [Security]     [Git]     [Netfilter]     [Bugtraq]     [Yosemite News]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux ATA RAID]     [Linux IIO]     [Samba]     [Device Mapper]

  Powered by Linux