diff options
| -rw-r--r-- | drivers/scsi/lpfc/lpfc_bsg.c | 358 | ||||
| -rw-r--r-- | drivers/scsi/lpfc/lpfc_crtn.h | 9 | ||||
| -rw-r--r-- | drivers/scsi/lpfc/lpfc_els.c | 125 | ||||
| -rw-r--r-- | drivers/scsi/lpfc/lpfc_hbadisc.c | 60 | ||||
| -rw-r--r-- | drivers/scsi/lpfc/lpfc_hw.h | 2 | ||||
| -rw-r--r-- | drivers/scsi/lpfc/lpfc_hw4.h | 7 | ||||
| -rw-r--r-- | drivers/scsi/lpfc/lpfc_init.c | 40 | ||||
| -rw-r--r-- | drivers/scsi/lpfc/lpfc_mbox.c | 8 | ||||
| -rw-r--r-- | drivers/scsi/lpfc/lpfc_sli.c | 28 |
9 files changed, 470 insertions, 167 deletions
diff --git a/drivers/scsi/lpfc/lpfc_bsg.c b/drivers/scsi/lpfc/lpfc_bsg.c index c13e54760cb1..56a86baece5b 100644 --- a/drivers/scsi/lpfc/lpfc_bsg.c +++ b/drivers/scsi/lpfc/lpfc_bsg.c | |||
| @@ -916,9 +916,11 @@ lpfc_bsg_ct_unsol_event(struct lpfc_hba *phba, struct lpfc_sli_ring *pring, | |||
| 916 | } else { | 916 | } else { |
| 917 | switch (cmd) { | 917 | switch (cmd) { |
| 918 | case ELX_LOOPBACK_DATA: | 918 | case ELX_LOOPBACK_DATA: |
| 919 | diag_cmd_data_free(phba, | 919 | if (phba->sli_rev < |
| 920 | (struct lpfc_dmabufext *) | 920 | LPFC_SLI_REV4) |
| 921 | dmabuf); | 921 | diag_cmd_data_free(phba, |
| 922 | (struct lpfc_dmabufext | ||
| 923 | *)dmabuf); | ||
| 922 | break; | 924 | break; |
| 923 | case ELX_LOOPBACK_XRI_SETUP: | 925 | case ELX_LOOPBACK_XRI_SETUP: |
| 924 | if ((phba->sli_rev == | 926 | if ((phba->sli_rev == |
| @@ -1000,7 +1002,8 @@ lpfc_bsg_ct_unsol_event(struct lpfc_hba *phba, struct lpfc_sli_ring *pring, | |||
| 1000 | error_ct_unsol_exit: | 1002 | error_ct_unsol_exit: |
| 1001 | if (!list_empty(&head)) | 1003 | if (!list_empty(&head)) |
| 1002 | list_del(&head); | 1004 | list_del(&head); |
| 1003 | if (evt_req_id == SLI_CT_ELX_LOOPBACK) | 1005 | if ((phba->sli_rev < LPFC_SLI_REV4) && |
| 1006 | (evt_req_id == SLI_CT_ELX_LOOPBACK)) | ||
| 1004 | return 0; | 1007 | return 0; |
| 1005 | return 1; | 1008 | return 1; |
| 1006 | } | 1009 | } |
| @@ -1566,7 +1569,7 @@ lpfc_sli3_bsg_diag_loopback_mode(struct lpfc_hba *phba, struct fc_bsg_job *job) | |||
| 1566 | struct diag_mode_set *loopback_mode; | 1569 | struct diag_mode_set *loopback_mode; |
| 1567 | uint32_t link_flags; | 1570 | uint32_t link_flags; |
| 1568 | uint32_t timeout; | 1571 | uint32_t timeout; |
| 1569 | LPFC_MBOXQ_t *pmboxq; | 1572 | LPFC_MBOXQ_t *pmboxq = NULL; |
| 1570 | int mbxstatus = MBX_SUCCESS; | 1573 | int mbxstatus = MBX_SUCCESS; |
| 1571 | int i = 0; | 1574 | int i = 0; |
| 1572 | int rc = 0; | 1575 | int rc = 0; |
| @@ -1615,7 +1618,6 @@ lpfc_sli3_bsg_diag_loopback_mode(struct lpfc_hba *phba, struct fc_bsg_job *job) | |||
| 1615 | rc = -ETIMEDOUT; | 1618 | rc = -ETIMEDOUT; |
| 1616 | goto loopback_mode_exit; | 1619 | goto loopback_mode_exit; |
| 1617 | } | 1620 | } |
| 1618 | |||
| 1619 | msleep(10); | 1621 | msleep(10); |
| 1620 | } | 1622 | } |
| 1621 | 1623 | ||
| @@ -1635,7 +1637,9 @@ lpfc_sli3_bsg_diag_loopback_mode(struct lpfc_hba *phba, struct fc_bsg_job *job) | |||
| 1635 | if ((mbxstatus != MBX_SUCCESS) || (pmboxq->u.mb.mbxStatus)) | 1637 | if ((mbxstatus != MBX_SUCCESS) || (pmboxq->u.mb.mbxStatus)) |
| 1636 | rc = -ENODEV; | 1638 | rc = -ENODEV; |
| 1637 | else { | 1639 | else { |
| 1640 | spin_lock_irq(&phba->hbalock); | ||
| 1638 | phba->link_flag |= LS_LOOPBACK_MODE; | 1641 | phba->link_flag |= LS_LOOPBACK_MODE; |
| 1642 | spin_unlock_irq(&phba->hbalock); | ||
| 1639 | /* wait for the link attention interrupt */ | 1643 | /* wait for the link attention interrupt */ |
| 1640 | msleep(100); | 1644 | msleep(100); |
| 1641 | 1645 | ||
| @@ -1659,7 +1663,7 @@ loopback_mode_exit: | |||
| 1659 | /* | 1663 | /* |
| 1660 | * Let SLI layer release mboxq if mbox command completed after timeout. | 1664 | * Let SLI layer release mboxq if mbox command completed after timeout. |
| 1661 | */ | 1665 | */ |
| 1662 | if (mbxstatus != MBX_TIMEOUT) | 1666 | if (pmboxq && mbxstatus != MBX_TIMEOUT) |
| 1663 | mempool_free(pmboxq, phba->mbox_mem_pool); | 1667 | mempool_free(pmboxq, phba->mbox_mem_pool); |
| 1664 | 1668 | ||
| 1665 | job_error: | 1669 | job_error: |
| @@ -1700,11 +1704,16 @@ lpfc_sli4_bsg_set_link_diag_state(struct lpfc_hba *phba, uint32_t diag) | |||
| 1700 | rc = -ENOMEM; | 1704 | rc = -ENOMEM; |
| 1701 | goto link_diag_state_set_out; | 1705 | goto link_diag_state_set_out; |
| 1702 | } | 1706 | } |
| 1707 | lpfc_printf_log(phba, KERN_INFO, LOG_LIBDFC, | ||
| 1708 | "3128 Set link to diagnostic state:x%x (x%x/x%x)\n", | ||
| 1709 | diag, phba->sli4_hba.lnk_info.lnk_tp, | ||
| 1710 | phba->sli4_hba.lnk_info.lnk_no); | ||
| 1711 | |||
| 1703 | link_diag_state = &pmboxq->u.mqe.un.link_diag_state; | 1712 | link_diag_state = &pmboxq->u.mqe.un.link_diag_state; |
| 1704 | bf_set(lpfc_mbx_set_diag_state_link_num, &link_diag_state->u.req, | 1713 | bf_set(lpfc_mbx_set_diag_state_link_num, &link_diag_state->u.req, |
| 1705 | phba->sli4_hba.link_state.number); | 1714 | phba->sli4_hba.lnk_info.lnk_no); |
| 1706 | bf_set(lpfc_mbx_set_diag_state_link_type, &link_diag_state->u.req, | 1715 | bf_set(lpfc_mbx_set_diag_state_link_type, &link_diag_state->u.req, |
| 1707 | phba->sli4_hba.link_state.type); | 1716 | phba->sli4_hba.lnk_info.lnk_tp); |
| 1708 | if (diag) | 1717 | if (diag) |
| 1709 | bf_set(lpfc_mbx_set_diag_state_diag, | 1718 | bf_set(lpfc_mbx_set_diag_state_diag, |
| 1710 | &link_diag_state->u.req, 1); | 1719 | &link_diag_state->u.req, 1); |
| @@ -1727,6 +1736,79 @@ link_diag_state_set_out: | |||
| 1727 | } | 1736 | } |
| 1728 | 1737 | ||
| 1729 | /** | 1738 | /** |
| 1739 | * lpfc_sli4_bsg_set_internal_loopback - set sli4 internal loopback diagnostic | ||
| 1740 | * @phba: Pointer to HBA context object. | ||
| 1741 | * | ||
| 1742 | * This function is responsible for issuing a sli4 mailbox command for setting | ||
| 1743 | * up internal loopback diagnostic. | ||
| 1744 | */ | ||
| 1745 | static int | ||
| 1746 | lpfc_sli4_bsg_set_internal_loopback(struct lpfc_hba *phba) | ||
| 1747 | { | ||
| 1748 | LPFC_MBOXQ_t *pmboxq; | ||
| 1749 | uint32_t req_len, alloc_len; | ||
| 1750 | struct lpfc_mbx_set_link_diag_loopback *link_diag_loopback; | ||
| 1751 | int mbxstatus = MBX_SUCCESS, rc = 0; | ||
| 1752 | |||
| 1753 | pmboxq = mempool_alloc(phba->mbox_mem_pool, GFP_KERNEL); | ||
| 1754 | if (!pmboxq) | ||
| 1755 | return -ENOMEM; | ||
| 1756 | req_len = (sizeof(struct lpfc_mbx_set_link_diag_loopback) - | ||
| 1757 | sizeof(struct lpfc_sli4_cfg_mhdr)); | ||
| 1758 | alloc_len = lpfc_sli4_config(phba, pmboxq, LPFC_MBOX_SUBSYSTEM_FCOE, | ||
| 1759 | LPFC_MBOX_OPCODE_FCOE_LINK_DIAG_LOOPBACK, | ||
| 1760 | req_len, LPFC_SLI4_MBX_EMBED); | ||
| 1761 | if (alloc_len != req_len) { | ||
| 1762 | mempool_free(pmboxq, phba->mbox_mem_pool); | ||
| 1763 | return -ENOMEM; | ||
| 1764 | } | ||
| 1765 | link_diag_loopback = &pmboxq->u.mqe.un.link_diag_loopback; | ||
| 1766 | bf_set(lpfc_mbx_set_diag_state_link_num, | ||
| 1767 | &link_diag_loopback->u.req, phba->sli4_hba.lnk_info.lnk_no); | ||
| 1768 | bf_set(lpfc_mbx_set_diag_state_link_type, | ||
| 1769 | &link_diag_loopback->u.req, phba->sli4_hba.lnk_info.lnk_tp); | ||
| 1770 | bf_set(lpfc_mbx_set_diag_lpbk_type, &link_diag_loopback->u.req, | ||
| 1771 | LPFC_DIAG_LOOPBACK_TYPE_SERDES); | ||
| 1772 | |||
| 1773 | mbxstatus = lpfc_sli_issue_mbox_wait(phba, pmboxq, LPFC_MBOX_TMO); | ||
| 1774 | if ((mbxstatus != MBX_SUCCESS) || (pmboxq->u.mb.mbxStatus)) { | ||
| 1775 | lpfc_printf_log(phba, KERN_WARNING, LOG_LIBDFC, | ||
| 1776 | "3127 Failed setup loopback mode mailbox " | ||
| 1777 | "command, rc:x%x, status:x%x\n", mbxstatus, | ||
| 1778 | pmboxq->u.mb.mbxStatus); | ||
| 1779 | rc = -ENODEV; | ||
| 1780 | } | ||
| 1781 | if (pmboxq && (mbxstatus != MBX_TIMEOUT)) | ||
| 1782 | mempool_free(pmboxq, phba->mbox_mem_pool); | ||
| 1783 | return rc; | ||
| 1784 | } | ||
| 1785 | |||
| 1786 | /** | ||
| 1787 | * lpfc_sli4_diag_fcport_reg_setup - setup port registrations for diagnostic | ||
| 1788 | * @phba: Pointer to HBA context object. | ||
| 1789 | * | ||
| 1790 | * This function set up SLI4 FC port registrations for diagnostic run, which | ||
| 1791 | * includes all the rpis, vfi, and also vpi. | ||
| 1792 | */ | ||
| 1793 | static int | ||
| 1794 | lpfc_sli4_diag_fcport_reg_setup(struct lpfc_hba *phba) | ||
| 1795 | { | ||
| 1796 | int rc; | ||
| 1797 | |||
| 1798 | if (phba->pport->fc_flag & FC_VFI_REGISTERED) { | ||
| 1799 | lpfc_printf_log(phba, KERN_WARNING, LOG_LIBDFC, | ||
| 1800 | "3136 Port still had vfi registered: " | ||
| 1801 | "mydid:x%x, fcfi:%d, vfi:%d, vpi:%d\n", | ||
| 1802 | phba->pport->fc_myDID, phba->fcf.fcfi, | ||
| 1803 | phba->sli4_hba.vfi_ids[phba->pport->vfi], | ||
| 1804 | phba->vpi_ids[phba->pport->vpi]); | ||
| 1805 | return -EINVAL; | ||
| 1806 | } | ||
| 1807 | rc = lpfc_issue_reg_vfi(phba->pport); | ||
| 1808 | return rc; | ||
| 1809 | } | ||
| 1810 | |||
| 1811 | /** | ||
| 1730 | * lpfc_sli4_bsg_diag_loopback_mode - process an sli4 bsg vendor command | 1812 | * lpfc_sli4_bsg_diag_loopback_mode - process an sli4 bsg vendor command |
| 1731 | * @phba: Pointer to HBA context object. | 1813 | * @phba: Pointer to HBA context object. |
| 1732 | * @job: LPFC_BSG_VENDOR_DIAG_MODE | 1814 | * @job: LPFC_BSG_VENDOR_DIAG_MODE |
| @@ -1738,10 +1820,8 @@ static int | |||
| 1738 | lpfc_sli4_bsg_diag_loopback_mode(struct lpfc_hba *phba, struct fc_bsg_job *job) | 1820 | lpfc_sli4_bsg_diag_loopback_mode(struct lpfc_hba *phba, struct fc_bsg_job *job) |
| 1739 | { | 1821 | { |
| 1740 | struct diag_mode_set *loopback_mode; | 1822 | struct diag_mode_set *loopback_mode; |
| 1741 | uint32_t link_flags, timeout, req_len, alloc_len; | 1823 | uint32_t link_flags, timeout; |
| 1742 | struct lpfc_mbx_set_link_diag_loopback *link_diag_loopback; | 1824 | int i, rc = 0; |
| 1743 | LPFC_MBOXQ_t *pmboxq = NULL; | ||
| 1744 | int mbxstatus = MBX_SUCCESS, i, rc = 0; | ||
| 1745 | 1825 | ||
| 1746 | /* no data to return just the return code */ | 1826 | /* no data to return just the return code */ |
| 1747 | job->reply->reply_payload_rcv_len = 0; | 1827 | job->reply->reply_payload_rcv_len = 0; |
| @@ -1762,65 +1842,100 @@ lpfc_sli4_bsg_diag_loopback_mode(struct lpfc_hba *phba, struct fc_bsg_job *job) | |||
| 1762 | if (rc) | 1842 | if (rc) |
| 1763 | goto job_error; | 1843 | goto job_error; |
| 1764 | 1844 | ||
| 1845 | /* indicate we are in loobpack diagnostic mode */ | ||
| 1846 | spin_lock_irq(&phba->hbalock); | ||
| 1847 | phba->link_flag |= LS_LOOPBACK_MODE; | ||
| 1848 | spin_unlock_irq(&phba->hbalock); | ||
| 1849 | |||
| 1850 | /* reset port to start frome scratch */ | ||
| 1851 | rc = lpfc_selective_reset(phba); | ||
| 1852 | if (rc) | ||
| 1853 | goto job_error; | ||
| 1854 | |||
| 1765 | /* bring the link to diagnostic mode */ | 1855 | /* bring the link to diagnostic mode */ |
| 1856 | lpfc_printf_log(phba, KERN_INFO, LOG_LIBDFC, | ||
| 1857 | "3129 Bring link to diagnostic state.\n"); | ||
| 1766 | loopback_mode = (struct diag_mode_set *) | 1858 | loopback_mode = (struct diag_mode_set *) |
| 1767 | job->request->rqst_data.h_vendor.vendor_cmd; | 1859 | job->request->rqst_data.h_vendor.vendor_cmd; |
| 1768 | link_flags = loopback_mode->type; | 1860 | link_flags = loopback_mode->type; |
| 1769 | timeout = loopback_mode->timeout * 100; | 1861 | timeout = loopback_mode->timeout * 100; |
| 1770 | 1862 | ||
| 1771 | rc = lpfc_sli4_bsg_set_link_diag_state(phba, 1); | 1863 | rc = lpfc_sli4_bsg_set_link_diag_state(phba, 1); |
| 1772 | if (rc) | 1864 | if (rc) { |
| 1865 | lpfc_printf_log(phba, KERN_WARNING, LOG_LIBDFC, | ||
| 1866 | "3130 Failed to bring link to diagnostic " | ||
| 1867 | "state, rc:x%x\n", rc); | ||
| 1773 | goto loopback_mode_exit; | 1868 | goto loopback_mode_exit; |
| 1869 | } | ||
| 1774 | 1870 | ||
| 1775 | /* wait for link down before proceeding */ | 1871 | /* wait for link down before proceeding */ |
| 1776 | i = 0; | 1872 | i = 0; |
| 1777 | while (phba->link_state != LPFC_LINK_DOWN) { | 1873 | while (phba->link_state != LPFC_LINK_DOWN) { |
| 1778 | if (i++ > timeout) { | 1874 | if (i++ > timeout) { |
| 1779 | rc = -ETIMEDOUT; | 1875 | rc = -ETIMEDOUT; |
| 1876 | lpfc_printf_log(phba, KERN_INFO, LOG_LIBDFC, | ||
| 1877 | "3131 Timeout waiting for link to " | ||
| 1878 | "diagnostic mode, timeout:%d ms\n", | ||
| 1879 | timeout * 10); | ||
| 1780 | goto loopback_mode_exit; | 1880 | goto loopback_mode_exit; |
| 1781 | } | 1881 | } |
| 1782 | msleep(10); | 1882 | msleep(10); |
| 1783 | } | 1883 | } |
| 1884 | |||
| 1784 | /* set up loopback mode */ | 1885 | /* set up loopback mode */ |
| 1785 | pmboxq = mempool_alloc(phba->mbox_mem_pool, GFP_KERNEL); | 1886 | lpfc_printf_log(phba, KERN_INFO, LOG_LIBDFC, |
| 1786 | if (!pmboxq) { | 1887 | "3132 Set up loopback mode:x%x\n", link_flags); |
| 1787 | rc = -ENOMEM; | 1888 | |
| 1788 | goto loopback_mode_exit; | 1889 | if (link_flags == INTERNAL_LOOP_BACK) |
| 1789 | } | 1890 | rc = lpfc_sli4_bsg_set_internal_loopback(phba); |
| 1790 | req_len = (sizeof(struct lpfc_mbx_set_link_diag_loopback) - | 1891 | else if (link_flags == EXTERNAL_LOOP_BACK) |
| 1791 | sizeof(struct lpfc_sli4_cfg_mhdr)); | 1892 | rc = lpfc_hba_init_link_fc_topology(phba, |
| 1792 | alloc_len = lpfc_sli4_config(phba, pmboxq, LPFC_MBOX_SUBSYSTEM_FCOE, | 1893 | FLAGS_TOPOLOGY_MODE_PT_PT, |
| 1793 | LPFC_MBOX_OPCODE_FCOE_LINK_DIAG_LOOPBACK, | 1894 | MBX_NOWAIT); |
| 1794 | req_len, LPFC_SLI4_MBX_EMBED); | 1895 | else { |
| 1795 | if (alloc_len != req_len) { | 1896 | rc = -EINVAL; |
| 1796 | rc = -ENOMEM; | 1897 | lpfc_printf_log(phba, KERN_ERR, LOG_LIBDFC, |
| 1898 | "3141 Loopback mode:x%x not supported\n", | ||
| 1899 | link_flags); | ||
| 1797 | goto loopback_mode_exit; | 1900 | goto loopback_mode_exit; |
| 1798 | } | 1901 | } |
| 1799 | link_diag_loopback = &pmboxq->u.mqe.un.link_diag_loopback; | ||
| 1800 | bf_set(lpfc_mbx_set_diag_state_link_num, | ||
| 1801 | &link_diag_loopback->u.req, phba->sli4_hba.link_state.number); | ||
| 1802 | bf_set(lpfc_mbx_set_diag_state_link_type, | ||
| 1803 | &link_diag_loopback->u.req, phba->sli4_hba.link_state.type); | ||
| 1804 | if (link_flags == INTERNAL_LOOP_BACK) | ||
| 1805 | bf_set(lpfc_mbx_set_diag_lpbk_type, | ||
| 1806 | &link_diag_loopback->u.req, | ||
| 1807 | LPFC_DIAG_LOOPBACK_TYPE_INTERNAL); | ||
| 1808 | else | ||
| 1809 | bf_set(lpfc_mbx_set_diag_lpbk_type, | ||
| 1810 | &link_diag_loopback->u.req, | ||
| 1811 | LPFC_DIAG_LOOPBACK_TYPE_EXTERNAL); | ||
| 1812 | 1902 | ||
| 1813 | mbxstatus = lpfc_sli_issue_mbox_wait(phba, pmboxq, LPFC_MBOX_TMO); | 1903 | if (!rc) { |
| 1814 | if ((mbxstatus != MBX_SUCCESS) || (pmboxq->u.mb.mbxStatus)) | ||
| 1815 | rc = -ENODEV; | ||
| 1816 | else { | ||
| 1817 | phba->link_flag |= LS_LOOPBACK_MODE; | ||
| 1818 | /* wait for the link attention interrupt */ | 1904 | /* wait for the link attention interrupt */ |
| 1819 | msleep(100); | 1905 | msleep(100); |
| 1820 | i = 0; | 1906 | i = 0; |
| 1907 | while (phba->link_state < LPFC_LINK_UP) { | ||
| 1908 | if (i++ > timeout) { | ||
| 1909 | rc = -ETIMEDOUT; | ||
| 1910 | lpfc_printf_log(phba, KERN_INFO, LOG_LIBDFC, | ||
| 1911 | "3137 Timeout waiting for link up " | ||
| 1912 | "in loopback mode, timeout:%d ms\n", | ||
| 1913 | timeout * 10); | ||
| 1914 | break; | ||
| 1915 | } | ||
| 1916 | msleep(10); | ||
| 1917 | } | ||
| 1918 | } | ||
| 1919 | |||
| 1920 | /* port resource registration setup for loopback diagnostic */ | ||
| 1921 | if (!rc) { | ||
| 1922 | /* set up a none zero myDID for loopback test */ | ||
| 1923 | phba->pport->fc_myDID = 1; | ||
| 1924 | rc = lpfc_sli4_diag_fcport_reg_setup(phba); | ||
| 1925 | } else | ||
| 1926 | goto loopback_mode_exit; | ||
| 1927 | |||
| 1928 | if (!rc) { | ||
| 1929 | /* wait for the port ready */ | ||
| 1930 | msleep(100); | ||
| 1931 | i = 0; | ||
| 1821 | while (phba->link_state != LPFC_HBA_READY) { | 1932 | while (phba->link_state != LPFC_HBA_READY) { |
| 1822 | if (i++ > timeout) { | 1933 | if (i++ > timeout) { |
| 1823 | rc = -ETIMEDOUT; | 1934 | rc = -ETIMEDOUT; |
| 1935 | lpfc_printf_log(phba, KERN_INFO, LOG_LIBDFC, | ||
| 1936 | "3133 Timeout waiting for port " | ||
| 1937 | "loopback mode ready, timeout:%d ms\n", | ||
| 1938 | timeout * 10); | ||
| 1824 | break; | 1939 | break; |
| 1825 | } | 1940 | } |
| 1826 | msleep(10); | 1941 | msleep(10); |
| @@ -1828,14 +1943,14 @@ lpfc_sli4_bsg_diag_loopback_mode(struct lpfc_hba *phba, struct fc_bsg_job *job) | |||
| 1828 | } | 1943 | } |
| 1829 | 1944 | ||
| 1830 | loopback_mode_exit: | 1945 | loopback_mode_exit: |
| 1946 | /* clear loopback diagnostic mode */ | ||
| 1947 | if (rc) { | ||
| 1948 | spin_lock_irq(&phba->hbalock); | ||
| 1949 | phba->link_flag &= ~LS_LOOPBACK_MODE; | ||
| 1950 | spin_unlock_irq(&phba->hbalock); | ||
| 1951 | } | ||
| 1831 | lpfc_bsg_diag_mode_exit(phba); | 1952 | lpfc_bsg_diag_mode_exit(phba); |
| 1832 | 1953 | ||
| 1833 | /* | ||
| 1834 | * Let SLI layer release mboxq if mbox command completed after timeout. | ||
| 1835 | */ | ||
| 1836 | if (pmboxq && (mbxstatus != MBX_TIMEOUT)) | ||
| 1837 | mempool_free(pmboxq, phba->mbox_mem_pool); | ||
| 1838 | |||
| 1839 | job_error: | 1954 | job_error: |
| 1840 | /* make error code available to userspace */ | 1955 | /* make error code available to userspace */ |
| 1841 | job->reply->result = rc; | 1956 | job->reply->result = rc; |
| @@ -1879,7 +1994,6 @@ lpfc_bsg_diag_loopback_mode(struct fc_bsg_job *job) | |||
| 1879 | rc = -ENODEV; | 1994 | rc = -ENODEV; |
| 1880 | 1995 | ||
| 1881 | return rc; | 1996 | return rc; |
| 1882 | |||
| 1883 | } | 1997 | } |
| 1884 | 1998 | ||
| 1885 | /** | 1999 | /** |
| @@ -1895,7 +2009,9 @@ lpfc_sli4_bsg_diag_mode_end(struct fc_bsg_job *job) | |||
| 1895 | struct Scsi_Host *shost; | 2009 | struct Scsi_Host *shost; |
| 1896 | struct lpfc_vport *vport; | 2010 | struct lpfc_vport *vport; |
| 1897 | struct lpfc_hba *phba; | 2011 | struct lpfc_hba *phba; |
| 1898 | int rc; | 2012 | struct diag_mode_set *loopback_mode_end_cmd; |
| 2013 | uint32_t timeout; | ||
| 2014 | int rc, i; | ||
| 1899 | 2015 | ||
| 1900 | shost = job->shost; | 2016 | shost = job->shost; |
| 1901 | if (!shost) | 2017 | if (!shost) |
| @@ -1913,11 +2029,47 @@ lpfc_sli4_bsg_diag_mode_end(struct fc_bsg_job *job) | |||
| 1913 | LPFC_SLI_INTF_IF_TYPE_2) | 2029 | LPFC_SLI_INTF_IF_TYPE_2) |
| 1914 | return -ENODEV; | 2030 | return -ENODEV; |
| 1915 | 2031 | ||
| 2032 | /* clear loopback diagnostic mode */ | ||
| 2033 | spin_lock_irq(&phba->hbalock); | ||
| 2034 | phba->link_flag &= ~LS_LOOPBACK_MODE; | ||
| 2035 | spin_unlock_irq(&phba->hbalock); | ||
| 2036 | loopback_mode_end_cmd = (struct diag_mode_set *) | ||
| 2037 | job->request->rqst_data.h_vendor.vendor_cmd; | ||
| 2038 | timeout = loopback_mode_end_cmd->timeout * 100; | ||
| 2039 | |||
| 1916 | rc = lpfc_sli4_bsg_set_link_diag_state(phba, 0); | 2040 | rc = lpfc_sli4_bsg_set_link_diag_state(phba, 0); |
| 2041 | if (rc) { | ||
| 2042 | lpfc_printf_log(phba, KERN_WARNING, LOG_LIBDFC, | ||
| 2043 | "3139 Failed to bring link to diagnostic " | ||
| 2044 | "state, rc:x%x\n", rc); | ||
| 2045 | goto loopback_mode_end_exit; | ||
| 2046 | } | ||
| 2047 | |||
| 2048 | /* wait for link down before proceeding */ | ||
| 2049 | i = 0; | ||
| 2050 | while (phba->link_state != LPFC_LINK_DOWN) { | ||
| 2051 | if (i++ > timeout) { | ||
| 2052 | rc = -ETIMEDOUT; | ||
| 2053 | lpfc_printf_log(phba, KERN_INFO, LOG_LIBDFC, | ||
| 2054 | "3140 Timeout waiting for link to " | ||
| 2055 | "diagnostic mode_end, timeout:%d ms\n", | ||
| 2056 | timeout * 10); | ||
| 2057 | /* there is nothing much we can do here */ | ||
| 2058 | break; | ||
| 2059 | } | ||
| 2060 | msleep(10); | ||
| 2061 | } | ||
| 1917 | 2062 | ||
| 1918 | if (!rc) | 2063 | /* reset port resource registrations */ |
| 1919 | rc = phba->lpfc_hba_init_link(phba, MBX_NOWAIT); | 2064 | rc = lpfc_selective_reset(phba); |
| 2065 | phba->pport->fc_myDID = 0; | ||
| 1920 | 2066 | ||
| 2067 | loopback_mode_end_exit: | ||
| 2068 | /* make return code available to userspace */ | ||
| 2069 | job->reply->result = rc; | ||
| 2070 | /* complete the job back to userspace if no error */ | ||
| 2071 | if (rc == 0) | ||
| 2072 | job->job_done(job); | ||
| 1921 | return rc; | 2073 | return rc; |
| 1922 | } | 2074 | } |
| 1923 | 2075 | ||
| @@ -2012,9 +2164,9 @@ lpfc_sli4_bsg_link_diag_test(struct fc_bsg_job *job) | |||
| 2012 | } | 2164 | } |
| 2013 | run_link_diag_test = &pmboxq->u.mqe.un.link_diag_test; | 2165 | run_link_diag_test = &pmboxq->u.mqe.un.link_diag_test; |
| 2014 | bf_set(lpfc_mbx_run_diag_test_link_num, &run_link_diag_test->u.req, | 2166 | bf_set(lpfc_mbx_run_diag_test_link_num, &run_link_diag_test->u.req, |
| 2015 | phba->sli4_hba.link_state.number); | 2167 | phba->sli4_hba.lnk_info.lnk_no); |
| 2016 | bf_set(lpfc_mbx_run_diag_test_link_type, &run_link_diag_test->u.req, | 2168 | bf_set(lpfc_mbx_run_diag_test_link_type, &run_link_diag_test->u.req, |
| 2017 | phba->sli4_hba.link_state.type); | 2169 | phba->sli4_hba.lnk_info.lnk_tp); |
| 2018 | bf_set(lpfc_mbx_run_diag_test_test_id, &run_link_diag_test->u.req, | 2170 | bf_set(lpfc_mbx_run_diag_test_test_id, &run_link_diag_test->u.req, |
| 2019 | link_diag_test_cmd->test_id); | 2171 | link_diag_test_cmd->test_id); |
| 2020 | bf_set(lpfc_mbx_run_diag_test_loops, &run_link_diag_test->u.req, | 2172 | bf_set(lpfc_mbx_run_diag_test_loops, &run_link_diag_test->u.req, |
| @@ -2091,10 +2243,18 @@ static int lpfcdiag_loop_self_reg(struct lpfc_hba *phba, uint16_t *rpi) | |||
| 2091 | if (!mbox) | 2243 | if (!mbox) |
| 2092 | return -ENOMEM; | 2244 | return -ENOMEM; |
| 2093 | 2245 | ||
| 2094 | if (phba->sli_rev == LPFC_SLI_REV4) | 2246 | if (phba->sli_rev < LPFC_SLI_REV4) |
| 2247 | status = lpfc_reg_rpi(phba, 0, phba->pport->fc_myDID, | ||
| 2248 | (uint8_t *)&phba->pport->fc_sparam, | ||
| 2249 | mbox, *rpi); | ||
| 2250 | else { | ||
| 2095 | *rpi = lpfc_sli4_alloc_rpi(phba); | 2251 | *rpi = lpfc_sli4_alloc_rpi(phba); |
| 2096 | status = lpfc_reg_rpi(phba, 0, phba->pport->fc_myDID, | 2252 | status = lpfc_reg_rpi(phba, phba->pport->vpi, |
| 2097 | (uint8_t *)&phba->pport->fc_sparam, mbox, *rpi); | 2253 | phba->pport->fc_myDID, |
| 2254 | (uint8_t *)&phba->pport->fc_sparam, | ||
| 2255 | mbox, *rpi); | ||
| 2256 | } | ||
| 2257 | |||
| 2098 | if (status) { | 2258 | if (status) { |
| 2099 | mempool_free(mbox, phba->mbox_mem_pool); | 2259 | mempool_free(mbox, phba->mbox_mem_pool); |
| 2100 | if (phba->sli_rev == LPFC_SLI_REV4) | 2260 | if (phba->sli_rev == LPFC_SLI_REV4) |
| @@ -2117,7 +2277,8 @@ static int lpfcdiag_loop_self_reg(struct lpfc_hba *phba, uint16_t *rpi) | |||
| 2117 | return -ENODEV; | 2277 | return -ENODEV; |
| 2118 | } | 2278 | } |
| 2119 | 2279 | ||
| 2120 | *rpi = mbox->u.mb.un.varWords[0]; | 2280 | if (phba->sli_rev < LPFC_SLI_REV4) |
| 2281 | *rpi = mbox->u.mb.un.varWords[0]; | ||
| 2121 | 2282 | ||
| 2122 | lpfc_mbuf_free(phba, dmabuff->virt, dmabuff->phys); | 2283 | lpfc_mbuf_free(phba, dmabuff->virt, dmabuff->phys); |
| 2123 | kfree(dmabuff); | 2284 | kfree(dmabuff); |
| @@ -2142,7 +2303,12 @@ static int lpfcdiag_loop_self_unreg(struct lpfc_hba *phba, uint16_t rpi) | |||
| 2142 | if (mbox == NULL) | 2303 | if (mbox == NULL) |
| 2143 | return -ENOMEM; | 2304 | return -ENOMEM; |
| 2144 | 2305 | ||
| 2145 | lpfc_unreg_login(phba, 0, rpi, mbox); | 2306 | if (phba->sli_rev < LPFC_SLI_REV4) |
| 2307 | lpfc_unreg_login(phba, 0, rpi, mbox); | ||
| 2308 | else | ||
| 2309 | lpfc_unreg_login(phba, phba->pport->vpi, | ||
| 2310 | phba->sli4_hba.rpi_ids[rpi], mbox); | ||
| 2311 | |||
| 2146 | status = lpfc_sli_issue_mbox_wait(phba, mbox, LPFC_MBOX_TMO); | 2312 | status = lpfc_sli_issue_mbox_wait(phba, mbox, LPFC_MBOX_TMO); |
| 2147 | 2313 | ||
| 2148 | if ((status != MBX_SUCCESS) || (mbox->u.mb.mbxStatus)) { | 2314 | if ((status != MBX_SUCCESS) || (mbox->u.mb.mbxStatus)) { |
| @@ -2630,15 +2796,15 @@ lpfc_bsg_diag_loopback_run(struct fc_bsg_job *job) | |||
| 2630 | uint32_t full_size; | 2796 | uint32_t full_size; |
| 2631 | size_t segment_len = 0, segment_offset = 0, current_offset = 0; | 2797 | size_t segment_len = 0, segment_offset = 0, current_offset = 0; |
| 2632 | uint16_t rpi = 0; | 2798 | uint16_t rpi = 0; |
| 2633 | struct lpfc_iocbq *cmdiocbq, *rspiocbq; | 2799 | struct lpfc_iocbq *cmdiocbq, *rspiocbq = NULL; |
| 2634 | IOCB_t *cmd, *rsp; | 2800 | IOCB_t *cmd, *rsp = NULL; |
| 2635 | struct lpfc_sli_ct_request *ctreq; | 2801 | struct lpfc_sli_ct_request *ctreq; |
| 2636 | struct lpfc_dmabuf *txbmp; | 2802 | struct lpfc_dmabuf *txbmp; |
| 2637 | struct ulp_bde64 *txbpl = NULL; | 2803 | struct ulp_bde64 *txbpl = NULL; |
| 2638 | struct lpfc_dmabufext *txbuffer = NULL; | 2804 | struct lpfc_dmabufext *txbuffer = NULL; |
| 2639 | struct list_head head; | 2805 | struct list_head head; |
| 2640 | struct lpfc_dmabuf *curr; | 2806 | struct lpfc_dmabuf *curr; |
| 2641 | uint16_t txxri, rxxri; | 2807 | uint16_t txxri = 0, rxxri; |
| 2642 | uint32_t num_bde; | 2808 | uint32_t num_bde; |
| 2643 | uint8_t *ptr = NULL, *rx_databuf = NULL; | 2809 | uint8_t *ptr = NULL, *rx_databuf = NULL; |
| 2644 | int rc = 0; | 2810 | int rc = 0; |
| @@ -2665,7 +2831,6 @@ lpfc_bsg_diag_loopback_run(struct fc_bsg_job *job) | |||
| 2665 | rc = -EINVAL; | 2831 | rc = -EINVAL; |
| 2666 | goto loopback_test_exit; | 2832 | goto loopback_test_exit; |
| 2667 | } | 2833 | } |
| 2668 | |||
| 2669 | diag_mode = (struct diag_mode_test *) | 2834 | diag_mode = (struct diag_mode_test *) |
| 2670 | job->request->rqst_data.h_vendor.vendor_cmd; | 2835 | job->request->rqst_data.h_vendor.vendor_cmd; |
| 2671 | 2836 | ||
| @@ -2720,18 +2885,19 @@ lpfc_bsg_diag_loopback_run(struct fc_bsg_job *job) | |||
| 2720 | if (rc) | 2885 | if (rc) |
| 2721 | goto loopback_test_exit; | 2886 | goto loopback_test_exit; |
| 2722 | 2887 | ||
| 2723 | rc = lpfcdiag_loop_get_xri(phba, rpi, &txxri, &rxxri); | 2888 | if (phba->sli_rev < LPFC_SLI_REV4) { |
| 2724 | if (rc) { | 2889 | rc = lpfcdiag_loop_get_xri(phba, rpi, &txxri, &rxxri); |
| 2725 | lpfcdiag_loop_self_unreg(phba, rpi); | 2890 | if (rc) { |
| 2726 | goto loopback_test_exit; | 2891 | lpfcdiag_loop_self_unreg(phba, rpi); |
| 2727 | } | 2892 | goto loopback_test_exit; |
| 2893 | } | ||
| 2728 | 2894 | ||
| 2729 | rc = lpfcdiag_loop_post_rxbufs(phba, rxxri, full_size); | 2895 | rc = lpfcdiag_loop_post_rxbufs(phba, rxxri, full_size); |
| 2730 | if (rc) { | 2896 | if (rc) { |
| 2731 | lpfcdiag_loop_self_unreg(phba, rpi); | 2897 | lpfcdiag_loop_self_unreg(phba, rpi); |
| 2732 | goto loopback_test_exit; | 2898 | goto loopback_test_exit; |
| 2899 | } | ||
| 2733 | } | 2900 | } |
| 2734 | |||
| 2735 | evt = lpfc_bsg_event_new(FC_REG_CT_EVENT, current->pid, | 2901 | evt = lpfc_bsg_event_new(FC_REG_CT_EVENT, current->pid, |
| 2736 | SLI_CT_ELX_LOOPBACK); | 2902 | SLI_CT_ELX_LOOPBACK); |
| 2737 | if (!evt) { | 2903 | if (!evt) { |
| @@ -2746,7 +2912,8 @@ lpfc_bsg_diag_loopback_run(struct fc_bsg_job *job) | |||
| 2746 | spin_unlock_irqrestore(&phba->ct_ev_lock, flags); | 2912 | spin_unlock_irqrestore(&phba->ct_ev_lock, flags); |
| 2747 | 2913 | ||
| 2748 | cmdiocbq = lpfc_sli_get_iocbq(phba); | 2914 | cmdiocbq = lpfc_sli_get_iocbq(phba); |
| 2749 | rspiocbq = lpfc_sli_get_iocbq(phba); | 2915 | if (phba->sli_rev < LPFC_SLI_REV4) |
| 2916 | rspiocbq = lpfc_sli_get_iocbq(phba); | ||
| 2750 | txbmp = kmalloc(sizeof(struct lpfc_dmabuf), GFP_KERNEL); | 2917 | txbmp = kmalloc(sizeof(struct lpfc_dmabuf), GFP_KERNEL); |
| 2751 | 2918 | ||
| 2752 | if (txbmp) { | 2919 | if (txbmp) { |
| @@ -2759,14 +2926,18 @@ lpfc_bsg_diag_loopback_run(struct fc_bsg_job *job) | |||
| 2759 | } | 2926 | } |
| 2760 | } | 2927 | } |
| 2761 | 2928 | ||
| 2762 | if (!cmdiocbq || !rspiocbq || !txbmp || !txbpl || !txbuffer || | 2929 | if (!cmdiocbq || !txbmp || !txbpl || !txbuffer || !txbmp->virt) { |
| 2763 | !txbmp->virt) { | 2930 | rc = -ENOMEM; |
| 2931 | goto err_loopback_test_exit; | ||
| 2932 | } | ||
| 2933 | if ((phba->sli_rev < LPFC_SLI_REV4) && !rspiocbq) { | ||
| 2764 | rc = -ENOMEM; | 2934 | rc = -ENOMEM; |
| 2765 | goto err_loopback_test_exit; | 2935 | goto err_loopback_test_exit; |
| 2766 | } | 2936 | } |
| 2767 | 2937 | ||
| 2768 | cmd = &cmdiocbq->iocb; | 2938 | cmd = &cmdiocbq->iocb; |
| 2769 | rsp = &rspiocbq->iocb; | 2939 | if (phba->sli_rev < LPFC_SLI_REV4) |
| 2940 | rsp = &rspiocbq->iocb; | ||
| 2770 | 2941 | ||
| 2771 | INIT_LIST_HEAD(&head); | 2942 | INIT_LIST_HEAD(&head); |
| 2772 | list_add_tail(&head, &txbuffer->dma.list); | 2943 | list_add_tail(&head, &txbuffer->dma.list); |
| @@ -2796,7 +2967,6 @@ lpfc_bsg_diag_loopback_run(struct fc_bsg_job *job) | |||
| 2796 | list_del(&head); | 2967 | list_del(&head); |
| 2797 | 2968 | ||
| 2798 | /* Build the XMIT_SEQUENCE iocb */ | 2969 | /* Build the XMIT_SEQUENCE iocb */ |
| 2799 | |||
| 2800 | num_bde = (uint32_t)txbuffer->flag; | 2970 | num_bde = (uint32_t)txbuffer->flag; |
| 2801 | 2971 | ||
| 2802 | cmd->un.xseq64.bdl.addrHigh = putPaddrHigh(txbmp->phys); | 2972 | cmd->un.xseq64.bdl.addrHigh = putPaddrHigh(txbmp->phys); |
| @@ -2813,16 +2983,27 @@ lpfc_bsg_diag_loopback_run(struct fc_bsg_job *job) | |||
| 2813 | cmd->ulpBdeCount = 1; | 2983 | cmd->ulpBdeCount = 1; |
| 2814 | cmd->ulpLe = 1; | 2984 | cmd->ulpLe = 1; |
| 2815 | cmd->ulpClass = CLASS3; | 2985 | cmd->ulpClass = CLASS3; |
| 2816 | cmd->ulpContext = txxri; | ||
| 2817 | 2986 | ||
| 2987 | if (phba->sli_rev < LPFC_SLI_REV4) { | ||
| 2988 | cmd->ulpContext = txxri; | ||
| 2989 | } else { | ||
| 2990 | cmd->un.xseq64.bdl.ulpIoTag32 = 0; | ||
| 2991 | cmd->un.ulpWord[3] = phba->sli4_hba.rpi_ids[rpi]; | ||
| 2992 | cmdiocbq->context3 = txbmp; | ||
| 2993 | cmdiocbq->sli4_xritag = NO_XRI; | ||
| 2994 | cmd->unsli3.rcvsli3.ox_id = 0xffff; | ||
| 2995 | } | ||
| 2818 | cmdiocbq->iocb_flag |= LPFC_IO_LIBDFC; | 2996 | cmdiocbq->iocb_flag |= LPFC_IO_LIBDFC; |
| 2819 | cmdiocbq->vport = phba->pport; | 2997 | cmdiocbq->vport = phba->pport; |
| 2820 | |||
| 2821 | iocb_stat = lpfc_sli_issue_iocb_wait(phba, LPFC_ELS_RING, cmdiocbq, | 2998 | iocb_stat = lpfc_sli_issue_iocb_wait(phba, LPFC_ELS_RING, cmdiocbq, |
| 2822 | rspiocbq, (phba->fc_ratov * 2) + | 2999 | rspiocbq, (phba->fc_ratov * 2) + |
| 2823 | LPFC_DRVR_TIMEOUT); | 3000 | LPFC_DRVR_TIMEOUT); |
| 2824 | 3001 | ||
| 2825 | if ((iocb_stat != IOCB_SUCCESS) || (rsp->ulpStatus != IOCB_SUCCESS)) { | 3002 | if ((iocb_stat != IOCB_SUCCESS) || ((phba->sli_rev < LPFC_SLI_REV4) && |
| 3003 | (rsp->ulpStatus != IOCB_SUCCESS))) { | ||
| 3004 | lpfc_printf_log(phba, KERN_ERR, LOG_LIBDFC, | ||
| 3005 | "3126 Failed loopback test issue iocb: " | ||
| 3006 | "iocb_stat:x%x\n", iocb_stat); | ||
| 2826 | rc = -EIO; | 3007 | rc = -EIO; |
| 2827 | goto err_loopback_test_exit; | 3008 | goto err_loopback_test_exit; |
| 2828 | } | 3009 | } |
| @@ -2832,9 +3013,12 @@ lpfc_bsg_diag_loopback_run(struct fc_bsg_job *job) | |||
| 2832 | evt->wq, !list_empty(&evt->events_to_see), | 3013 | evt->wq, !list_empty(&evt->events_to_see), |
| 2833 | ((phba->fc_ratov * 2) + LPFC_DRVR_TIMEOUT) * HZ); | 3014 | ((phba->fc_ratov * 2) + LPFC_DRVR_TIMEOUT) * HZ); |
| 2834 | evt->waiting = 0; | 3015 | evt->waiting = 0; |
| 2835 | if (list_empty(&evt->events_to_see)) | 3016 | if (list_empty(&evt->events_to_see)) { |
| 2836 | rc = (time_left) ? -EINTR : -ETIMEDOUT; | 3017 | rc = (time_left) ? -EINTR : -ETIMEDOUT; |
| 2837 | else { | 3018 | lpfc_printf_log(phba, KERN_ERR, LOG_LIBDFC, |
| 3019 | "3125 Not receiving unsolicited event, " | ||
| 3020 | "rc:x%x\n", rc); | ||
| 3021 | } else { | ||
| 2838 | spin_lock_irqsave(&phba->ct_ev_lock, flags); | 3022 | spin_lock_irqsave(&phba->ct_ev_lock, flags); |
| 2839 | list_move(evt->events_to_see.prev, &evt->events_to_get); | 3023 | list_move(evt->events_to_see.prev, &evt->events_to_get); |
| 2840 | evdat = list_entry(evt->events_to_get.prev, | 3024 | evdat = list_entry(evt->events_to_get.prev, |
| @@ -2891,7 +3075,7 @@ loopback_test_exit: | |||
| 2891 | job->reply->result = rc; | 3075 | job->reply->result = rc; |
| 2892 | job->dd_data = NULL; | 3076 | job->dd_data = NULL; |
| 2893 | /* complete the job back to userspace if no error */ | 3077 | /* complete the job back to userspace if no error */ |
| 2894 | if (rc == 0) | 3078 | if (rc == IOCB_SUCCESS) |
| 2895 | job->job_done(job); | 3079 | job->job_done(job); |
| 2896 | return rc; | 3080 | return rc; |
| 2897 | } | 3081 | } |
| @@ -3078,7 +3262,9 @@ static int lpfc_bsg_check_cmd_access(struct lpfc_hba *phba, | |||
| 3078 | && (mb->un.varWords[1] == 1)) { | 3262 | && (mb->un.varWords[1] == 1)) { |
| 3079 | phba->wait_4_mlo_maint_flg = 1; | 3263 | phba->wait_4_mlo_maint_flg = 1; |
| 3080 | } else if (mb->un.varWords[0] == SETVAR_MLORST) { | 3264 | } else if (mb->un.varWords[0] == SETVAR_MLORST) { |
| 3265 | spin_lock_irq(&phba->hbalock); | ||
| 3081 | phba->link_flag &= ~LS_LOOPBACK_MODE; | 3266 | phba->link_flag &= ~LS_LOOPBACK_MODE; |
| 3267 | spin_unlock_irq(&phba->hbalock); | ||
| 3082 | phba->fc_topology = LPFC_TOPOLOGY_PT_PT; | 3268 | phba->fc_topology = LPFC_TOPOLOGY_PT_PT; |
| 3083 | } | 3269 | } |
| 3084 | break; | 3270 | break; |
diff --git a/drivers/scsi/lpfc/lpfc_crtn.h b/drivers/scsi/lpfc/lpfc_crtn.h index bcc021f3c8eb..26924b7a6cde 100644 --- a/drivers/scsi/lpfc/lpfc_crtn.h +++ b/drivers/scsi/lpfc/lpfc_crtn.h | |||
| @@ -78,6 +78,7 @@ void lpfc_mbx_cmpl_fabric_reg_login(struct lpfc_hba *, LPFC_MBOXQ_t *); | |||
| 78 | void lpfc_mbx_cmpl_ns_reg_login(struct lpfc_hba *, LPFC_MBOXQ_t *); | 78 | void lpfc_mbx_cmpl_ns_reg_login(struct lpfc_hba *, LPFC_MBOXQ_t *); |
| 79 | void lpfc_mbx_cmpl_fdmi_reg_login(struct lpfc_hba *, LPFC_MBOXQ_t *); | 79 | void lpfc_mbx_cmpl_fdmi_reg_login(struct lpfc_hba *, LPFC_MBOXQ_t *); |
| 80 | void lpfc_mbx_cmpl_reg_vfi(struct lpfc_hba *, LPFC_MBOXQ_t *); | 80 | void lpfc_mbx_cmpl_reg_vfi(struct lpfc_hba *, LPFC_MBOXQ_t *); |
| 81 | void lpfc_unregister_vfi_cmpl(struct lpfc_hba *, LPFC_MBOXQ_t *); | ||
| 81 | void lpfc_enqueue_node(struct lpfc_vport *, struct lpfc_nodelist *); | 82 | void lpfc_enqueue_node(struct lpfc_vport *, struct lpfc_nodelist *); |
| 82 | void lpfc_dequeue_node(struct lpfc_vport *, struct lpfc_nodelist *); | 83 | void lpfc_dequeue_node(struct lpfc_vport *, struct lpfc_nodelist *); |
| 83 | struct lpfc_nodelist *lpfc_enable_node(struct lpfc_vport *, | 84 | struct lpfc_nodelist *lpfc_enable_node(struct lpfc_vport *, |
| @@ -453,7 +454,11 @@ int lpfc_sli_probe_sriov_nr_virtfn(struct lpfc_hba *, int); | |||
| 453 | uint16_t lpfc_sli_sriov_nr_virtfn_get(struct lpfc_hba *); | 454 | uint16_t lpfc_sli_sriov_nr_virtfn_get(struct lpfc_hba *); |
| 454 | int lpfc_sli4_queue_create(struct lpfc_hba *); | 455 | int lpfc_sli4_queue_create(struct lpfc_hba *); |
| 455 | void lpfc_sli4_queue_destroy(struct lpfc_hba *); | 456 | void lpfc_sli4_queue_destroy(struct lpfc_hba *); |
| 456 | int lpfc_sli4_read_config(struct lpfc_hba *phba); | ||
| 457 | int lpfc_scsi_buf_update(struct lpfc_hba *phba); | ||
| 458 | void lpfc_sli4_abts_err_handler(struct lpfc_hba *, struct lpfc_nodelist *, | 457 | void lpfc_sli4_abts_err_handler(struct lpfc_hba *, struct lpfc_nodelist *, |
| 459 | struct sli4_wcqe_xri_aborted *); | 458 | struct sli4_wcqe_xri_aborted *); |
| 459 | int lpfc_hba_init_link_fc_topology(struct lpfc_hba *, uint32_t, uint32_t); | ||
| 460 | int lpfc_issue_reg_vfi(struct lpfc_vport *); | ||
| 461 | int lpfc_issue_unreg_vfi(struct lpfc_vport *); | ||
| 462 | int lpfc_selective_reset(struct lpfc_hba *); | ||
| 463 | int lpfc_sli4_read_config(struct lpfc_hba *phba); | ||
| 464 | int lpfc_scsi_buf_update(struct lpfc_hba *phba); | ||
diff --git a/drivers/scsi/lpfc/lpfc_els.c b/drivers/scsi/lpfc/lpfc_els.c index 0b662db23284..7afc757338de 100644 --- a/drivers/scsi/lpfc/lpfc_els.c +++ b/drivers/scsi/lpfc/lpfc_els.c | |||
| @@ -421,13 +421,13 @@ fail: | |||
| 421 | * @vport: pointer to a host virtual N_Port data structure. | 421 | * @vport: pointer to a host virtual N_Port data structure. |
| 422 | * | 422 | * |
| 423 | * This routine issues a REG_VFI mailbox for the vfi, vpi, fcfi triplet for | 423 | * This routine issues a REG_VFI mailbox for the vfi, vpi, fcfi triplet for |
| 424 | * the @vport. This mailbox command is necessary for FCoE only. | 424 | * the @vport. This mailbox command is necessary for SLI4 port only. |
| 425 | * | 425 | * |
| 426 | * Return code | 426 | * Return code |
| 427 | * 0 - successfully issued REG_VFI for @vport | 427 | * 0 - successfully issued REG_VFI for @vport |
| 428 | * A failure code otherwise. | 428 | * A failure code otherwise. |
| 429 | **/ | 429 | **/ |
| 430 | static int | 430 | int |
| 431 | lpfc_issue_reg_vfi(struct lpfc_vport *vport) | 431 | lpfc_issue_reg_vfi(struct lpfc_vport *vport) |
| 432 | { | 432 | { |
| 433 | struct lpfc_hba *phba = vport->phba; | 433 | struct lpfc_hba *phba = vport->phba; |
| @@ -438,10 +438,14 @@ lpfc_issue_reg_vfi(struct lpfc_vport *vport) | |||
| 438 | int rc = 0; | 438 | int rc = 0; |
| 439 | 439 | ||
| 440 | sp = &phba->fc_fabparam; | 440 | sp = &phba->fc_fabparam; |
| 441 | ndlp = lpfc_findnode_did(vport, Fabric_DID); | 441 | /* move forward in case of SLI4 FC port loopback test */ |
| 442 | if (!ndlp || !NLP_CHK_NODE_ACT(ndlp)) { | 442 | if ((phba->sli_rev == LPFC_SLI_REV4) && |
| 443 | rc = -ENODEV; | 443 | !(phba->link_flag & LS_LOOPBACK_MODE)) { |
| 444 | goto fail; | 444 | ndlp = lpfc_findnode_did(vport, Fabric_DID); |
| 445 | if (!ndlp || !NLP_CHK_NODE_ACT(ndlp)) { | ||
| 446 | rc = -ENODEV; | ||
| 447 | goto fail; | ||
| 448 | } | ||
| 445 | } | 449 | } |
| 446 | 450 | ||
| 447 | dmabuf = kzalloc(sizeof(struct lpfc_dmabuf), GFP_KERNEL); | 451 | dmabuf = kzalloc(sizeof(struct lpfc_dmabuf), GFP_KERNEL); |
| @@ -487,6 +491,54 @@ fail: | |||
| 487 | } | 491 | } |
| 488 | 492 | ||
| 489 | /** | 493 | /** |
| 494 | * lpfc_issue_unreg_vfi - Unregister VFI for this vport's fabric login | ||
| 495 | * @vport: pointer to a host virtual N_Port data structure. | ||
| 496 | * | ||
| 497 | * This routine issues a UNREG_VFI mailbox with the vfi, vpi, fcfi triplet for | ||
| 498 | * the @vport. This mailbox command is necessary for SLI4 port only. | ||
| 499 | * | ||
| 500 | * Return code | ||
| 501 | * 0 - successfully issued REG_VFI for @vport | ||
| 502 | * A failure code otherwise. | ||
| 503 | **/ | ||
| 504 | int | ||
| 505 | lpfc_issue_unreg_vfi(struct lpfc_vport *vport) | ||
| 506 | { | ||
| 507 | struct lpfc_hba *phba = vport->phba; | ||
| 508 | struct Scsi_Host *shost; | ||
| 509 | LPFC_MBOXQ_t *mboxq; | ||
| 510 | int rc; | ||
| 511 | |||
| 512 | mboxq = mempool_alloc(phba->mbox_mem_pool, GFP_KERNEL); | ||
| 513 | if (!mboxq) { | ||
| 514 | lpfc_printf_log(phba, KERN_ERR, LOG_DISCOVERY|LOG_MBOX, | ||
| 515 | "2556 UNREG_VFI mbox allocation failed" | ||
| 516 | "HBA state x%x\n", phba->pport->port_state); | ||
| 517 | return -ENOMEM; | ||
| 518 | } | ||
| 519 | |||
| 520 | lpfc_unreg_vfi(mboxq, vport); | ||
| 521 | mboxq->vport = vport; | ||
| 522 | mboxq->mbox_cmpl = lpfc_unregister_vfi_cmpl; | ||
| 523 | |||
| 524 | rc = lpfc_sli_issue_mbox(phba, mboxq, MBX_NOWAIT); | ||
| 525 | if (rc == MBX_NOT_FINISHED) { | ||
| 526 | lpfc_printf_log(phba, KERN_ERR, LOG_DISCOVERY|LOG_MBOX, | ||
| 527 | "2557 UNREG_VFI issue mbox failed rc x%x " | ||
| 528 | "HBA state x%x\n", | ||
| 529 | rc, phba->pport->port_state); | ||
| 530 | mempool_free(mboxq, phba->mbox_mem_pool); | ||
| 531 | return -EIO; | ||
| 532 | } | ||
| 533 | |||
| 534 | shost = lpfc_shost_from_vport(vport); | ||
| 535 | spin_lock_irq(shost->host_lock); | ||
| 536 | vport->fc_flag &= ~FC_VFI_REGISTERED; | ||
| 537 | spin_unlock_irq(shost->host_lock); | ||
| 538 | return 0; | ||
| 539 | } | ||
| 540 | |||
| 541 | /** | ||
| 490 | * lpfc_check_clean_addr_bit - Check whether assigned FCID is clean. | 542 | * lpfc_check_clean_addr_bit - Check whether assigned FCID is clean. |
| 491 | * @vport: pointer to a host virtual N_Port data structure. | 543 | * @vport: pointer to a host virtual N_Port data structure. |
| 492 | * @sp: pointer to service parameter data structure. | 544 | * @sp: pointer to service parameter data structure. |
| @@ -615,7 +667,9 @@ lpfc_cmpl_els_flogi_fabric(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp, | |||
| 615 | "1816 FLOGI NPIV supported, " | 667 | "1816 FLOGI NPIV supported, " |
| 616 | "response data 0x%x\n", | 668 | "response data 0x%x\n", |
| 617 | sp->cmn.response_multiple_NPort); | 669 | sp->cmn.response_multiple_NPort); |
| 670 | spin_lock_irq(&phba->hbalock); | ||
| 618 | phba->link_flag |= LS_NPIV_FAB_SUPPORTED; | 671 | phba->link_flag |= LS_NPIV_FAB_SUPPORTED; |
| 672 | spin_unlock_irq(&phba->hbalock); | ||
| 619 | } else { | 673 | } else { |
| 620 | /* Because we asked f/w for NPIV it still expects us | 674 | /* Because we asked f/w for NPIV it still expects us |
| 621 | to call reg_vnpid atleast for the physcial host */ | 675 | to call reg_vnpid atleast for the physcial host */ |
| @@ -623,7 +677,9 @@ lpfc_cmpl_els_flogi_fabric(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp, | |||
| 623 | LOG_ELS | LOG_VPORT, | 677 | LOG_ELS | LOG_VPORT, |
| 624 | "1817 Fabric does not support NPIV " | 678 | "1817 Fabric does not support NPIV " |
| 625 | "- configuring single port mode.\n"); | 679 | "- configuring single port mode.\n"); |
| 680 | spin_lock_irq(&phba->hbalock); | ||
| 626 | phba->link_flag &= ~LS_NPIV_FAB_SUPPORTED; | 681 | phba->link_flag &= ~LS_NPIV_FAB_SUPPORTED; |
| 682 | spin_unlock_irq(&phba->hbalock); | ||
| 627 | } | 683 | } |
| 628 | } | 684 | } |
| 629 | 685 | ||
| @@ -686,11 +742,16 @@ lpfc_cmpl_els_flogi_fabric(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp, | |||
| 686 | lpfc_do_scr_ns_plogi(phba, vport); | 742 | lpfc_do_scr_ns_plogi(phba, vport); |
| 687 | } else if (vport->fc_flag & FC_VFI_REGISTERED) | 743 | } else if (vport->fc_flag & FC_VFI_REGISTERED) |
| 688 | lpfc_issue_init_vpi(vport); | 744 | lpfc_issue_init_vpi(vport); |
| 689 | else | 745 | else { |
| 746 | lpfc_printf_vlog(vport, KERN_INFO, LOG_ELS, | ||
| 747 | "3135 Need register VFI: (x%x/%x)\n", | ||
| 748 | vport->fc_prevDID, vport->fc_myDID); | ||
| 690 | lpfc_issue_reg_vfi(vport); | 749 | lpfc_issue_reg_vfi(vport); |
| 750 | } | ||
| 691 | } | 751 | } |
| 692 | return 0; | 752 | return 0; |
| 693 | } | 753 | } |
| 754 | |||
| 694 | /** | 755 | /** |
| 695 | * lpfc_cmpl_els_flogi_nport - Completion function for flogi to an N_Port | 756 | * lpfc_cmpl_els_flogi_nport - Completion function for flogi to an N_Port |
| 696 | * @vport: pointer to a host virtual N_Port data structure. | 757 | * @vport: pointer to a host virtual N_Port data structure. |
| @@ -907,9 +968,8 @@ lpfc_cmpl_els_flogi(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb, | |||
| 907 | * LPFC_MAX_DISC_THREADS (32). Scanning in the case of no | 968 | * LPFC_MAX_DISC_THREADS (32). Scanning in the case of no |
| 908 | * alpa map would take too long otherwise. | 969 | * alpa map would take too long otherwise. |
| 909 | */ | 970 | */ |
| 910 | if (phba->alpa_map[0] == 0) { | 971 | if (phba->alpa_map[0] == 0) |
| 911 | vport->cfg_discovery_threads = LPFC_MAX_DISC_THREADS; | 972 | vport->cfg_discovery_threads = LPFC_MAX_DISC_THREADS; |
| 912 | } | ||
| 913 | if ((phba->sli_rev == LPFC_SLI_REV4) && | 973 | if ((phba->sli_rev == LPFC_SLI_REV4) && |
| 914 | (!(vport->fc_flag & FC_VFI_REGISTERED) || | 974 | (!(vport->fc_flag & FC_VFI_REGISTERED) || |
| 915 | (vport->fc_prevDID != vport->fc_myDID))) { | 975 | (vport->fc_prevDID != vport->fc_myDID))) { |
| @@ -1164,8 +1224,7 @@ lpfc_els_abort_flogi(struct lpfc_hba *phba) | |||
| 1164 | spin_lock_irq(&phba->hbalock); | 1224 | spin_lock_irq(&phba->hbalock); |
| 1165 | list_for_each_entry_safe(iocb, next_iocb, &pring->txcmplq, list) { | 1225 | list_for_each_entry_safe(iocb, next_iocb, &pring->txcmplq, list) { |
| 1166 | icmd = &iocb->iocb; | 1226 | icmd = &iocb->iocb; |
| 1167 | if (icmd->ulpCommand == CMD_ELS_REQUEST64_CR && | 1227 | if (icmd->ulpCommand == CMD_ELS_REQUEST64_CR) { |
| 1168 | icmd->un.elsreq64.bdl.ulpIoTag32) { | ||
| 1169 | ndlp = (struct lpfc_nodelist *)(iocb->context1); | 1228 | ndlp = (struct lpfc_nodelist *)(iocb->context1); |
| 1170 | if (ndlp && NLP_CHK_NODE_ACT(ndlp) && | 1229 | if (ndlp && NLP_CHK_NODE_ACT(ndlp) && |
| 1171 | (ndlp->nlp_DID == Fabric_DID)) | 1230 | (ndlp->nlp_DID == Fabric_DID)) |
| @@ -4879,23 +4938,31 @@ lpfc_els_rcv_flogi(struct lpfc_vport *vport, struct lpfc_iocbq *cmdiocb, | |||
| 4879 | sizeof(struct lpfc_name)); | 4938 | sizeof(struct lpfc_name)); |
| 4880 | 4939 | ||
| 4881 | if (!rc) { | 4940 | if (!rc) { |
| 4882 | mbox = mempool_alloc(phba->mbox_mem_pool, GFP_KERNEL); | 4941 | if (phba->sli_rev < LPFC_SLI_REV4) { |
| 4883 | if (!mbox) | 4942 | mbox = mempool_alloc(phba->mbox_mem_pool, |
| 4943 | GFP_KERNEL); | ||
| 4944 | if (!mbox) | ||
| 4945 | return 1; | ||
| 4946 | lpfc_linkdown(phba); | ||
| 4947 | lpfc_init_link(phba, mbox, | ||
| 4948 | phba->cfg_topology, | ||
| 4949 | phba->cfg_link_speed); | ||
| 4950 | mbox->u.mb.un.varInitLnk.lipsr_AL_PA = 0; | ||
| 4951 | mbox->mbox_cmpl = lpfc_sli_def_mbox_cmpl; | ||
| 4952 | mbox->vport = vport; | ||
| 4953 | rc = lpfc_sli_issue_mbox(phba, mbox, | ||
| 4954 | MBX_NOWAIT); | ||
| 4955 | lpfc_set_loopback_flag(phba); | ||
| 4956 | if (rc == MBX_NOT_FINISHED) | ||
| 4957 | mempool_free(mbox, phba->mbox_mem_pool); | ||
| 4884 | return 1; | 4958 | return 1; |
| 4885 | 4959 | } else { | |
| 4886 | lpfc_linkdown(phba); | 4960 | /* abort the flogi coming back to ourselves |
| 4887 | lpfc_init_link(phba, mbox, | 4961 | * due to external loopback on the port. |
| 4888 | phba->cfg_topology, | 4962 | */ |
| 4889 | phba->cfg_link_speed); | 4963 | lpfc_els_abort_flogi(phba); |
| 4890 | mbox->u.mb.un.varInitLnk.lipsr_AL_PA = 0; | 4964 | return 0; |
| 4891 | mbox->mbox_cmpl = lpfc_sli_def_mbox_cmpl; | ||
| 4892 | mbox->vport = vport; | ||
| 4893 | rc = lpfc_sli_issue_mbox(phba, mbox, MBX_NOWAIT); | ||
| 4894 | lpfc_set_loopback_flag(phba); | ||
| 4895 | if (rc == MBX_NOT_FINISHED) { | ||
| 4896 | mempool_free(mbox, phba->mbox_mem_pool); | ||
| 4897 | } | 4965 | } |
| 4898 | return 1; | ||
| 4899 | } else if (rc > 0) { /* greater than */ | 4966 | } else if (rc > 0) { /* greater than */ |
| 4900 | spin_lock_irq(shost->host_lock); | 4967 | spin_lock_irq(shost->host_lock); |
| 4901 | vport->fc_flag |= FC_PT2PT_PLOGI; | 4968 | vport->fc_flag |= FC_PT2PT_PLOGI; |
| @@ -5850,8 +5917,12 @@ lpfc_els_rcv_fan(struct lpfc_vport *vport, struct lpfc_iocbq *cmdiocb, | |||
| 5850 | vport->fc_myDID = vport->fc_prevDID; | 5917 | vport->fc_myDID = vport->fc_prevDID; |
| 5851 | if (phba->sli_rev < LPFC_SLI_REV4) | 5918 | if (phba->sli_rev < LPFC_SLI_REV4) |
| 5852 | lpfc_issue_fabric_reglogin(vport); | 5919 | lpfc_issue_fabric_reglogin(vport); |
| 5853 | else | 5920 | else { |
| 5921 | lpfc_printf_vlog(vport, KERN_INFO, LOG_ELS, | ||
| 5922 | "3138 Need register VFI: (x%x/%x)\n", | ||
| 5923 | vport->fc_prevDID, vport->fc_myDID); | ||
| 5854 | lpfc_issue_reg_vfi(vport); | 5924 | lpfc_issue_reg_vfi(vport); |
| 5925 | } | ||
| 5855 | } | 5926 | } |
| 5856 | } | 5927 | } |
| 5857 | return 0; | 5928 | return 0; |
diff --git a/drivers/scsi/lpfc/lpfc_hbadisc.c b/drivers/scsi/lpfc/lpfc_hbadisc.c index d96498581ebe..678a4b11059c 100644 --- a/drivers/scsi/lpfc/lpfc_hbadisc.c +++ b/drivers/scsi/lpfc/lpfc_hbadisc.c | |||
| @@ -1074,6 +1074,12 @@ lpfc_mbx_cmpl_local_config_link(struct lpfc_hba *phba, LPFC_MBOXQ_t *pmb) | |||
| 1074 | 1074 | ||
| 1075 | mempool_free(pmb, phba->mbox_mem_pool); | 1075 | mempool_free(pmb, phba->mbox_mem_pool); |
| 1076 | 1076 | ||
| 1077 | /* don't perform discovery for SLI4 loopback diagnostic test */ | ||
| 1078 | if ((phba->sli_rev == LPFC_SLI_REV4) && | ||
| 1079 | !(phba->hba_flag & HBA_FCOE_MODE) && | ||
| 1080 | (phba->link_flag & LS_LOOPBACK_MODE)) | ||
| 1081 | return; | ||
| 1082 | |||
| 1077 | if (phba->fc_topology == LPFC_TOPOLOGY_LOOP && | 1083 | if (phba->fc_topology == LPFC_TOPOLOGY_LOOP && |
| 1078 | vport->fc_flag & FC_PUBLIC_LOOP && | 1084 | vport->fc_flag & FC_PUBLIC_LOOP && |
| 1079 | !(vport->fc_flag & FC_LBIT)) { | 1085 | !(vport->fc_flag & FC_LBIT)) { |
| @@ -2847,10 +2853,10 @@ lpfc_mbx_cmpl_reg_vfi(struct lpfc_hba *phba, LPFC_MBOXQ_t *mboxq) | |||
| 2847 | lpfc_disc_list_loopmap(vport); | 2853 | lpfc_disc_list_loopmap(vport); |
| 2848 | /* Start discovery */ | 2854 | /* Start discovery */ |
| 2849 | lpfc_disc_start(vport); | 2855 | lpfc_disc_start(vport); |
| 2850 | goto fail_free_mem; | 2856 | goto out_free_mem; |
| 2851 | } | 2857 | } |
| 2852 | lpfc_vport_set_state(vport, FC_VPORT_FAILED); | 2858 | lpfc_vport_set_state(vport, FC_VPORT_FAILED); |
| 2853 | goto fail_free_mem; | 2859 | goto out_free_mem; |
| 2854 | } | 2860 | } |
| 2855 | /* The VPI is implicitly registered when the VFI is registered */ | 2861 | /* The VPI is implicitly registered when the VFI is registered */ |
| 2856 | spin_lock_irq(shost->host_lock); | 2862 | spin_lock_irq(shost->host_lock); |
| @@ -2860,6 +2866,13 @@ lpfc_mbx_cmpl_reg_vfi(struct lpfc_hba *phba, LPFC_MBOXQ_t *mboxq) | |||
| 2860 | vport->fc_flag &= ~FC_VPORT_NEEDS_INIT_VPI; | 2866 | vport->fc_flag &= ~FC_VPORT_NEEDS_INIT_VPI; |
| 2861 | spin_unlock_irq(shost->host_lock); | 2867 | spin_unlock_irq(shost->host_lock); |
| 2862 | 2868 | ||
| 2869 | /* In case SLI4 FC loopback test, we are ready */ | ||
| 2870 | if ((phba->sli_rev == LPFC_SLI_REV4) && | ||
| 2871 | (phba->link_flag & LS_LOOPBACK_MODE)) { | ||
| 2872 | phba->link_state = LPFC_HBA_READY; | ||
| 2873 | goto out_free_mem; | ||
| 2874 | } | ||
| 2875 | |||
| 2863 | if (vport->port_state == LPFC_FABRIC_CFG_LINK) { | 2876 | if (vport->port_state == LPFC_FABRIC_CFG_LINK) { |
| 2864 | /* For private loop just start discovery and we are done. */ | 2877 | /* For private loop just start discovery and we are done. */ |
| 2865 | if ((phba->fc_topology == LPFC_TOPOLOGY_LOOP) && | 2878 | if ((phba->fc_topology == LPFC_TOPOLOGY_LOOP) && |
| @@ -2874,7 +2887,7 @@ lpfc_mbx_cmpl_reg_vfi(struct lpfc_hba *phba, LPFC_MBOXQ_t *mboxq) | |||
| 2874 | } | 2887 | } |
| 2875 | } | 2888 | } |
| 2876 | 2889 | ||
| 2877 | fail_free_mem: | 2890 | out_free_mem: |
| 2878 | mempool_free(mboxq, phba->mbox_mem_pool); | 2891 | mempool_free(mboxq, phba->mbox_mem_pool); |
| 2879 | lpfc_mbuf_free(phba, dmabuf->virt, dmabuf->phys); | 2892 | lpfc_mbuf_free(phba, dmabuf->virt, dmabuf->phys); |
| 2880 | kfree(dmabuf); | 2893 | kfree(dmabuf); |
| @@ -3235,15 +3248,14 @@ lpfc_mbx_cmpl_read_topology(struct lpfc_hba *phba, LPFC_MBOXQ_t *pmb) | |||
| 3235 | } else if (bf_get(lpfc_mbx_read_top_att_type, la) == | 3248 | } else if (bf_get(lpfc_mbx_read_top_att_type, la) == |
| 3236 | LPFC_ATT_LINK_DOWN) { | 3249 | LPFC_ATT_LINK_DOWN) { |
| 3237 | phba->fc_stat.LinkDown++; | 3250 | phba->fc_stat.LinkDown++; |
| 3238 | if (phba->link_flag & LS_LOOPBACK_MODE) { | 3251 | if (phba->link_flag & LS_LOOPBACK_MODE) |
| 3239 | lpfc_printf_log(phba, KERN_ERR, LOG_LINK_EVENT, | 3252 | lpfc_printf_log(phba, KERN_ERR, LOG_LINK_EVENT, |
| 3240 | "1308 Link Down Event in loop back mode " | 3253 | "1308 Link Down Event in loop back mode " |
| 3241 | "x%x received " | 3254 | "x%x received " |
| 3242 | "Data: x%x x%x x%x\n", | 3255 | "Data: x%x x%x x%x\n", |
| 3243 | la->eventTag, phba->fc_eventTag, | 3256 | la->eventTag, phba->fc_eventTag, |
| 3244 | phba->pport->port_state, vport->fc_flag); | 3257 | phba->pport->port_state, vport->fc_flag); |
| 3245 | } | 3258 | else |
| 3246 | else { | ||
| 3247 | lpfc_printf_log(phba, KERN_ERR, LOG_LINK_EVENT, | 3259 | lpfc_printf_log(phba, KERN_ERR, LOG_LINK_EVENT, |
| 3248 | "1305 Link Down Event x%x received " | 3260 | "1305 Link Down Event x%x received " |
| 3249 | "Data: x%x x%x x%x x%x x%x\n", | 3261 | "Data: x%x x%x x%x x%x x%x\n", |
| @@ -3251,7 +3263,6 @@ lpfc_mbx_cmpl_read_topology(struct lpfc_hba *phba, LPFC_MBOXQ_t *pmb) | |||
| 3251 | phba->pport->port_state, vport->fc_flag, | 3263 | phba->pport->port_state, vport->fc_flag, |
| 3252 | bf_get(lpfc_mbx_read_top_mm, la), | 3264 | bf_get(lpfc_mbx_read_top_mm, la), |
| 3253 | bf_get(lpfc_mbx_read_top_fa, la)); | 3265 | bf_get(lpfc_mbx_read_top_fa, la)); |
| 3254 | } | ||
| 3255 | lpfc_mbx_issue_link_down(phba); | 3266 | lpfc_mbx_issue_link_down(phba); |
| 3256 | } | 3267 | } |
| 3257 | if ((bf_get(lpfc_mbx_read_top_mm, la)) && | 3268 | if ((bf_get(lpfc_mbx_read_top_mm, la)) && |
| @@ -5682,7 +5693,7 @@ out: | |||
| 5682 | * | 5693 | * |
| 5683 | * This function frees memory associated with the mailbox command. | 5694 | * This function frees memory associated with the mailbox command. |
| 5684 | */ | 5695 | */ |
| 5685 | static void | 5696 | void |
| 5686 | lpfc_unregister_vfi_cmpl(struct lpfc_hba *phba, LPFC_MBOXQ_t *mboxq) | 5697 | lpfc_unregister_vfi_cmpl(struct lpfc_hba *phba, LPFC_MBOXQ_t *mboxq) |
| 5687 | { | 5698 | { |
| 5688 | struct lpfc_vport *vport = mboxq->vport; | 5699 | struct lpfc_vport *vport = mboxq->vport; |
| @@ -5734,7 +5745,6 @@ lpfc_unregister_fcfi_cmpl(struct lpfc_hba *phba, LPFC_MBOXQ_t *mboxq) | |||
| 5734 | int | 5745 | int |
| 5735 | lpfc_unregister_fcf_prep(struct lpfc_hba *phba) | 5746 | lpfc_unregister_fcf_prep(struct lpfc_hba *phba) |
| 5736 | { | 5747 | { |
| 5737 | LPFC_MBOXQ_t *mbox; | ||
| 5738 | struct lpfc_vport **vports; | 5748 | struct lpfc_vport **vports; |
| 5739 | struct lpfc_nodelist *ndlp; | 5749 | struct lpfc_nodelist *ndlp; |
| 5740 | struct Scsi_Host *shost; | 5750 | struct Scsi_Host *shost; |
| @@ -5770,35 +5780,9 @@ lpfc_unregister_fcf_prep(struct lpfc_hba *phba) | |||
| 5770 | /* Cleanup any outstanding ELS commands */ | 5780 | /* Cleanup any outstanding ELS commands */ |
| 5771 | lpfc_els_flush_all_cmd(phba); | 5781 | lpfc_els_flush_all_cmd(phba); |
| 5772 | 5782 | ||
| 5773 | /* Unregister VFI */ | 5783 | /* Unregister the physical port VFI */ |
| 5774 | mbox = mempool_alloc(phba->mbox_mem_pool, GFP_KERNEL); | 5784 | rc = lpfc_issue_unreg_vfi(phba->pport); |
| 5775 | if (!mbox) { | 5785 | return rc; |
| 5776 | lpfc_printf_log(phba, KERN_ERR, LOG_DISCOVERY|LOG_MBOX, | ||
| 5777 | "2556 UNREG_VFI mbox allocation failed" | ||
| 5778 | "HBA state x%x\n", phba->pport->port_state); | ||
| 5779 | return -ENOMEM; | ||
| 5780 | } | ||
| 5781 | |||
| 5782 | lpfc_unreg_vfi(mbox, phba->pport); | ||
| 5783 | mbox->vport = phba->pport; | ||
| 5784 | mbox->mbox_cmpl = lpfc_unregister_vfi_cmpl; | ||
| 5785 | |||
| 5786 | rc = lpfc_sli_issue_mbox(phba, mbox, MBX_NOWAIT); | ||
| 5787 | if (rc == MBX_NOT_FINISHED) { | ||
| 5788 | lpfc_printf_log(phba, KERN_ERR, LOG_DISCOVERY|LOG_MBOX, | ||
| 5789 | "2557 UNREG_VFI issue mbox failed rc x%x " | ||
| 5790 | "HBA state x%x\n", | ||
| 5791 | rc, phba->pport->port_state); | ||
| 5792 | mempool_free(mbox, phba->mbox_mem_pool); | ||
| 5793 | return -EIO; | ||
| 5794 | } | ||
| 5795 | |||
| 5796 | shost = lpfc_shost_from_vport(phba->pport); | ||
| 5797 | spin_lock_irq(shost->host_lock); | ||
| 5798 | phba->pport->fc_flag &= ~FC_VFI_REGISTERED; | ||
| 5799 | spin_unlock_irq(shost->host_lock); | ||
| 5800 | |||
| 5801 | return 0; | ||
| 5802 | } | 5786 | } |
| 5803 | 5787 | ||
| 5804 | /** | 5788 | /** |
diff --git a/drivers/scsi/lpfc/lpfc_hw.h b/drivers/scsi/lpfc/lpfc_hw.h index 73fc5318641b..7245bead3755 100644 --- a/drivers/scsi/lpfc/lpfc_hw.h +++ b/drivers/scsi/lpfc/lpfc_hw.h | |||
| @@ -1858,8 +1858,8 @@ typedef struct { | |||
| 1858 | uint8_t fabric_AL_PA; /* If using a Fabric Assigned AL_PA */ | 1858 | uint8_t fabric_AL_PA; /* If using a Fabric Assigned AL_PA */ |
| 1859 | #endif | 1859 | #endif |
| 1860 | 1860 | ||
| 1861 | #define FLAGS_LOCAL_LB 0x01 /* link_flags (=1) ENDEC loopback */ | ||
| 1862 | #define FLAGS_TOPOLOGY_MODE_LOOP_PT 0x00 /* Attempt loop then pt-pt */ | 1861 | #define FLAGS_TOPOLOGY_MODE_LOOP_PT 0x00 /* Attempt loop then pt-pt */ |
| 1862 | #define FLAGS_LOCAL_LB 0x01 /* link_flags (=1) ENDEC loopback */ | ||
| 1863 | #define FLAGS_TOPOLOGY_MODE_PT_PT 0x02 /* Attempt pt-pt only */ | 1863 | #define FLAGS_TOPOLOGY_MODE_PT_PT 0x02 /* Attempt pt-pt only */ |
| 1864 | #define FLAGS_TOPOLOGY_MODE_LOOP 0x04 /* Attempt loop only */ | 1864 | #define FLAGS_TOPOLOGY_MODE_LOOP 0x04 /* Attempt loop only */ |
| 1865 | #define FLAGS_TOPOLOGY_MODE_PT_LOOP 0x06 /* Attempt pt-pt then loop */ | 1865 | #define FLAGS_TOPOLOGY_MODE_PT_LOOP 0x06 /* Attempt pt-pt then loop */ |
diff --git a/drivers/scsi/lpfc/lpfc_hw4.h b/drivers/scsi/lpfc/lpfc_hw4.h index 43c4c56f9e68..e5bfa7f334e3 100644 --- a/drivers/scsi/lpfc/lpfc_hw4.h +++ b/drivers/scsi/lpfc/lpfc_hw4.h | |||
| @@ -1351,11 +1351,11 @@ struct lpfc_mbx_set_link_diag_loopback { | |||
| 1351 | struct { | 1351 | struct { |
| 1352 | uint32_t word0; | 1352 | uint32_t word0; |
| 1353 | #define lpfc_mbx_set_diag_lpbk_type_SHIFT 0 | 1353 | #define lpfc_mbx_set_diag_lpbk_type_SHIFT 0 |
| 1354 | #define lpfc_mbx_set_diag_lpbk_type_MASK 0x00000001 | 1354 | #define lpfc_mbx_set_diag_lpbk_type_MASK 0x00000003 |
| 1355 | #define lpfc_mbx_set_diag_lpbk_type_WORD word0 | 1355 | #define lpfc_mbx_set_diag_lpbk_type_WORD word0 |
| 1356 | #define LPFC_DIAG_LOOPBACK_TYPE_DISABLE 0x0 | 1356 | #define LPFC_DIAG_LOOPBACK_TYPE_DISABLE 0x0 |
| 1357 | #define LPFC_DIAG_LOOPBACK_TYPE_INTERNAL 0x1 | 1357 | #define LPFC_DIAG_LOOPBACK_TYPE_INTERNAL 0x1 |
| 1358 | #define LPFC_DIAG_LOOPBACK_TYPE_EXTERNAL 0x2 | 1358 | #define LPFC_DIAG_LOOPBACK_TYPE_SERDES 0x2 |
| 1359 | #define lpfc_mbx_set_diag_lpbk_link_num_SHIFT 16 | 1359 | #define lpfc_mbx_set_diag_lpbk_link_num_SHIFT 16 |
| 1360 | #define lpfc_mbx_set_diag_lpbk_link_num_MASK 0x0000003F | 1360 | #define lpfc_mbx_set_diag_lpbk_link_num_MASK 0x0000003F |
| 1361 | #define lpfc_mbx_set_diag_lpbk_link_num_WORD word0 | 1361 | #define lpfc_mbx_set_diag_lpbk_link_num_WORD word0 |
| @@ -3324,6 +3324,9 @@ struct wqe_rctl_dfctl { | |||
| 3324 | #define wqe_la_SHIFT 3 | 3324 | #define wqe_la_SHIFT 3 |
| 3325 | #define wqe_la_MASK 0x000000001 | 3325 | #define wqe_la_MASK 0x000000001 |
| 3326 | #define wqe_la_WORD word5 | 3326 | #define wqe_la_WORD word5 |
| 3327 | #define wqe_xo_SHIFT 6 | ||
| 3328 | #define wqe_xo_MASK 0x000000001 | ||
| 3329 | #define wqe_xo_WORD word5 | ||
| 3327 | #define wqe_ls_SHIFT 7 | 3330 | #define wqe_ls_SHIFT 7 |
| 3328 | #define wqe_ls_MASK 0x000000001 | 3331 | #define wqe_ls_MASK 0x000000001 |
| 3329 | #define wqe_ls_WORD word5 | 3332 | #define wqe_ls_WORD word5 |
diff --git a/drivers/scsi/lpfc/lpfc_init.c b/drivers/scsi/lpfc/lpfc_init.c index cb714d2342d4..dfea2dada02c 100644 --- a/drivers/scsi/lpfc/lpfc_init.c +++ b/drivers/scsi/lpfc/lpfc_init.c | |||
| @@ -628,6 +628,28 @@ lpfc_config_port_post(struct lpfc_hba *phba) | |||
| 628 | int | 628 | int |
| 629 | lpfc_hba_init_link(struct lpfc_hba *phba, uint32_t flag) | 629 | lpfc_hba_init_link(struct lpfc_hba *phba, uint32_t flag) |
| 630 | { | 630 | { |
| 631 | return lpfc_hba_init_link_fc_topology(phba, phba->cfg_topology, flag); | ||
| 632 | } | ||
| 633 | |||
| 634 | /** | ||
| 635 | * lpfc_hba_init_link_fc_topology - Initialize FC link with desired topology | ||
| 636 | * @phba: pointer to lpfc hba data structure. | ||
| 637 | * @fc_topology: desired fc topology. | ||
| 638 | * @flag: mailbox command issue mode - either MBX_POLL or MBX_NOWAIT | ||
| 639 | * | ||
| 640 | * This routine will issue the INIT_LINK mailbox command call. | ||
| 641 | * It is available to other drivers through the lpfc_hba data | ||
| 642 | * structure for use as a delayed link up mechanism with the | ||
| 643 | * module parameter lpfc_suppress_link_up. | ||
| 644 | * | ||
| 645 | * Return code | ||
| 646 | * 0 - success | ||
| 647 | * Any other value - error | ||
| 648 | **/ | ||
| 649 | int | ||
| 650 | lpfc_hba_init_link_fc_topology(struct lpfc_hba *phba, uint32_t fc_topology, | ||
| 651 | uint32_t flag) | ||
| 652 | { | ||
| 631 | struct lpfc_vport *vport = phba->pport; | 653 | struct lpfc_vport *vport = phba->pport; |
| 632 | LPFC_MBOXQ_t *pmb; | 654 | LPFC_MBOXQ_t *pmb; |
| 633 | MAILBOX_t *mb; | 655 | MAILBOX_t *mb; |
| @@ -661,9 +683,10 @@ lpfc_hba_init_link(struct lpfc_hba *phba, uint32_t flag) | |||
| 661 | phba->cfg_link_speed); | 683 | phba->cfg_link_speed); |
| 662 | phba->cfg_link_speed = LPFC_USER_LINK_SPEED_AUTO; | 684 | phba->cfg_link_speed = LPFC_USER_LINK_SPEED_AUTO; |
| 663 | } | 685 | } |
| 664 | lpfc_init_link(phba, pmb, phba->cfg_topology, phba->cfg_link_speed); | 686 | lpfc_init_link(phba, pmb, fc_topology, phba->cfg_link_speed); |
| 665 | pmb->mbox_cmpl = lpfc_sli_def_mbox_cmpl; | 687 | pmb->mbox_cmpl = lpfc_sli_def_mbox_cmpl; |
| 666 | lpfc_set_loopback_flag(phba); | 688 | if (phba->sli_rev < LPFC_SLI_REV4) |
| 689 | lpfc_set_loopback_flag(phba); | ||
| 667 | rc = lpfc_sli_issue_mbox(phba, pmb, flag); | 690 | rc = lpfc_sli_issue_mbox(phba, pmb, flag); |
| 668 | if ((rc != MBX_BUSY) && (rc != MBX_SUCCESS)) { | 691 | if ((rc != MBX_BUSY) && (rc != MBX_SUCCESS)) { |
| 669 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, | 692 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, |
| @@ -6654,9 +6677,10 @@ lpfc_sli4_queue_setup(struct lpfc_hba *phba) | |||
| 6654 | phba->sli4_hba.sp_eq->queue_id); | 6677 | phba->sli4_hba.sp_eq->queue_id); |
| 6655 | 6678 | ||
| 6656 | /* Set up fast-path event queue */ | 6679 | /* Set up fast-path event queue */ |
| 6657 | if (!phba->sli4_hba.fp_eq) { | 6680 | if (phba->cfg_fcp_eq_count && !phba->sli4_hba.fp_eq) { |
| 6658 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, | 6681 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, |
| 6659 | "3147 Fast-path EQs not allocated\n"); | 6682 | "3147 Fast-path EQs not allocated\n"); |
| 6683 | rc = -ENOMEM; | ||
| 6660 | goto out_destroy_sp_eq; | 6684 | goto out_destroy_sp_eq; |
| 6661 | } | 6685 | } |
| 6662 | for (fcp_eqidx = 0; fcp_eqidx < phba->cfg_fcp_eq_count; fcp_eqidx++) { | 6686 | for (fcp_eqidx = 0; fcp_eqidx < phba->cfg_fcp_eq_count; fcp_eqidx++) { |
| @@ -6664,6 +6688,7 @@ lpfc_sli4_queue_setup(struct lpfc_hba *phba) | |||
| 6664 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, | 6688 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, |
| 6665 | "0522 Fast-path EQ (%d) not " | 6689 | "0522 Fast-path EQ (%d) not " |
| 6666 | "allocated\n", fcp_eqidx); | 6690 | "allocated\n", fcp_eqidx); |
| 6691 | rc = -ENOMEM; | ||
| 6667 | goto out_destroy_fp_eq; | 6692 | goto out_destroy_fp_eq; |
| 6668 | } | 6693 | } |
| 6669 | rc = lpfc_eq_create(phba, phba->sli4_hba.fp_eq[fcp_eqidx], | 6694 | rc = lpfc_eq_create(phba, phba->sli4_hba.fp_eq[fcp_eqidx], |
| @@ -6688,6 +6713,7 @@ lpfc_sli4_queue_setup(struct lpfc_hba *phba) | |||
| 6688 | if (!phba->sli4_hba.mbx_cq) { | 6713 | if (!phba->sli4_hba.mbx_cq) { |
| 6689 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, | 6714 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, |
| 6690 | "0528 Mailbox CQ not allocated\n"); | 6715 | "0528 Mailbox CQ not allocated\n"); |
| 6716 | rc = -ENOMEM; | ||
| 6691 | goto out_destroy_fp_eq; | 6717 | goto out_destroy_fp_eq; |
| 6692 | } | 6718 | } |
| 6693 | rc = lpfc_cq_create(phba, phba->sli4_hba.mbx_cq, phba->sli4_hba.sp_eq, | 6719 | rc = lpfc_cq_create(phba, phba->sli4_hba.mbx_cq, phba->sli4_hba.sp_eq, |
| @@ -6707,6 +6733,7 @@ lpfc_sli4_queue_setup(struct lpfc_hba *phba) | |||
| 6707 | if (!phba->sli4_hba.els_cq) { | 6733 | if (!phba->sli4_hba.els_cq) { |
| 6708 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, | 6734 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, |
| 6709 | "0530 ELS CQ not allocated\n"); | 6735 | "0530 ELS CQ not allocated\n"); |
| 6736 | rc = -ENOMEM; | ||
| 6710 | goto out_destroy_mbx_cq; | 6737 | goto out_destroy_mbx_cq; |
| 6711 | } | 6738 | } |
| 6712 | rc = lpfc_cq_create(phba, phba->sli4_hba.els_cq, phba->sli4_hba.sp_eq, | 6739 | rc = lpfc_cq_create(phba, phba->sli4_hba.els_cq, phba->sli4_hba.sp_eq, |
| @@ -6727,6 +6754,7 @@ lpfc_sli4_queue_setup(struct lpfc_hba *phba) | |||
| 6727 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, | 6754 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, |
| 6728 | "3148 Fast-path FCP CQ array not " | 6755 | "3148 Fast-path FCP CQ array not " |
| 6729 | "allocated\n"); | 6756 | "allocated\n"); |
| 6757 | rc = -ENOMEM; | ||
| 6730 | goto out_destroy_els_cq; | 6758 | goto out_destroy_els_cq; |
| 6731 | } | 6759 | } |
| 6732 | fcp_cqidx = 0; | 6760 | fcp_cqidx = 0; |
| @@ -6735,6 +6763,7 @@ lpfc_sli4_queue_setup(struct lpfc_hba *phba) | |||
| 6735 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, | 6763 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, |
| 6736 | "0526 Fast-path FCP CQ (%d) not " | 6764 | "0526 Fast-path FCP CQ (%d) not " |
| 6737 | "allocated\n", fcp_cqidx); | 6765 | "allocated\n", fcp_cqidx); |
| 6766 | rc = -ENOMEM; | ||
| 6738 | goto out_destroy_fcp_cq; | 6767 | goto out_destroy_fcp_cq; |
| 6739 | } | 6768 | } |
| 6740 | if (phba->cfg_fcp_eq_count) | 6769 | if (phba->cfg_fcp_eq_count) |
| @@ -6773,6 +6802,7 @@ lpfc_sli4_queue_setup(struct lpfc_hba *phba) | |||
| 6773 | if (!phba->sli4_hba.mbx_wq) { | 6802 | if (!phba->sli4_hba.mbx_wq) { |
| 6774 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, | 6803 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, |
| 6775 | "0538 Slow-path MQ not allocated\n"); | 6804 | "0538 Slow-path MQ not allocated\n"); |
| 6805 | rc = -ENOMEM; | ||
| 6776 | goto out_destroy_fcp_cq; | 6806 | goto out_destroy_fcp_cq; |
| 6777 | } | 6807 | } |
| 6778 | rc = lpfc_mq_create(phba, phba->sli4_hba.mbx_wq, | 6808 | rc = lpfc_mq_create(phba, phba->sli4_hba.mbx_wq, |
| @@ -6792,6 +6822,7 @@ lpfc_sli4_queue_setup(struct lpfc_hba *phba) | |||
| 6792 | if (!phba->sli4_hba.els_wq) { | 6822 | if (!phba->sli4_hba.els_wq) { |
| 6793 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, | 6823 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, |
| 6794 | "0536 Slow-path ELS WQ not allocated\n"); | 6824 | "0536 Slow-path ELS WQ not allocated\n"); |
| 6825 | rc = -ENOMEM; | ||
| 6795 | goto out_destroy_mbx_wq; | 6826 | goto out_destroy_mbx_wq; |
| 6796 | } | 6827 | } |
| 6797 | rc = lpfc_wq_create(phba, phba->sli4_hba.els_wq, | 6828 | rc = lpfc_wq_create(phba, phba->sli4_hba.els_wq, |
| @@ -6812,6 +6843,7 @@ lpfc_sli4_queue_setup(struct lpfc_hba *phba) | |||
| 6812 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, | 6843 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, |
| 6813 | "3149 Fast-path FCP WQ array not " | 6844 | "3149 Fast-path FCP WQ array not " |
| 6814 | "allocated\n"); | 6845 | "allocated\n"); |
| 6846 | rc = -ENOMEM; | ||
| 6815 | goto out_destroy_els_wq; | 6847 | goto out_destroy_els_wq; |
| 6816 | } | 6848 | } |
| 6817 | for (fcp_wqidx = 0; fcp_wqidx < phba->cfg_fcp_wq_count; fcp_wqidx++) { | 6849 | for (fcp_wqidx = 0; fcp_wqidx < phba->cfg_fcp_wq_count; fcp_wqidx++) { |
| @@ -6819,6 +6851,7 @@ lpfc_sli4_queue_setup(struct lpfc_hba *phba) | |||
| 6819 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, | 6851 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, |
| 6820 | "0534 Fast-path FCP WQ (%d) not " | 6852 | "0534 Fast-path FCP WQ (%d) not " |
| 6821 | "allocated\n", fcp_wqidx); | 6853 | "allocated\n", fcp_wqidx); |
| 6854 | rc = -ENOMEM; | ||
| 6822 | goto out_destroy_fcp_wq; | 6855 | goto out_destroy_fcp_wq; |
| 6823 | } | 6856 | } |
| 6824 | rc = lpfc_wq_create(phba, phba->sli4_hba.fcp_wq[fcp_wqidx], | 6857 | rc = lpfc_wq_create(phba, phba->sli4_hba.fcp_wq[fcp_wqidx], |
| @@ -6849,6 +6882,7 @@ lpfc_sli4_queue_setup(struct lpfc_hba *phba) | |||
| 6849 | if (!phba->sli4_hba.hdr_rq || !phba->sli4_hba.dat_rq) { | 6882 | if (!phba->sli4_hba.hdr_rq || !phba->sli4_hba.dat_rq) { |
| 6850 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, | 6883 | lpfc_printf_log(phba, KERN_ERR, LOG_INIT, |
| 6851 | "0540 Receive Queue not allocated\n"); | 6884 | "0540 Receive Queue not allocated\n"); |
| 6885 | rc = -ENOMEM; | ||
| 6852 | goto out_destroy_fcp_wq; | 6886 | goto out_destroy_fcp_wq; |
| 6853 | } | 6887 | } |
| 6854 | 6888 | ||
diff --git a/drivers/scsi/lpfc/lpfc_mbox.c b/drivers/scsi/lpfc/lpfc_mbox.c index 328782efc839..20336f09fb3c 100644 --- a/drivers/scsi/lpfc/lpfc_mbox.c +++ b/drivers/scsi/lpfc/lpfc_mbox.c | |||
| @@ -2133,6 +2133,14 @@ lpfc_reg_vfi(struct lpfcMboxq *mbox, struct lpfc_vport *vport, dma_addr_t phys) | |||
| 2133 | reg_vfi->bde.tus.f.bdeSize = sizeof(vport->fc_sparam); | 2133 | reg_vfi->bde.tus.f.bdeSize = sizeof(vport->fc_sparam); |
| 2134 | reg_vfi->bde.tus.f.bdeFlags = BUFF_TYPE_BDE_64; | 2134 | reg_vfi->bde.tus.f.bdeFlags = BUFF_TYPE_BDE_64; |
| 2135 | bf_set(lpfc_reg_vfi_nport_id, reg_vfi, vport->fc_myDID); | 2135 | bf_set(lpfc_reg_vfi_nport_id, reg_vfi, vport->fc_myDID); |
| 2136 | lpfc_printf_vlog(vport, KERN_INFO, LOG_MBOX, | ||
| 2137 | "3134 Register VFI, mydid:x%x, fcfi:%d, " | ||
| 2138 | " vfi:%d, vpi:%d, fc_pname:%x%x\n", | ||
| 2139 | vport->fc_myDID, | ||
| 2140 | vport->phba->fcf.fcfi, | ||
| 2141 | vport->phba->sli4_hba.vfi_ids[vport->vfi], | ||
| 2142 | vport->phba->vpi_ids[vport->vpi], | ||
| 2143 | reg_vfi->wwn[0], reg_vfi->wwn[1]); | ||
| 2136 | } | 2144 | } |
| 2137 | 2145 | ||
| 2138 | /** | 2146 | /** |
diff --git a/drivers/scsi/lpfc/lpfc_sli.c b/drivers/scsi/lpfc/lpfc_sli.c index e27cb44b3ec2..23a27592388c 100644 --- a/drivers/scsi/lpfc/lpfc_sli.c +++ b/drivers/scsi/lpfc/lpfc_sli.c | |||
| @@ -3619,8 +3619,8 @@ lpfc_sli_brdready(struct lpfc_hba *phba, uint32_t mask) | |||
| 3619 | * lpfc_reset_barrier - Make HBA ready for HBA reset | 3619 | * lpfc_reset_barrier - Make HBA ready for HBA reset |
| 3620 | * @phba: Pointer to HBA context object. | 3620 | * @phba: Pointer to HBA context object. |
| 3621 | * | 3621 | * |
| 3622 | * This function is called before resetting an HBA. This | 3622 | * This function is called before resetting an HBA. This function is called |
| 3623 | * function requests HBA to quiesce DMAs before a reset. | 3623 | * with hbalock held and requests HBA to quiesce DMAs before a reset. |
| 3624 | **/ | 3624 | **/ |
| 3625 | void lpfc_reset_barrier(struct lpfc_hba *phba) | 3625 | void lpfc_reset_barrier(struct lpfc_hba *phba) |
| 3626 | { | 3626 | { |
| @@ -6267,9 +6267,12 @@ lpfc_sli4_hba_setup(struct lpfc_hba *phba) | |||
| 6267 | goto out_unset_queue; | 6267 | goto out_unset_queue; |
| 6268 | } | 6268 | } |
| 6269 | } else if (phba->cfg_suppress_link_up == LPFC_INITIALIZE_LINK) { | 6269 | } else if (phba->cfg_suppress_link_up == LPFC_INITIALIZE_LINK) { |
| 6270 | rc = phba->lpfc_hba_init_link(phba, MBX_NOWAIT); | 6270 | /* don't perform init_link on SLI4 FC port loopback test */ |
| 6271 | if (rc) | 6271 | if (!(phba->link_flag & LS_LOOPBACK_MODE)) { |
| 6272 | goto out_unset_queue; | 6272 | rc = phba->lpfc_hba_init_link(phba, MBX_NOWAIT); |
| 6273 | if (rc) | ||
| 6274 | goto out_unset_queue; | ||
| 6275 | } | ||
| 6273 | } | 6276 | } |
| 6274 | mempool_free(mboxq, phba->mbox_mem_pool); | 6277 | mempool_free(mboxq, phba->mbox_mem_pool); |
| 6275 | return rc; | 6278 | return rc; |
| @@ -7540,6 +7543,7 @@ lpfc_sli4_bpl2sgl(struct lpfc_hba *phba, struct lpfc_iocbq *piocbq, | |||
| 7540 | struct ulp_bde64 *bpl = NULL; | 7543 | struct ulp_bde64 *bpl = NULL; |
| 7541 | struct ulp_bde64 bde; | 7544 | struct ulp_bde64 bde; |
| 7542 | struct sli4_sge *sgl = NULL; | 7545 | struct sli4_sge *sgl = NULL; |
| 7546 | struct lpfc_dmabuf *dmabuf; | ||
| 7543 | IOCB_t *icmd; | 7547 | IOCB_t *icmd; |
| 7544 | int numBdes = 0; | 7548 | int numBdes = 0; |
| 7545 | int i = 0; | 7549 | int i = 0; |
| @@ -7558,9 +7562,12 @@ lpfc_sli4_bpl2sgl(struct lpfc_hba *phba, struct lpfc_iocbq *piocbq, | |||
| 7558 | * have not been byteswapped yet so there is no | 7562 | * have not been byteswapped yet so there is no |
| 7559 | * need to swap them back. | 7563 | * need to swap them back. |
| 7560 | */ | 7564 | */ |
| 7561 | bpl = (struct ulp_bde64 *) | 7565 | if (piocbq->context3) |
| 7562 | ((struct lpfc_dmabuf *)piocbq->context3)->virt; | 7566 | dmabuf = (struct lpfc_dmabuf *)piocbq->context3; |
| 7567 | else | ||
| 7568 | return xritag; | ||
| 7563 | 7569 | ||
| 7570 | bpl = (struct ulp_bde64 *)dmabuf->virt; | ||
| 7564 | if (!bpl) | 7571 | if (!bpl) |
| 7565 | return xritag; | 7572 | return xritag; |
| 7566 | 7573 | ||
| @@ -7670,6 +7677,7 @@ lpfc_sli4_iocb2wqe(struct lpfc_hba *phba, struct lpfc_iocbq *iocbq, | |||
| 7670 | struct ulp_bde64 bde; | 7677 | struct ulp_bde64 bde; |
| 7671 | struct lpfc_nodelist *ndlp; | 7678 | struct lpfc_nodelist *ndlp; |
| 7672 | uint32_t *pcmd; | 7679 | uint32_t *pcmd; |
| 7680 | uint32_t if_type; | ||
| 7673 | 7681 | ||
| 7674 | fip = phba->hba_flag & HBA_FIP_SUPPORT; | 7682 | fip = phba->hba_flag & HBA_FIP_SUPPORT; |
| 7675 | /* The fcp commands will set command type */ | 7683 | /* The fcp commands will set command type */ |
| @@ -7743,7 +7751,9 @@ lpfc_sli4_iocb2wqe(struct lpfc_hba *phba, struct lpfc_iocbq *iocbq, | |||
| 7743 | >> LPFC_FIP_ELS_ID_SHIFT); | 7751 | >> LPFC_FIP_ELS_ID_SHIFT); |
| 7744 | pcmd = (uint32_t *) (((struct lpfc_dmabuf *) | 7752 | pcmd = (uint32_t *) (((struct lpfc_dmabuf *) |
| 7745 | iocbq->context2)->virt); | 7753 | iocbq->context2)->virt); |
| 7746 | if (phba->fc_topology == LPFC_TOPOLOGY_LOOP) { | 7754 | if_type = bf_get(lpfc_sli_intf_if_type, |
| 7755 | &phba->sli4_hba.sli_intf); | ||
| 7756 | if (if_type == LPFC_SLI_INTF_IF_TYPE_2) { | ||
| 7747 | if (pcmd && (*pcmd == ELS_CMD_FLOGI || | 7757 | if (pcmd && (*pcmd == ELS_CMD_FLOGI || |
| 7748 | *pcmd == ELS_CMD_SCR || | 7758 | *pcmd == ELS_CMD_SCR || |
| 7749 | *pcmd == ELS_CMD_PLOGI)) { | 7759 | *pcmd == ELS_CMD_PLOGI)) { |
| @@ -7776,6 +7786,8 @@ lpfc_sli4_iocb2wqe(struct lpfc_hba *phba, struct lpfc_iocbq *iocbq, | |||
| 7776 | /* The entire sequence is transmitted for this IOCB */ | 7786 | /* The entire sequence is transmitted for this IOCB */ |
| 7777 | xmit_len = total_len; | 7787 | xmit_len = total_len; |
| 7778 | cmnd = CMD_XMIT_SEQUENCE64_CR; | 7788 | cmnd = CMD_XMIT_SEQUENCE64_CR; |
| 7789 | if (phba->link_flag & LS_LOOPBACK_MODE) | ||
| 7790 | bf_set(wqe_xo, &wqe->xmit_sequence.wge_ctl, 1); | ||
| 7779 | case CMD_XMIT_SEQUENCE64_CR: | 7791 | case CMD_XMIT_SEQUENCE64_CR: |
| 7780 | /* word3 iocb=io_tag32 wqe=reserved */ | 7792 | /* word3 iocb=io_tag32 wqe=reserved */ |
| 7781 | wqe->xmit_sequence.rsvd3 = 0; | 7793 | wqe->xmit_sequence.rsvd3 = 0; |
