diff options
Diffstat (limited to 'drivers/scsi/lpfc/lpfc_scsi.c')
-rw-r--r-- | drivers/scsi/lpfc/lpfc_scsi.c | 56 |
1 files changed, 46 insertions, 10 deletions
diff --git a/drivers/scsi/lpfc/lpfc_scsi.c b/drivers/scsi/lpfc/lpfc_scsi.c index 84e4481b2406..3ccc97496ebf 100644 --- a/drivers/scsi/lpfc/lpfc_scsi.c +++ b/drivers/scsi/lpfc/lpfc_scsi.c | |||
@@ -743,7 +743,14 @@ lpfc_sli4_repost_scsi_sgl_list(struct lpfc_hba *phba) | |||
743 | if (bcnt == 0) | 743 | if (bcnt == 0) |
744 | continue; | 744 | continue; |
745 | /* Now, post the SCSI buffer list sgls as a block */ | 745 | /* Now, post the SCSI buffer list sgls as a block */ |
746 | status = lpfc_sli4_post_scsi_sgl_block(phba, &sblist, bcnt); | 746 | if (!phba->sli4_hba.extents_in_use) |
747 | status = lpfc_sli4_post_scsi_sgl_block(phba, | ||
748 | &sblist, | ||
749 | bcnt); | ||
750 | else | ||
751 | status = lpfc_sli4_post_scsi_sgl_blk_ext(phba, | ||
752 | &sblist, | ||
753 | bcnt); | ||
747 | /* Reset SCSI buffer count for next round of posting */ | 754 | /* Reset SCSI buffer count for next round of posting */ |
748 | bcnt = 0; | 755 | bcnt = 0; |
749 | while (!list_empty(&sblist)) { | 756 | while (!list_empty(&sblist)) { |
@@ -787,7 +794,7 @@ lpfc_new_scsi_buf_s4(struct lpfc_vport *vport, int num_to_alloc) | |||
787 | dma_addr_t pdma_phys_fcp_cmd; | 794 | dma_addr_t pdma_phys_fcp_cmd; |
788 | dma_addr_t pdma_phys_fcp_rsp; | 795 | dma_addr_t pdma_phys_fcp_rsp; |
789 | dma_addr_t pdma_phys_bpl, pdma_phys_bpl1; | 796 | dma_addr_t pdma_phys_bpl, pdma_phys_bpl1; |
790 | uint16_t iotag, last_xritag = NO_XRI; | 797 | uint16_t iotag, last_xritag = NO_XRI, lxri = 0; |
791 | int status = 0, index; | 798 | int status = 0, index; |
792 | int bcnt; | 799 | int bcnt; |
793 | int non_sequential_xri = 0; | 800 | int non_sequential_xri = 0; |
@@ -823,13 +830,15 @@ lpfc_new_scsi_buf_s4(struct lpfc_vport *vport, int num_to_alloc) | |||
823 | break; | 830 | break; |
824 | } | 831 | } |
825 | 832 | ||
826 | psb->cur_iocbq.sli4_xritag = lpfc_sli4_next_xritag(phba); | 833 | lxri = lpfc_sli4_next_xritag(phba); |
827 | if (psb->cur_iocbq.sli4_xritag == NO_XRI) { | 834 | if (lxri == NO_XRI) { |
828 | pci_pool_free(phba->lpfc_scsi_dma_buf_pool, | 835 | pci_pool_free(phba->lpfc_scsi_dma_buf_pool, |
829 | psb->data, psb->dma_handle); | 836 | psb->data, psb->dma_handle); |
830 | kfree(psb); | 837 | kfree(psb); |
831 | break; | 838 | break; |
832 | } | 839 | } |
840 | psb->cur_iocbq.sli4_lxritag = lxri; | ||
841 | psb->cur_iocbq.sli4_xritag = phba->sli4_hba.xri_ids[lxri]; | ||
833 | if (last_xritag != NO_XRI | 842 | if (last_xritag != NO_XRI |
834 | && psb->cur_iocbq.sli4_xritag != (last_xritag+1)) { | 843 | && psb->cur_iocbq.sli4_xritag != (last_xritag+1)) { |
835 | non_sequential_xri = 1; | 844 | non_sequential_xri = 1; |
@@ -861,6 +870,7 @@ lpfc_new_scsi_buf_s4(struct lpfc_vport *vport, int num_to_alloc) | |||
861 | */ | 870 | */ |
862 | sgl->addr_hi = cpu_to_le32(putPaddrHigh(pdma_phys_fcp_cmd)); | 871 | sgl->addr_hi = cpu_to_le32(putPaddrHigh(pdma_phys_fcp_cmd)); |
863 | sgl->addr_lo = cpu_to_le32(putPaddrLow(pdma_phys_fcp_cmd)); | 872 | sgl->addr_lo = cpu_to_le32(putPaddrLow(pdma_phys_fcp_cmd)); |
873 | sgl->word2 = le32_to_cpu(sgl->word2); | ||
864 | bf_set(lpfc_sli4_sge_last, sgl, 0); | 874 | bf_set(lpfc_sli4_sge_last, sgl, 0); |
865 | sgl->word2 = cpu_to_le32(sgl->word2); | 875 | sgl->word2 = cpu_to_le32(sgl->word2); |
866 | sgl->sge_len = cpu_to_le32(sizeof(struct fcp_cmnd)); | 876 | sgl->sge_len = cpu_to_le32(sizeof(struct fcp_cmnd)); |
@@ -869,6 +879,7 @@ lpfc_new_scsi_buf_s4(struct lpfc_vport *vport, int num_to_alloc) | |||
869 | /* Setup the physical region for the FCP RSP */ | 879 | /* Setup the physical region for the FCP RSP */ |
870 | sgl->addr_hi = cpu_to_le32(putPaddrHigh(pdma_phys_fcp_rsp)); | 880 | sgl->addr_hi = cpu_to_le32(putPaddrHigh(pdma_phys_fcp_rsp)); |
871 | sgl->addr_lo = cpu_to_le32(putPaddrLow(pdma_phys_fcp_rsp)); | 881 | sgl->addr_lo = cpu_to_le32(putPaddrLow(pdma_phys_fcp_rsp)); |
882 | sgl->word2 = le32_to_cpu(sgl->word2); | ||
872 | bf_set(lpfc_sli4_sge_last, sgl, 1); | 883 | bf_set(lpfc_sli4_sge_last, sgl, 1); |
873 | sgl->word2 = cpu_to_le32(sgl->word2); | 884 | sgl->word2 = cpu_to_le32(sgl->word2); |
874 | sgl->sge_len = cpu_to_le32(sizeof(struct fcp_rsp)); | 885 | sgl->sge_len = cpu_to_le32(sizeof(struct fcp_rsp)); |
@@ -914,7 +925,21 @@ lpfc_new_scsi_buf_s4(struct lpfc_vport *vport, int num_to_alloc) | |||
914 | } | 925 | } |
915 | } | 926 | } |
916 | if (bcnt) { | 927 | if (bcnt) { |
917 | status = lpfc_sli4_post_scsi_sgl_block(phba, &sblist, bcnt); | 928 | if (!phba->sli4_hba.extents_in_use) |
929 | status = lpfc_sli4_post_scsi_sgl_block(phba, | ||
930 | &sblist, | ||
931 | bcnt); | ||
932 | else | ||
933 | status = lpfc_sli4_post_scsi_sgl_blk_ext(phba, | ||
934 | &sblist, | ||
935 | bcnt); | ||
936 | |||
937 | if (status) { | ||
938 | lpfc_printf_log(phba, KERN_ERR, LOG_MBOX | LOG_SLI, | ||
939 | "3021 SCSI SGL post error %d\n", | ||
940 | status); | ||
941 | bcnt = 0; | ||
942 | } | ||
918 | /* Reset SCSI buffer count for next round of posting */ | 943 | /* Reset SCSI buffer count for next round of posting */ |
919 | while (!list_empty(&sblist)) { | 944 | while (!list_empty(&sblist)) { |
920 | list_remove_head(&sblist, psb, struct lpfc_scsi_buf, | 945 | list_remove_head(&sblist, psb, struct lpfc_scsi_buf, |
@@ -2081,6 +2106,7 @@ lpfc_scsi_prep_dma_buf_s4(struct lpfc_hba *phba, struct lpfc_scsi_buf *lpfc_cmd) | |||
2081 | dma_len = sg_dma_len(sgel); | 2106 | dma_len = sg_dma_len(sgel); |
2082 | sgl->addr_lo = cpu_to_le32(putPaddrLow(physaddr)); | 2107 | sgl->addr_lo = cpu_to_le32(putPaddrLow(physaddr)); |
2083 | sgl->addr_hi = cpu_to_le32(putPaddrHigh(physaddr)); | 2108 | sgl->addr_hi = cpu_to_le32(putPaddrHigh(physaddr)); |
2109 | sgl->word2 = le32_to_cpu(sgl->word2); | ||
2084 | if ((num_bde + 1) == nseg) | 2110 | if ((num_bde + 1) == nseg) |
2085 | bf_set(lpfc_sli4_sge_last, sgl, 1); | 2111 | bf_set(lpfc_sli4_sge_last, sgl, 1); |
2086 | else | 2112 | else |
@@ -2794,6 +2820,9 @@ lpfc_scsi_prep_cmnd(struct lpfc_vport *vport, struct lpfc_scsi_buf *lpfc_cmd, | |||
2794 | * of the scsi_cmnd request_buffer | 2820 | * of the scsi_cmnd request_buffer |
2795 | */ | 2821 | */ |
2796 | piocbq->iocb.ulpContext = pnode->nlp_rpi; | 2822 | piocbq->iocb.ulpContext = pnode->nlp_rpi; |
2823 | if (phba->sli_rev == LPFC_SLI_REV4) | ||
2824 | piocbq->iocb.ulpContext = | ||
2825 | phba->sli4_hba.rpi_ids[pnode->nlp_rpi]; | ||
2797 | if (pnode->nlp_fcp_info & NLP_FCP_2_DEVICE) | 2826 | if (pnode->nlp_fcp_info & NLP_FCP_2_DEVICE) |
2798 | piocbq->iocb.ulpFCP2Rcvy = 1; | 2827 | piocbq->iocb.ulpFCP2Rcvy = 1; |
2799 | else | 2828 | else |
@@ -2807,7 +2836,7 @@ lpfc_scsi_prep_cmnd(struct lpfc_vport *vport, struct lpfc_scsi_buf *lpfc_cmd, | |||
2807 | } | 2836 | } |
2808 | 2837 | ||
2809 | /** | 2838 | /** |
2810 | * lpfc_scsi_prep_task_mgmt_cmnd - Convert SLI3 scsi TM cmd to FCP info unit | 2839 | * lpfc_scsi_prep_task_mgmt_cmd - Convert SLI3 scsi TM cmd to FCP info unit |
2811 | * @vport: The virtual port for which this call is being executed. | 2840 | * @vport: The virtual port for which this call is being executed. |
2812 | * @lpfc_cmd: Pointer to lpfc_scsi_buf data structure. | 2841 | * @lpfc_cmd: Pointer to lpfc_scsi_buf data structure. |
2813 | * @lun: Logical unit number. | 2842 | * @lun: Logical unit number. |
@@ -2851,6 +2880,10 @@ lpfc_scsi_prep_task_mgmt_cmd(struct lpfc_vport *vport, | |||
2851 | lpfc_fcpcmd_to_iocb(piocb->unsli3.fcp_ext.icd, fcp_cmnd); | 2880 | lpfc_fcpcmd_to_iocb(piocb->unsli3.fcp_ext.icd, fcp_cmnd); |
2852 | piocb->ulpCommand = CMD_FCP_ICMND64_CR; | 2881 | piocb->ulpCommand = CMD_FCP_ICMND64_CR; |
2853 | piocb->ulpContext = ndlp->nlp_rpi; | 2882 | piocb->ulpContext = ndlp->nlp_rpi; |
2883 | if (vport->phba->sli_rev == LPFC_SLI_REV4) { | ||
2884 | piocb->ulpContext = | ||
2885 | vport->phba->sli4_hba.rpi_ids[ndlp->nlp_rpi]; | ||
2886 | } | ||
2854 | if (ndlp->nlp_fcp_info & NLP_FCP_2_DEVICE) { | 2887 | if (ndlp->nlp_fcp_info & NLP_FCP_2_DEVICE) { |
2855 | piocb->ulpFCP2Rcvy = 1; | 2888 | piocb->ulpFCP2Rcvy = 1; |
2856 | } | 2889 | } |
@@ -3405,9 +3438,10 @@ lpfc_send_taskmgmt(struct lpfc_vport *vport, struct lpfc_rport_data *rdata, | |||
3405 | 3438 | ||
3406 | lpfc_printf_vlog(vport, KERN_INFO, LOG_FCP, | 3439 | lpfc_printf_vlog(vport, KERN_INFO, LOG_FCP, |
3407 | "0702 Issue %s to TGT %d LUN %d " | 3440 | "0702 Issue %s to TGT %d LUN %d " |
3408 | "rpi x%x nlp_flag x%x\n", | 3441 | "rpi x%x nlp_flag x%x Data: x%x x%x\n", |
3409 | lpfc_taskmgmt_name(task_mgmt_cmd), tgt_id, lun_id, | 3442 | lpfc_taskmgmt_name(task_mgmt_cmd), tgt_id, lun_id, |
3410 | pnode->nlp_rpi, pnode->nlp_flag); | 3443 | pnode->nlp_rpi, pnode->nlp_flag, iocbq->sli4_xritag, |
3444 | iocbq->iocb_flag); | ||
3411 | 3445 | ||
3412 | status = lpfc_sli_issue_iocb_wait(phba, LPFC_FCP_RING, | 3446 | status = lpfc_sli_issue_iocb_wait(phba, LPFC_FCP_RING, |
3413 | iocbq, iocbqrsp, lpfc_cmd->timeout); | 3447 | iocbq, iocbqrsp, lpfc_cmd->timeout); |
@@ -3419,10 +3453,12 @@ lpfc_send_taskmgmt(struct lpfc_vport *vport, struct lpfc_rport_data *rdata, | |||
3419 | ret = FAILED; | 3453 | ret = FAILED; |
3420 | lpfc_cmd->status = IOSTAT_DRIVER_REJECT; | 3454 | lpfc_cmd->status = IOSTAT_DRIVER_REJECT; |
3421 | lpfc_printf_vlog(vport, KERN_ERR, LOG_FCP, | 3455 | lpfc_printf_vlog(vport, KERN_ERR, LOG_FCP, |
3422 | "0727 TMF %s to TGT %d LUN %d failed (%d, %d)\n", | 3456 | "0727 TMF %s to TGT %d LUN %d failed (%d, %d) " |
3457 | "iocb_flag x%x\n", | ||
3423 | lpfc_taskmgmt_name(task_mgmt_cmd), | 3458 | lpfc_taskmgmt_name(task_mgmt_cmd), |
3424 | tgt_id, lun_id, iocbqrsp->iocb.ulpStatus, | 3459 | tgt_id, lun_id, iocbqrsp->iocb.ulpStatus, |
3425 | iocbqrsp->iocb.un.ulpWord[4]); | 3460 | iocbqrsp->iocb.un.ulpWord[4], |
3461 | iocbq->iocb_flag); | ||
3426 | } else if (status == IOCB_BUSY) | 3462 | } else if (status == IOCB_BUSY) |
3427 | ret = FAILED; | 3463 | ret = FAILED; |
3428 | else | 3464 | else |