aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/block/cciss.c
diff options
context:
space:
mode:
authorscameron@beardog.cca.cpqcorp.net <scameron@beardog.cca.cpqcorp.net>2009-06-08 17:04:35 -0400
committerJens Axboe <jens.axboe@oracle.com>2009-06-08 23:47:43 -0400
commit3c2ab40296894d1f7ad9714550fdf9b96d4e9ee6 (patch)
treed83a8cfceddeae1c7a2bc102250c0482ffd6fb36 /drivers/block/cciss.c
parentb57695fe131b13d3f2460cfeb9175cff673ed337 (diff)
cciss: factor out fix target status processing code from sendcmd functions
Factor out code to process target status of completed commands in sendcmd() and sendcmd_withirq_core(), and fix problem that bad target status was ignored in sendcmd_withirq_core. Signed-off-by: Stephen M. Cameron <scameron@beardog.cca.cpqcorp.net> Signed-off-by: Jens Axboe <jens.axboe@oracle.com>
Diffstat (limited to 'drivers/block/cciss.c')
-rw-r--r--drivers/block/cciss.c56
1 files changed, 34 insertions, 22 deletions
diff --git a/drivers/block/cciss.c b/drivers/block/cciss.c
index 885ea1e38e42..2d128831d3ca 100644
--- a/drivers/block/cciss.c
+++ b/drivers/block/cciss.c
@@ -2267,6 +2267,31 @@ static int fill_cmd(CommandList_struct *c, __u8 cmd, int ctlr, void *buff,
2267 return status; 2267 return status;
2268} 2268}
2269 2269
2270static int check_target_status(ctlr_info_t *h, CommandList_struct *c)
2271{
2272 switch (c->err_info->ScsiStatus) {
2273 case SAM_STAT_GOOD:
2274 return IO_OK;
2275 case SAM_STAT_CHECK_CONDITION:
2276 switch (0xf & c->err_info->SenseInfo[2]) {
2277 case 0: return IO_OK; /* no sense */
2278 case 1: return IO_OK; /* recovered error */
2279 default:
2280 printk(KERN_WARNING "cciss%d: cmd 0x%02x "
2281 "check condition, sense key = 0x%02x\n",
2282 h->ctlr, c->Request.CDB[0],
2283 c->err_info->SenseInfo[2]);
2284 }
2285 break;
2286 default:
2287 printk(KERN_WARNING "cciss%d: cmd 0x%02x"
2288 "scsi status = 0x%02x\n", h->ctlr,
2289 c->Request.CDB[0], c->err_info->ScsiStatus);
2290 break;
2291 }
2292 return IO_ERROR;
2293}
2294
2270static int sendcmd_withirq_core(ctlr_info_t *h, CommandList_struct *c) 2295static int sendcmd_withirq_core(ctlr_info_t *h, CommandList_struct *c)
2271{ 2296{
2272 DECLARE_COMPLETION_ONSTACK(wait); 2297 DECLARE_COMPLETION_ONSTACK(wait);
@@ -2290,16 +2315,7 @@ resend_cmd2:
2290 2315
2291 switch (c->err_info->CommandStatus) { 2316 switch (c->err_info->CommandStatus) {
2292 case CMD_TARGET_STATUS: 2317 case CMD_TARGET_STATUS:
2293 printk(KERN_WARNING "cciss: cmd 0x%02x " 2318 return_status = check_target_status(h, c);
2294 "has completed with errors\n", c->Request.CDB[0]);
2295 if (c->err_info->ScsiStatus) {
2296 printk(KERN_WARNING "cciss: cmd 0x%02x "
2297 "has SCSI Status = %x\n",
2298 c->Request.CDB[0], c->err_info->ScsiStatus);
2299 if (c->err_info->ScsiStatus == SAM_STAT_CHECK_CONDITION)
2300 printk(KERN_WARNING "sense key = 0x%02x\n",
2301 0xf & c->err_info->SenseInfo[2]);
2302 }
2303 break; 2319 break;
2304 case CMD_DATA_UNDERRUN: 2320 case CMD_DATA_UNDERRUN:
2305 case CMD_DATA_OVERRUN: 2321 case CMD_DATA_OVERRUN:
@@ -2710,33 +2726,29 @@ resend_cmd1:
2710 printk(KERN_WARNING "cciss%d: retried %p too many " 2726 printk(KERN_WARNING "cciss%d: retried %p too many "
2711 "times\n", h->ctlr, c); 2727 "times\n", h->ctlr, c);
2712 status = IO_ERROR; 2728 status = IO_ERROR;
2713 goto cleanup1; 2729 break;
2714 } 2730 }
2715 2731
2716 if (c->err_info->CommandStatus == CMD_UNABORTABLE) { 2732 if (c->err_info->CommandStatus == CMD_UNABORTABLE) {
2717 printk(KERN_WARNING "cciss%d: command could not be " 2733 printk(KERN_WARNING "cciss%d: command could not be "
2718 "aborted.\n", h->ctlr); 2734 "aborted.\n", h->ctlr);
2719 status = IO_ERROR; 2735 status = IO_ERROR;
2720 goto cleanup1; 2736 break;
2721 } 2737 }
2722 2738
2723 printk(KERN_WARNING "cciss%d: sendcmd error\n", h->ctlr);
2724 printk(KERN_WARNING "cmd = 0x%02x, CommandStatus = 0x%02x\n",
2725 c->Request.CDB[0], c->err_info->CommandStatus);
2726 if (c->err_info->CommandStatus == CMD_TARGET_STATUS) { 2739 if (c->err_info->CommandStatus == CMD_TARGET_STATUS) {
2727 printk(KERN_WARNING "Target status = 0x%02x\n", 2740 status = check_target_status(h, c);
2728 c->err_info->ScsiStatus); 2741 break;
2729 if (c->err_info->ScsiStatus == 2) /* chk cond */
2730 printk(KERN_WARNING "Sense key = 0x%02x\n",
2731 0xf & c->err_info->SenseInfo[2]);
2732 } 2742 }
2733 2743
2744 printk(KERN_WARNING "cciss%d: sendcmd error\n", h->ctlr);
2745 printk(KERN_WARNING "cmd = 0x%02x, CommandStatus = 0x%02x\n",
2746 c->Request.CDB[0], c->err_info->CommandStatus);
2734 status = IO_ERROR; 2747 status = IO_ERROR;
2735 goto cleanup1; 2748 break;
2736 2749
2737 } while (1); 2750 } while (1);
2738 2751
2739cleanup1:
2740 /* unlock the data buffer from DMA */ 2752 /* unlock the data buffer from DMA */
2741 buff_dma_handle.val32.lower = c->SG[0].Addr.lower; 2753 buff_dma_handle.val32.lower = c->SG[0].Addr.lower;
2742 buff_dma_handle.val32.upper = c->SG[0].Addr.upper; 2754 buff_dma_handle.val32.upper = c->SG[0].Addr.upper;