diff options
author | David S. Miller <davem@davemloft.net> | 2012-02-26 21:55:51 -0500 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2012-02-26 21:55:51 -0500 |
commit | ff4783ce78c08d2990126ce1874250ae8e72bbd2 (patch) | |
tree | 5c95885a4ab768101dd72942b57c238d452a7565 /drivers/scsi/device_handler/scsi_dh_rdac.c | |
parent | 622121719934f60378279eb440d3cec2fc3176d2 (diff) | |
parent | 203738e548cefc3fc3c2f73a9063176c9f3583d5 (diff) | |
download | kernel_goldelico_gta04-ff4783ce78c08d2990126ce1874250ae8e72bbd2.zip kernel_goldelico_gta04-ff4783ce78c08d2990126ce1874250ae8e72bbd2.tar.gz kernel_goldelico_gta04-ff4783ce78c08d2990126ce1874250ae8e72bbd2.tar.bz2 |
Merge git://git.kernel.org/pub/scm/linux/kernel/git/davem/net
Conflicts:
drivers/net/ethernet/sfc/rx.c
Overlapping changes in drivers/net/ethernet/sfc/rx.c, one to change
the rx_buf->is_page boolean into a set of u16 flags, and another to
adjust how ->ip_summed is initialized.
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/scsi/device_handler/scsi_dh_rdac.c')
-rw-r--r-- | drivers/scsi/device_handler/scsi_dh_rdac.c | 25 |
1 files changed, 14 insertions, 11 deletions
diff --git a/drivers/scsi/device_handler/scsi_dh_rdac.c b/drivers/scsi/device_handler/scsi_dh_rdac.c index 53a31c7..20c4557 100644 --- a/drivers/scsi/device_handler/scsi_dh_rdac.c +++ b/drivers/scsi/device_handler/scsi_dh_rdac.c @@ -364,10 +364,7 @@ static void release_controller(struct kref *kref) struct rdac_controller *ctlr; ctlr = container_of(kref, struct rdac_controller, kref); - flush_workqueue(kmpath_rdacd); - spin_lock(&list_lock); list_del(&ctlr->node); - spin_unlock(&list_lock); kfree(ctlr); } @@ -376,20 +373,17 @@ static struct rdac_controller *get_controller(int index, char *array_name, { struct rdac_controller *ctlr, *tmp; - spin_lock(&list_lock); - list_for_each_entry(tmp, &ctlr_list, node) { if ((memcmp(tmp->array_id, array_id, UNIQUE_ID_LEN) == 0) && (tmp->index == index) && (tmp->host == sdev->host)) { kref_get(&tmp->kref); - spin_unlock(&list_lock); return tmp; } } ctlr = kmalloc(sizeof(*ctlr), GFP_ATOMIC); if (!ctlr) - goto done; + return NULL; /* initialize fields of controller */ memcpy(ctlr->array_id, array_id, UNIQUE_ID_LEN); @@ -405,8 +399,7 @@ static struct rdac_controller *get_controller(int index, char *array_name, INIT_WORK(&ctlr->ms_work, send_mode_select); INIT_LIST_HEAD(&ctlr->ms_head); list_add(&ctlr->node, &ctlr_list); -done: - spin_unlock(&list_lock); + return ctlr; } @@ -517,9 +510,12 @@ static int initialize_controller(struct scsi_device *sdev, index = 0; else index = 1; + + spin_lock(&list_lock); h->ctlr = get_controller(index, array_name, array_id, sdev); if (!h->ctlr) err = SCSI_DH_RES_TEMP_UNAVAIL; + spin_unlock(&list_lock); } return err; } @@ -906,7 +902,9 @@ static int rdac_bus_attach(struct scsi_device *sdev) return 0; clean_ctlr: + spin_lock(&list_lock); kref_put(&h->ctlr->kref, release_controller); + spin_unlock(&list_lock); failed: kfree(scsi_dh_data); @@ -921,14 +919,19 @@ static void rdac_bus_detach( struct scsi_device *sdev ) struct rdac_dh_data *h; unsigned long flags; - spin_lock_irqsave(sdev->request_queue->queue_lock, flags); scsi_dh_data = sdev->scsi_dh_data; + h = (struct rdac_dh_data *) scsi_dh_data->buf; + if (h->ctlr && h->ctlr->ms_queued) + flush_workqueue(kmpath_rdacd); + + spin_lock_irqsave(sdev->request_queue->queue_lock, flags); sdev->scsi_dh_data = NULL; spin_unlock_irqrestore(sdev->request_queue->queue_lock, flags); - h = (struct rdac_dh_data *) scsi_dh_data->buf; + spin_lock(&list_lock); if (h->ctlr) kref_put(&h->ctlr->kref, release_controller); + spin_unlock(&list_lock); kfree(scsi_dh_data); module_put(THIS_MODULE); sdev_printk(KERN_NOTICE, sdev, "%s: Detached\n", RDAC_NAME); |