diff options
Diffstat (limited to 'drivers/message/fusion/mptspi.c')
-rw-r--r-- | drivers/message/fusion/mptspi.c | 52 |
1 files changed, 31 insertions, 21 deletions
diff --git a/drivers/message/fusion/mptspi.c b/drivers/message/fusion/mptspi.c index 643a3c6443af..8f46fdff7f77 100644 --- a/drivers/message/fusion/mptspi.c +++ b/drivers/message/fusion/mptspi.c | |||
@@ -614,19 +614,24 @@ static void mptspi_read_parameters(struct scsi_target *starget) | |||
614 | spi_width(starget) = (nego & MPI_SCSIDEVPAGE0_NP_WIDE) ? 1 : 0; | 614 | spi_width(starget) = (nego & MPI_SCSIDEVPAGE0_NP_WIDE) ? 1 : 0; |
615 | } | 615 | } |
616 | 616 | ||
617 | static int | 617 | int |
618 | mptscsih_quiesce_raid(MPT_SCSI_HOST *hd, int quiesce, u8 channel, u8 id) | 618 | mptscsih_quiesce_raid(MPT_SCSI_HOST *hd, int quiesce, u8 channel, u8 id) |
619 | { | 619 | { |
620 | MPT_ADAPTER *ioc = hd->ioc; | ||
620 | MpiRaidActionRequest_t *pReq; | 621 | MpiRaidActionRequest_t *pReq; |
621 | MPT_FRAME_HDR *mf; | 622 | MPT_FRAME_HDR *mf; |
622 | MPT_ADAPTER *ioc = hd->ioc; | 623 | int ret; |
624 | unsigned long timeleft; | ||
625 | |||
626 | mutex_lock(&ioc->internal_cmds.mutex); | ||
623 | 627 | ||
624 | /* Get and Populate a free Frame | 628 | /* Get and Populate a free Frame |
625 | */ | 629 | */ |
626 | if ((mf = mpt_get_msg_frame(ioc->InternalCtx, ioc)) == NULL) { | 630 | if ((mf = mpt_get_msg_frame(ioc->InternalCtx, ioc)) == NULL) { |
627 | ddvprintk(ioc, printk(MYIOC_s_WARN_FMT "_do_raid: no msg frames!\n", | 631 | dfailprintk(hd->ioc, printk(MYIOC_s_WARN_FMT |
628 | ioc->name)); | 632 | "%s: no msg frames!\n", ioc->name, __func__)); |
629 | return -EAGAIN; | 633 | ret = -EAGAIN; |
634 | goto out; | ||
630 | } | 635 | } |
631 | pReq = (MpiRaidActionRequest_t *)mf; | 636 | pReq = (MpiRaidActionRequest_t *)mf; |
632 | if (quiesce) | 637 | if (quiesce) |
@@ -649,23 +654,30 @@ mptscsih_quiesce_raid(MPT_SCSI_HOST *hd, int quiesce, u8 channel, u8 id) | |||
649 | ddvprintk(ioc, printk(MYIOC_s_DEBUG_FMT "RAID Volume action=%x channel=%d id=%d\n", | 654 | ddvprintk(ioc, printk(MYIOC_s_DEBUG_FMT "RAID Volume action=%x channel=%d id=%d\n", |
650 | ioc->name, pReq->Action, channel, id)); | 655 | ioc->name, pReq->Action, channel, id)); |
651 | 656 | ||
652 | hd->pLocal = NULL; | 657 | INITIALIZE_MGMT_STATUS(ioc->internal_cmds.status) |
653 | hd->timer.expires = jiffies + HZ*10; /* 10 second timeout */ | ||
654 | hd->scandv_wait_done = 0; | ||
655 | |||
656 | /* Save cmd pointer, for resource free if timeout or | ||
657 | * FW reload occurs | ||
658 | */ | ||
659 | hd->cmdPtr = mf; | ||
660 | |||
661 | add_timer(&hd->timer); | ||
662 | mpt_put_msg_frame(ioc->InternalCtx, ioc, mf); | 658 | mpt_put_msg_frame(ioc->InternalCtx, ioc, mf); |
663 | wait_event(hd->scandv_waitq, hd->scandv_wait_done); | 659 | timeleft = wait_for_completion_timeout(&ioc->internal_cmds.done, 10*HZ); |
660 | if (!(ioc->internal_cmds.status & MPT_MGMT_STATUS_COMMAND_GOOD)) { | ||
661 | ret = -ETIME; | ||
662 | dfailprintk(ioc, printk(MYIOC_s_DEBUG_FMT "%s: TIMED OUT!\n", | ||
663 | ioc->name, __func__)); | ||
664 | if (ioc->internal_cmds.status & MPT_MGMT_STATUS_DID_IOCRESET) | ||
665 | goto out; | ||
666 | if (!timeleft) { | ||
667 | printk(MYIOC_s_WARN_FMT "Issuing Reset from %s!!\n", | ||
668 | ioc->name, __func__); | ||
669 | mpt_HardResetHandler(ioc, CAN_SLEEP); | ||
670 | mpt_free_msg_frame(ioc, mf); | ||
671 | } | ||
672 | goto out; | ||
673 | } | ||
664 | 674 | ||
665 | if ((hd->pLocal == NULL) || (hd->pLocal->completion != 0)) | 675 | ret = ioc->internal_cmds.completion_code; |
666 | return -1; | ||
667 | 676 | ||
668 | return 0; | 677 | out: |
678 | CLEAR_MGMT_STATUS(ioc->internal_cmds.status) | ||
679 | mutex_unlock(&ioc->internal_cmds.mutex); | ||
680 | return ret; | ||
669 | } | 681 | } |
670 | 682 | ||
671 | static void mptspi_dv_device(struct _MPT_SCSI_HOST *hd, | 683 | static void mptspi_dv_device(struct _MPT_SCSI_HOST *hd, |
@@ -1491,8 +1503,6 @@ mptspi_probe(struct pci_dev *pdev, const struct pci_device_id *id) | |||
1491 | mpt_saf_te)); | 1503 | mpt_saf_te)); |
1492 | ioc->spi_data.noQas = 0; | 1504 | ioc->spi_data.noQas = 0; |
1493 | 1505 | ||
1494 | init_waitqueue_head(&hd->scandv_waitq); | ||
1495 | hd->scandv_wait_done = 0; | ||
1496 | hd->last_queue_full = 0; | 1506 | hd->last_queue_full = 0; |
1497 | hd->spi_pending = 0; | 1507 | hd->spi_pending = 0; |
1498 | 1508 | ||