ipr abort hang fix - resend
Subsystems (2)
Brian King
maintainerPATCH 1/3 ipr abort hang fix - resend
This one didn't seem to come through, so here it is again. Apologies if you've already seen it.
Signature · 3 lines
Brian King eServer Storage I/O IBM Linux Technology Center
The following patch fixes a hang that occurs when an abort is issued by the midlayer. The hang is the result of overriding a field in the union of the ipr_cmd struct. It is fixed by moving this pointer outside of the union, since it is not mutually exclusive with the other fields in the union.
---
linux-2.6.7-rc2-bjking1/drivers/scsi/ipr.c | 15 ++++++++------- linux-2.6.7-rc2-bjking1/drivers/scsi/ipr.h | 2 +- 2 files changed, 9 insertions(+), 8 deletions(-)
drivers/scsi/ipr.c renamed from drivers/scsi/ipr.c~ipr_abort_hang +8 -7
@@ -448,6 +448,7 @@ static void ipr_init_ipr_cmnd(struct ipr {ipr_reinit_ipr_cmnd (ipr_cmd); ipr_cmd->u.scratch =0 ; + ipr_cmd->sibling =NULL ;init_timer (&ipr_cmd->timer); }
@@ -676,8 +677,8 @@ static void ipr_do_req(struct ipr_cmnd ***/ static void ipr_internal_cmd_done (struct ipr_cmnd *ipr_cmd) { -if (ipr_cmd->u.sibling) - ipr_cmd->u.sibling =NULL ; +if (ipr_cmd->sibling) + ipr_cmd->sibling =NULL ;else complete (&ipr_cmd->completion); }
@@ -3015,10 +3016,10 @@ static void ipr_bus_reset_done(struct ip* If abort has not completed, indicate the reset has, else call the * abort's done function to wake the sleeping eh thread */ -if (ipr_cmd->u.sibling->u.sibling) - ipr_cmd->u.sibling->u.sibling =NULL ; +if (ipr_cmd->sibling->sibling) + ipr_cmd->sibling->sibling =NULL ;else - ipr_cmd->u.sibling->done (ipr_cmd->u.sibling); + ipr_cmd->sibling->done (ipr_cmd->sibling);list_add_tail (&ipr_cmd->queue, &ioa_cfg->free_q);LEAVE ;
@@ -3051,8 +3052,8 @@ static void ipr_abort_timeout(struct ipripr_sdev_err (ipr_cmd->u.sdev,"Abort timed out. Resetting bus\n" ); reset_cmd =ipr_get_free_ipr_cmnd (ioa_cfg); - ipr_cmd->u.sibling = reset_cmd; - reset_cmd->u.sibling = ipr_cmd; + ipr_cmd->sibling = reset_cmd; + reset_cmd->sibling = ipr_cmd; reset_cmd->ioarcb.res_handle = ipr_cmd->ioarcb.res_handle; cmd_pkt = &reset_cmd->ioarcb.cmd_pkt; cmd_pkt->request_type =IPR_RQTYPE_IOACMD ;
drivers/scsi/ipr.h renamed from drivers/scsi/ipr.h~ipr_abort_hang +1 -1
@@ -932,13 +932,13 @@ struct ipr_cmnd {dma_addr_t sense_buffer_dma;unsigned short dma_use_sg;dma_addr_t dma_handle; +struct ipr_cmnd *sibling;union {enum ipr_shutdown_type shutdown_type;struct ipr_hostrcb *hostrcb;unsigned long time_left;unsigned long scratch;struct ipr_resource_entry *res; -struct ipr_cmnd *sibling;struct scsi_device *sdev; } u;
_