summaryrefslogtreecommitdiff
path: root/drivers/scsi/libsas
diff options
context:
space:
mode:
authorDan Williams <dan.j.williams@intel.com>2012-06-21 23:36:30 -0700
committerJames Bottomley <JBottomley@Parallels.com>2012-07-20 08:58:54 +0100
commitf0bf750c2d25c3a2131ececbff63c7878e0e3765 (patch)
treeba967c5d28945e76bee78feb24ade328d5b0b3a6 /drivers/scsi/libsas
parenta494fd5bd98bb35d5a9a274fecb768e14ebf499c (diff)
downloadlinux-3.10-f0bf750c2d25c3a2131ececbff63c7878e0e3765.tar.gz
linux-3.10-f0bf750c2d25c3a2131ececbff63c7878e0e3765.tar.bz2
linux-3.10-f0bf750c2d25c3a2131ececbff63c7878e0e3765.zip
[SCSI] libsas: trim sas_task of slow path infrastructure
The timer and the completion are only used for slow path tasks (smp, and lldd tmfs), yet we incur the allocation space and cpu setup time for every fast path task. Cc: Xiangliang Yu <yuxiangl@marvell.com> Acked-by: Jack Wang <jack_wang@usish.com> Signed-off-by: Dan Williams <dan.j.williams@intel.com> Signed-off-by: James Bottomley <JBottomley@Parallels.com>
Diffstat (limited to 'drivers/scsi/libsas')
-rw-r--r--drivers/scsi/libsas/sas_expander.c20
-rw-r--r--drivers/scsi/libsas/sas_init.c23
-rw-r--r--drivers/scsi/libsas/sas_scsi_host.c8
3 files changed, 37 insertions, 14 deletions
diff --git a/drivers/scsi/libsas/sas_expander.c b/drivers/scsi/libsas/sas_expander.c
index 879dbbe6979..efc6e72f09f 100644
--- a/drivers/scsi/libsas/sas_expander.c
+++ b/drivers/scsi/libsas/sas_expander.c
@@ -51,14 +51,14 @@ static void smp_task_timedout(unsigned long _task)
task->task_state_flags |= SAS_TASK_STATE_ABORTED;
spin_unlock_irqrestore(&task->task_state_lock, flags);
- complete(&task->completion);
+ complete(&task->slow_task->completion);
}
static void smp_task_done(struct sas_task *task)
{
- if (!del_timer(&task->timer))
+ if (!del_timer(&task->slow_task->timer))
return;
- complete(&task->completion);
+ complete(&task->slow_task->completion);
}
/* Give it some long enough timeout. In seconds. */
@@ -79,7 +79,7 @@ static int smp_execute_task(struct domain_device *dev, void *req, int req_size,
break;
}
- task = sas_alloc_task(GFP_KERNEL);
+ task = sas_alloc_slow_task(GFP_KERNEL);
if (!task) {
res = -ENOMEM;
break;
@@ -91,20 +91,20 @@ static int smp_execute_task(struct domain_device *dev, void *req, int req_size,
task->task_done = smp_task_done;
- task->timer.data = (unsigned long) task;
- task->timer.function = smp_task_timedout;
- task->timer.expires = jiffies + SMP_TIMEOUT*HZ;
- add_timer(&task->timer);
+ task->slow_task->timer.data = (unsigned long) task;
+ task->slow_task->timer.function = smp_task_timedout;
+ task->slow_task->timer.expires = jiffies + SMP_TIMEOUT*HZ;
+ add_timer(&task->slow_task->timer);
res = i->dft->lldd_execute_task(task, 1, GFP_KERNEL);
if (res) {
- del_timer(&task->timer);
+ del_timer(&task->slow_task->timer);
SAS_DPRINTK("executing SMP task failed:%d\n", res);
break;
}
- wait_for_completion(&task->completion);
+ wait_for_completion(&task->slow_task->completion);
res = -ECOMM;
if ((task->task_state_flags & SAS_TASK_STATE_ABORTED)) {
SAS_DPRINTK("smp task timed out or aborted\n");
diff --git a/drivers/scsi/libsas/sas_init.c b/drivers/scsi/libsas/sas_init.c
index 1bbab3d94a2..014297c0588 100644
--- a/drivers/scsi/libsas/sas_init.c
+++ b/drivers/scsi/libsas/sas_init.c
@@ -48,18 +48,37 @@ struct sas_task *sas_alloc_task(gfp_t flags)
INIT_LIST_HEAD(&task->list);
spin_lock_init(&task->task_state_lock);
task->task_state_flags = SAS_TASK_STATE_PENDING;
- init_timer(&task->timer);
- init_completion(&task->completion);
}
return task;
}
EXPORT_SYMBOL_GPL(sas_alloc_task);
+struct sas_task *sas_alloc_slow_task(gfp_t flags)
+{
+ struct sas_task *task = sas_alloc_task(flags);
+ struct sas_task_slow *slow = kmalloc(sizeof(*slow), flags);
+
+ if (!task || !slow) {
+ if (task)
+ kmem_cache_free(sas_task_cache, task);
+ kfree(slow);
+ return NULL;
+ }
+
+ task->slow_task = slow;
+ init_timer(&slow->timer);
+ init_completion(&slow->completion);
+
+ return task;
+}
+EXPORT_SYMBOL_GPL(sas_alloc_slow_task);
+
void sas_free_task(struct sas_task *task)
{
if (task) {
BUG_ON(!list_empty(&task->list));
+ kfree(task->slow_task);
kmem_cache_free(sas_task_cache, task);
}
}
diff --git a/drivers/scsi/libsas/sas_scsi_host.c b/drivers/scsi/libsas/sas_scsi_host.c
index 67641485987..6e795a174a1 100644
--- a/drivers/scsi/libsas/sas_scsi_host.c
+++ b/drivers/scsi/libsas/sas_scsi_host.c
@@ -1134,9 +1134,13 @@ void sas_task_abort(struct sas_task *task)
/* Escape for libsas internal commands */
if (!sc) {
- if (!del_timer(&task->timer))
+ struct sas_task_slow *slow = task->slow_task;
+
+ if (!slow)
+ return;
+ if (!del_timer(&slow->timer))
return;
- task->timer.function(task->timer.data);
+ slow->timer.function(slow->timer.data);
return;
}