[SCSI] Shorten the path length of scsi_cmd_to_driver()
authorLi Zhong <zhong@linux.vnet.ibm.com>
Sat, 29 Sep 2012 04:23:37 +0000 (12:23 +0800)
committerJames Bottomley <JBottomley@Parallels.com>
Tue, 9 Oct 2012 11:04:42 +0000 (12:04 +0100)
This patch tries to shorten the path length of scsi_cmd_to_driver(). As only
REQ_TYPE_BLOCK_PC commands can be submitted without a driver, so we could
avoid the related NULL checking, as long as we make sure we don't use it for
REQ_TYPE_BLOCK_PC type commands. Plus, this fixes a bug where you get
different behaviors from REQ_TYPE_BLOCK_PC commands when a driver is and isn't
attached.

Signed-off-by: Li Zhong <zhong@linux.vnet.ibm.com>
Reviewed-by: Martin K. Petersen <martin.petersen@oracle.com>
Signed-off-by: James Bottomley <JBottomley@Parallels.com>
drivers/scsi/scsi_error.c
include/scsi/scsi_cmnd.h

index de2337f..c1b05a8 100644 (file)
@@ -789,7 +789,6 @@ static int scsi_send_eh_cmnd(struct scsi_cmnd *scmd, unsigned char *cmnd,
                             int cmnd_size, int timeout, unsigned sense_bytes)
 {
        struct scsi_device *sdev = scmd->device;
-       struct scsi_driver *sdrv = scsi_cmd_to_driver(scmd);
        struct Scsi_Host *shost = sdev->host;
        DECLARE_COMPLETION_ONSTACK(done);
        unsigned long timeleft;
@@ -845,8 +844,11 @@ static int scsi_send_eh_cmnd(struct scsi_cmnd *scmd, unsigned char *cmnd,
 
        scsi_eh_restore_cmnd(scmd, &ses);
 
-       if (sdrv && sdrv->eh_action)
-               rtn = sdrv->eh_action(scmd, cmnd, cmnd_size, rtn);
+       if (scmd->request->cmd_type != REQ_TYPE_BLOCK_PC) {
+               struct scsi_driver *sdrv = scsi_cmd_to_driver(scmd);
+               if (sdrv->eh_action)
+                       rtn = sdrv->eh_action(scmd, cmnd, cmnd_size, rtn);
+       }
 
        return rtn;
 }
index ac06cc5..de5f5d8 100644 (file)
@@ -132,18 +132,10 @@ struct scsi_cmnd {
        unsigned char tag;      /* SCSI-II queued command tag */
 };
 
+/* make sure not to use it with REQ_TYPE_BLOCK_PC commands */
 static inline struct scsi_driver *scsi_cmd_to_driver(struct scsi_cmnd *cmd)
 {
-       struct scsi_driver **sdp;
-
-       if (!cmd->request->rq_disk)
-               return NULL;
-
-       sdp = (struct scsi_driver **)cmd->request->rq_disk->private_data;
-       if (!sdp)
-               return NULL;
-
-       return *sdp;
+       return *(struct scsi_driver **)cmd->request->rq_disk->private_data;
 }
 
 extern struct scsi_cmnd *scsi_get_command(struct scsi_device *, gfp_t);