[SCSI] zfcp: Remove SCSI device when removing unit
authorChristof Schmitt <christof.schmitt@de.ibm.com>
Fri, 16 Jul 2010 13:37:35 +0000 (15:37 +0200)
committerJames Bottomley <James.Bottomley@suse.de>
Wed, 28 Jul 2010 14:48:46 +0000 (09:48 -0500)
Configuring a LUN in zfcp, also creates a SCSI device. For
consistency, it makes sense to remove the SCSI device when the LUN is
deconfigured. Replace the flush_work with the call to
scsi_remove_device: scsi_remove_device also takes the scan_mutex that
synchronizes itself with any long running device discovery.

Reviewed-by: Swen Schillig <swen@vnet.ibm.com>
Signed-off-by: Christof Schmitt <christof.schmitt@de.ibm.com>
Signed-off-by: James Bottomley <James.Bottomley@suse.de>
drivers/s390/scsi/zfcp_def.h
drivers/s390/scsi/zfcp_scsi.c
drivers/s390/scsi/zfcp_sysfs.c

index 9fa1b06..86a8725 100644 (file)
@@ -212,6 +212,7 @@ struct zfcp_port {
        struct work_struct     test_link_work;
        struct work_struct     rport_work;
        enum { RPORT_NONE, RPORT_ADD, RPORT_DEL }  rport_task;
+       unsigned int            starget_id;
 };
 
 struct zfcp_unit {
index 4cab33a..9d117ee 100644 (file)
@@ -564,6 +564,7 @@ static void zfcp_scsi_rport_register(struct zfcp_port *port)
        rport->maxframe_size = port->maxframe_size;
        rport->supported_classes = port->supported_classes;
        port->rport = rport;
+       port->starget_id = rport->scsi_target_id;
 
        zfcp_scsi_queue_unit_register(port);
 }
index 205b9f8..b4561c8 100644 (file)
@@ -290,6 +290,7 @@ static ssize_t zfcp_sysfs_unit_remove_store(struct device *dev,
        struct zfcp_unit *unit;
        u64 fcp_lun;
        int retval = -EINVAL;
+       struct scsi_device *sdev;
 
        if (!(port && get_device(&port->dev)))
                return -EBUSY;
@@ -303,8 +304,13 @@ static ssize_t zfcp_sysfs_unit_remove_store(struct device *dev,
        else
                retval = 0;
 
-       /* wait for possible timeout during SCSI probe */
-       flush_work(&unit->scsi_work);
+       sdev = scsi_device_lookup(port->adapter->scsi_host, 0,
+                                 port->starget_id,
+                                 scsilun_to_int((struct scsi_lun *)&fcp_lun));
+       if (sdev) {
+               scsi_remove_device(sdev);
+               scsi_device_put(sdev);
+       }
 
        write_lock_irq(&port->unit_list_lock);
        list_del(&unit->list);