Fix scsi_dispatch_cmd() to stop timers.
Signed-off-by: Malahal Naineni <[EMAIL PROTECTED]>
diff -r 870bb598c977 drivers/scsi/scsi.c
--- a/drivers/scsi/scsi.c Thu Sep 27 00:25:38 2007 -0700
+++ b/drivers/scsi/scsi.c Thu Sep 27 01:04:10 2007 -0700
@@ -471,14 +471,19 @@ int scsi_dispatch_cmd(struct scsi_cmnd *
unsigned long timeout;
int rtn = 0;
+ /*
+* We will use a queued command if possible, otherwise we will
+* emulate the queuing and calling of completion function ourselves.
+*/
+ atomic_inc(&cmd->device->iorequest_cnt);
+
/* check if the device is still usable */
if (unlikely(cmd->device->sdev_state == SDEV_DEL)) {
/* in SDEV_DEL we error all commands. DID_NO_CONNECT
* returns an immediate error upwards, and signals
* that the device is no longer present */
cmd->result = DID_NO_CONNECT << 16;
- atomic_inc(&cmd->device->iorequest_cnt);
- __blk_complete_request(cmd->request);
+ scsi_done(cmd);
/* return 0 (because the command has been processed) */
goto out;
}
@@ -491,7 +496,8 @@ int scsi_dispatch_cmd(struct scsi_cmnd *
* future requests should not occur until the device
* transitions out of the suspend state.
*/
- scsi_queue_insert(cmd, SCSI_MLQUEUE_DEVICE_BUSY);
+
+ scsi_queue_retry(cmd, SCSI_MLQUEUE_DEVICE_BUSY);
SCSI_LOG_MLQUEUE(3, printk("queuecommand : device blocked \n"));
@@ -536,12 +542,6 @@ int scsi_dispatch_cmd(struct scsi_cmnd *
scsi_log_send(cmd);
/*
-* We will use a queued command if possible, otherwise we will
-* emulate the queuing and calling of completion function ourselves.
-*/
- atomic_inc(&cmd->device->iorequest_cnt);
-
- /*
* Before we queue this command, check if the command
* length exceeds what the host adapter can handle.
*/
@@ -571,12 +571,8 @@ int scsi_dispatch_cmd(struct scsi_cmnd *
}
spin_unlock_irqrestore(host->host_lock, flags);
if (rtn) {
- if (blk_delete_timer(cmd->request)) {
- atomic_inc(&cmd->device->iodone_cnt);
- scsi_queue_insert(cmd,
- (rtn == SCSI_MLQUEUE_DEVICE_BUSY) ?
- rtn : SCSI_MLQUEUE_HOST_BUSY);
- }
+ scsi_queue_retry(cmd, (rtn == SCSI_MLQUEUE_DEVICE_BUSY) ?
+ rtn : SCSI_MLQUEUE_HOST_BUSY);
SCSI_LOG_MLQUEUE(3,
printk("queuecommand : request rejected\n"));
}
diff -r 870bb598c977 drivers/scsi/scsi_lib.c
--- a/drivers/scsi/scsi_lib.c Thu Sep 27 00:25:38 2007 -0700
+++ b/drivers/scsi/scsi_lib.c Thu Sep 27 01:16:28 2007 -0700
@@ -160,6 +160,36 @@ int scsi_queue_insert(struct scsi_cmnd *
return 0;
}
+
+/*
+ * Function:scsi_queue_retry()
+ *
+ * Purpose: Try inserting a command in the midlevel queue.
+ *
+ * Arguments: cmd- command that we are adding to queue.
+ * reason - why we are inserting command to queue.
+ *
+ * Lock status: Assumed that lock is not held upon entry.
+ *
+ * Returns: Nothing.
+ *
+ * Notes: This is very similar to scsi_queue_insert except that we
+ * call this function when we don't know if the blk layer timer
+ * is active or not. We could implement this either by calling
+ * blk_delete_timer and inserting in the midlevel queue if we
+ * successfully delete the timer OR setting appropriate result
+ * field in the cmd and letting it go through the normal done
+ * routines which will retry the command. For now, We call
+ * blk_delete_timer!
+ */
+void scsi_queue_retry(struct scsi_cmnd *cmd, int reason)
+{
+ if (blk_delete_timer(cmd->request)) {
+ atomic_inc(&cmd->device->iodone_cnt);
+ scsi_queue_insert(cmd, reason);
+ }
+}
+
/**
* scsi_execute - insert request and wait for the result
diff -r 870bb598c977 drivers/scsi/scsi_priv.h
--- a/drivers/scsi/scsi_priv.h Thu Sep 27 00:25:38 2007 -0700
+++ b/drivers/scsi/scsi_priv.h Thu Sep 27 01:03:39 2007 -0700
@@ -64,6 +64,7 @@ extern int scsi_maybe_unblock_host(struc
extern int scsi_maybe_unblock_host(struct scsi_device *sdev);
extern void scsi_device_unbusy(struct scsi_device *sdev);
extern int scsi_queue_insert(struct scsi_cmnd *cmd, int reason);
+extern void scsi_queue_retry(struct scsi_cmnd *cmd, int reason);
extern void scsi_next_command(struct scsi_cmnd *cmd);
extern void scsi_run_host_queues(struct Scsi_Host *shost);
extern struct request_queue *scsi_alloc_queue(struct scsi_device *sdev);
-
To unsubscribe from this list: