fix all REQ_BLOCK_PC retries and requeues (take2)
Subsystems (3)
PATCH 1/1 fix all REQ_BLOCK_PC retries and requeues (take2)
sd and st handle REQ_BLOCK_PC command setup the same, and except for a bug in st_intr they would handle completion exactly the same. And it seems we want scsi_execute* to handle setup and completion in the same way as the ULDs so the patch below moves everyone to use scsi_generic_done for REQ_BLOCK_PC commands.
This patch also adds a reties count onto the request so that we handle command retries like we used to.
This patch was made against scsi-rc-fixes.
drivers/block/scsi_ioctl.c +3 -0
@@ -302,6 +302,7 @@ static int sg_io(struct file *file, requ rq->timeout = q->sg_timeout;if (!rq->timeout) rq->timeout =BLK_DEFAULT_TIMEOUT ; + rq->retries =1 ; start_time = jiffies;
@@ -412,6 +413,7 @@ static int sg_scsi_ioctl(struct file *fi rq->timeout =BLK_DEFAULT_TIMEOUT ;break ; } + rq->retries =1 ;memset (sense,0 ,sizeof (sense)); rq->sense = sense;
@@ -570,6 +572,7 @@ int scsi_cmd_ioctl(struct file *file, st rq->data =NULL ; rq->data_len =0 ; rq->timeout =BLK_DEFAULT_TIMEOUT ; + rq->retries =1 ;memset (rq->cmd,0 ,sizeof (rq->cmd)); rq->cmd[0 ] =GPCMD_START_STOP_UNIT ; rq->cmd[4 ] =0x02 + (close !=0 );
drivers/scsi/scsi_lib.c +10 -3
@@ -337,6 +337,7 @@ int scsi_execute(struct scsi_device *sdememcpy (req->cmd, cmd, req->cmd_len); req->sense = sense; req->sense_len =0 ; + req->retries = retries; req->timeout = timeout; req->flags |= flags |REQ_BLOCK_PC |REQ_SPECIAL |REQ_QUIET ;
@@ -1125,7 +1126,13 @@ static int scsi_issue_flush_fn(request_qstatic void scsi_generic_done (struct scsi_cmnd *cmd) {BUG_ON (!blk_pc_request (cmd->request)); -scsi_io_completion (cmd, cmd->result ==0 ? cmd->bufflen :0 ,0 ); +/* +* This will complete the whole command with uptodate=1 so +* as far as the block layer is concerned the command completed +* successfully. Since this is REQ_BLOCK_PC command though the +* caller should check the errors value to check for errors +*/ +scsi_io_completion (cmd, cmd->bufflen,0 ); }static int scsi_prep_fn (struct request_queue *q,struct request *req)
@@ -1255,7 +1262,7 @@ static int scsi_prep_fn(struct request_q/* * Initialize the actual SCSI command for this request. */ -if (req->rq_disk) { +if (!blk_pc_request (req)) { drv = *(struct scsi_driver **)req->rq_disk->private_data;if (unlikely (!drv->init_command (cmd))) {scsi_release_buffers (cmd);
@@ -1273,7 +1280,7 @@ static int scsi_prep_fn(struct request_q cmd->sc_data_direction =DMA_NONE ; cmd->transfersize = req->data_len; - cmd->allowed =3 ; + cmd->allowed = req->retries; cmd->timeout_per_command = req->timeout; cmd->done = scsi_generic_done; }
drivers/scsi/sd.c +4 -43
77 lines not on this page · raw message
drivers/scsi/st.c +0 -38
@@ -196,7 +196,6 @@ static int sgl_unmap_user_pages(struct sstatic int st_probe (struct device *);static int st_remove (struct device *); -static int st_init_command (struct scsi_cmnd *);static void do_create_driverfs_files (void );static void do_remove_driverfs_files (void );
@@ -209,7 +208,6 @@ static struct scsi_driver st_template = .probe = st_probe, .remove = st_remove, }, - .init_command = st_init_command, };static int st_compression (struct scsi_tape *,int );
@@ -4185,42 +4183,6 @@ static void scsi_tape_release(struct krereturn ; } -static void st_intr (struct scsi_cmnd *SCpnt) -{ -scsi_io_completion (SCpnt, (SCpnt->result ?0 : SCpnt->bufflen),1 ); -} - -/* -* st_init_command: only called via the scsi_cmd_ioctl (block SG_IO) -* interface for REQ_BLOCK_PC commands. -*/ -static int st_init_command (struct scsi_cmnd *SCpnt) -{ -struct request *rq; - -if (!(SCpnt->request->flags &REQ_BLOCK_PC )) -return 0 ; - - rq = SCpnt->request; -if (sizeof (rq->cmd) >sizeof (SCpnt->cmnd)) -return 0 ; - -memcpy (SCpnt->cmnd, rq->cmd,sizeof (SCpnt->cmnd)); - SCpnt->cmd_len = rq->cmd_len; - -if (rq_data_dir (rq) ==WRITE ) - SCpnt->sc_data_direction =DMA_TO_DEVICE ; -else if (rq->data_len) - SCpnt->sc_data_direction =DMA_FROM_DEVICE ; -else - SCpnt->sc_data_direction =DMA_NONE ; - - SCpnt->timeout_per_command = rq->timeout; - SCpnt->transfersize = rq->data_len; - SCpnt->done = st_intr; -return 1 ; -} -static int __init init_st (void ) {validate_options ();
include/linux/blkdev.h +1 -0
@@ -184,6 +184,7 @@ struct request {void *sense;unsigned int timeout; +int retries;/* * For Power Management requests
Quoted 1 line · Mike Christie
sd and st handle
REQ_BLOCK_PCcommand setup the same, and
crap, I need to go to sleep. I guess those other patches here
http://marc.theaimsgroup.com/?l=linux-scsi&m=112708362822874&w=2
http://marc.theaimsgroup.com/?l=linux-scsi&m=112708367105404&w=2
were right because sr wants is special.