aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/megaraid
diff options
context:
space:
mode:
authoradam radford <aradford@gmail.com>2014-03-10 05:51:56 -0400
committerJames Bottomley <JBottomley@Parallels.com>2014-03-15 13:19:21 -0400
commit229fe47cd046ef2d01c13298293cda9693811417 (patch)
tree5fbc96b8332d466ddc2f1a903314fb3419677f17 /drivers/scsi/megaraid
parent3d0c24cd9bedf5a0665d60c8219a0a84c05abeb3 (diff)
[SCSI] megaraid_sas: Add Dell PowerEdge VRTX SR-IOV VF support
The following patch for megaraid_sas adds Dell PowerEdge VRTS SR-IOV VF support (Device ID 0x002f). This patch has some > 80 column lines that need to be left in place for code readability purposes. Signed-off-by: Adam Radford <aradford@gmail.com> Signed-off-by: James Bottomley <JBottomley@Parallels.com>
Diffstat (limited to 'drivers/scsi/megaraid')
-rw-r--r--drivers/scsi/megaraid/megaraid_sas.h100
-rw-r--r--drivers/scsi/megaraid/megaraid_sas_base.c634
-rw-r--r--drivers/scsi/megaraid/megaraid_sas_fusion.c232
-rw-r--r--drivers/scsi/megaraid/megaraid_sas_fusion.h3
4 files changed, 851 insertions, 118 deletions
diff --git a/drivers/scsi/megaraid/megaraid_sas.h b/drivers/scsi/megaraid/megaraid_sas.h
index a80e13ef9ffa..66be91249bfa 100644
--- a/drivers/scsi/megaraid/megaraid_sas.h
+++ b/drivers/scsi/megaraid/megaraid_sas.h
@@ -48,6 +48,7 @@
48#define PCI_DEVICE_ID_LSI_SAS0073SKINNY 0x0073 48#define PCI_DEVICE_ID_LSI_SAS0073SKINNY 0x0073
49#define PCI_DEVICE_ID_LSI_SAS0071SKINNY 0x0071 49#define PCI_DEVICE_ID_LSI_SAS0071SKINNY 0x0071
50#define PCI_DEVICE_ID_LSI_FUSION 0x005b 50#define PCI_DEVICE_ID_LSI_FUSION 0x005b
51#define PCI_DEVICE_ID_LSI_PLASMA 0x002f
51#define PCI_DEVICE_ID_LSI_INVADER 0x005d 52#define PCI_DEVICE_ID_LSI_INVADER 0x005d
52#define PCI_DEVICE_ID_LSI_FURY 0x005f 53#define PCI_DEVICE_ID_LSI_FURY 0x005f
53 54
@@ -559,7 +560,8 @@ struct megasas_ctrl_info {
559 u8 PCIE:1; 560 u8 PCIE:1;
560 u8 iSCSI:1; 561 u8 iSCSI:1;
561 u8 SAS_3G:1; 562 u8 SAS_3G:1;
562 u8 reserved_0:4; 563 u8 SRIOV:1;
564 u8 reserved_0:3;
563 u8 reserved_1[6]; 565 u8 reserved_1[6];
564 u8 port_count; 566 u8 port_count;
565 u64 port_addr[8]; 567 u64 port_addr[8];
@@ -839,7 +841,12 @@ struct megasas_ctrl_info {
839 841
840 struct { /*7A4h */ 842 struct { /*7A4h */
841#if defined(__BIG_ENDIAN_BITFIELD) 843#if defined(__BIG_ENDIAN_BITFIELD)
842 u32 reserved:11; 844 u32 reserved:5;
845 u32 activePassive:2;
846 u32 supportConfigAutoBalance:1;
847 u32 mpio:1;
848 u32 supportDataLDonSSCArray:1;
849 u32 supportPointInTimeProgress:1;
843 u32 supportUnevenSpans:1; 850 u32 supportUnevenSpans:1;
844 u32 dedicatedHotSparesLimited:1; 851 u32 dedicatedHotSparesLimited:1;
845 u32 headlessMode:1; 852 u32 headlessMode:1;
@@ -886,7 +893,12 @@ struct megasas_ctrl_info {
886 893
887 894
888 u32 supportUnevenSpans:1; 895 u32 supportUnevenSpans:1;
889 u32 reserved:11; 896 u32 supportPointInTimeProgress:1;
897 u32 supportDataLDonSSCArray:1;
898 u32 mpio:1;
899 u32 supportConfigAutoBalance:1;
900 u32 activePassive:2;
901 u32 reserved:5;
890#endif 902#endif
891 } adapterOperations2; 903 } adapterOperations2;
892 904
@@ -914,8 +926,14 @@ struct megasas_ctrl_info {
914 } cluster; 926 } cluster;
915 927
916 char clusterId[16]; /*7D4h */ 928 char clusterId[16]; /*7D4h */
929 struct {
930 u8 maxVFsSupported; /*0x7E4*/
931 u8 numVFsEnabled; /*0x7E5*/
932 u8 requestorId; /*0x7E6 0:PF, 1:VF1, 2:VF2*/
933 u8 reserved; /*0x7E7*/
934 } iov;
917 935
918 u8 pad[0x800-0x7E4]; /*7E4 */ 936 u8 pad[0x800-0x7E8]; /*0x7E8 pad to 2k */
919} __packed; 937} __packed;
920 938
921/* 939/*
@@ -986,7 +1004,9 @@ struct megasas_ctrl_info {
986 1004
987#define MFI_OB_INTR_STATUS_MASK 0x00000002 1005#define MFI_OB_INTR_STATUS_MASK 0x00000002
988#define MFI_POLL_TIMEOUT_SECS 60 1006#define MFI_POLL_TIMEOUT_SECS 60
989 1007#define MEGASAS_SRIOV_HEARTBEAT_INTERVAL_VF (5 * HZ)
1008#define MEGASAS_OCR_SETTLE_TIME_VF (1000 * 30)
1009#define MEGASAS_ROUTINE_WAIT_TIME_VF 300
990#define MFI_REPLY_1078_MESSAGE_INTERRUPT 0x80000000 1010#define MFI_REPLY_1078_MESSAGE_INTERRUPT 0x80000000
991#define MFI_REPLY_GEN2_MESSAGE_INTERRUPT 0x00000001 1011#define MFI_REPLY_GEN2_MESSAGE_INTERRUPT 0x00000001
992#define MFI_GEN2_ENABLE_INTERRUPT_MASK (0x00000001 | 0x00000004) 1012#define MFI_GEN2_ENABLE_INTERRUPT_MASK (0x00000001 | 0x00000004)
@@ -1529,6 +1549,12 @@ struct megasas_instance {
1529 dma_addr_t producer_h; 1549 dma_addr_t producer_h;
1530 u32 *consumer; 1550 u32 *consumer;
1531 dma_addr_t consumer_h; 1551 dma_addr_t consumer_h;
1552 struct MR_LD_VF_AFFILIATION *vf_affiliation;
1553 dma_addr_t vf_affiliation_h;
1554 struct MR_LD_VF_AFFILIATION_111 *vf_affiliation_111;
1555 dma_addr_t vf_affiliation_111_h;
1556 struct MR_CTRL_HB_HOST_MEM *hb_host_mem;
1557 dma_addr_t hb_host_mem_h;
1532 1558
1533 u32 *reply_queue; 1559 u32 *reply_queue;
1534 dma_addr_t reply_queue_h; 1560 dma_addr_t reply_queue_h;
@@ -1604,10 +1630,73 @@ struct megasas_instance {
1604 unsigned long bar; 1630 unsigned long bar;
1605 long reset_flags; 1631 long reset_flags;
1606 struct mutex reset_mutex; 1632 struct mutex reset_mutex;
1633 struct timer_list sriov_heartbeat_timer;
1634 char skip_heartbeat_timer_del;
1635 u8 requestorId;
1636 u64 initiator_sas_address;
1637 u64 ld_sas_address[64];
1638 char PlasmaFW111;
1639 char mpio;
1607 int throttlequeuedepth; 1640 int throttlequeuedepth;
1608 u8 mask_interrupts; 1641 u8 mask_interrupts;
1609 u8 is_imr; 1642 u8 is_imr;
1610}; 1643};
1644struct MR_LD_VF_MAP {
1645 u32 size;
1646 union MR_LD_REF ref;
1647 u8 ldVfCount;
1648 u8 reserved[6];
1649 u8 policy[1];
1650};
1651
1652struct MR_LD_VF_AFFILIATION {
1653 u32 size;
1654 u8 ldCount;
1655 u8 vfCount;
1656 u8 thisVf;
1657 u8 reserved[9];
1658 struct MR_LD_VF_MAP map[1];
1659};
1660
1661/* Plasma 1.11 FW backward compatibility structures */
1662#define IOV_111_OFFSET 0x7CE
1663#define MAX_VIRTUAL_FUNCTIONS 8
1664
1665struct IOV_111 {
1666 u8 maxVFsSupported;
1667 u8 numVFsEnabled;
1668 u8 requestorId;
1669 u8 reserved[5];
1670};
1671
1672struct MR_LD_VF_MAP_111 {
1673 u8 targetId;
1674 u8 reserved[3];
1675 u8 policy[MAX_VIRTUAL_FUNCTIONS];
1676};
1677
1678struct MR_LD_VF_AFFILIATION_111 {
1679 u8 vdCount;
1680 u8 vfCount;
1681 u8 thisVf;
1682 u8 reserved[5];
1683 struct MR_LD_VF_MAP_111 map[MAX_LOGICAL_DRIVES];
1684};
1685
1686struct MR_CTRL_HB_HOST_MEM {
1687 struct {
1688 u32 fwCounter; /* Firmware heart beat counter */
1689 struct {
1690 u32 debugmode:1; /* 1=Firmware is in debug mode.
1691 Heart beat will not be updated. */
1692 u32 reserved:31;
1693 } debug;
1694 u32 reserved_fw[6];
1695 u32 driverCounter; /* Driver heart beat counter. 0x20 */
1696 u32 reserved_driver[7];
1697 } HB;
1698 u8 pad[0x400-0x40];
1699};
1611 1700
1612enum { 1701enum {
1613 MEGASAS_HBA_OPERATIONAL = 0, 1702 MEGASAS_HBA_OPERATIONAL = 0,
@@ -1615,6 +1704,7 @@ enum {
1615 MEGASAS_ADPRESET_SM_FW_RESET_SUCCESS = 2, 1704 MEGASAS_ADPRESET_SM_FW_RESET_SUCCESS = 2,
1616 MEGASAS_ADPRESET_SM_OPERATIONAL = 3, 1705 MEGASAS_ADPRESET_SM_OPERATIONAL = 3,
1617 MEGASAS_HW_CRITICAL_ERROR = 4, 1706 MEGASAS_HW_CRITICAL_ERROR = 4,
1707 MEGASAS_ADPRESET_SM_POLLING = 5,
1618 MEGASAS_ADPRESET_INPROG_SIGN = 0xDEADDEAD, 1708 MEGASAS_ADPRESET_INPROG_SIGN = 0xDEADDEAD,
1619}; 1709};
1620 1710
diff --git a/drivers/scsi/megaraid/megaraid_sas_base.c b/drivers/scsi/megaraid/megaraid_sas_base.c
index c6203e677ab3..1fb7ab6e77bd 100644
--- a/drivers/scsi/megaraid/megaraid_sas_base.c
+++ b/drivers/scsi/megaraid/megaraid_sas_base.c
@@ -75,6 +75,10 @@ static unsigned int msix_vectors;
75module_param(msix_vectors, int, S_IRUGO); 75module_param(msix_vectors, int, S_IRUGO);
76MODULE_PARM_DESC(msix_vectors, "MSI-X max vector count. Default: Set by FW"); 76MODULE_PARM_DESC(msix_vectors, "MSI-X max vector count. Default: Set by FW");
77 77
78static int allow_vf_ioctls;
79module_param(allow_vf_ioctls, int, S_IRUGO);
80MODULE_PARM_DESC(allow_vf_ioctls, "Allow ioctls in SR-IOV VF mode. Default: 0");
81
78static int throttlequeuedepth = MEGASAS_THROTTLE_QUEUE_DEPTH; 82static int throttlequeuedepth = MEGASAS_THROTTLE_QUEUE_DEPTH;
79module_param(throttlequeuedepth, int, S_IRUGO); 83module_param(throttlequeuedepth, int, S_IRUGO);
80MODULE_PARM_DESC(throttlequeuedepth, 84MODULE_PARM_DESC(throttlequeuedepth,
@@ -122,6 +126,8 @@ static struct pci_device_id megasas_pci_table[] = {
122 /* xscale IOP */ 126 /* xscale IOP */
123 {PCI_DEVICE(PCI_VENDOR_ID_LSI_LOGIC, PCI_DEVICE_ID_LSI_FUSION)}, 127 {PCI_DEVICE(PCI_VENDOR_ID_LSI_LOGIC, PCI_DEVICE_ID_LSI_FUSION)},
124 /* Fusion */ 128 /* Fusion */
129 {PCI_DEVICE(PCI_VENDOR_ID_LSI_LOGIC, PCI_DEVICE_ID_LSI_PLASMA)},
130 /* Plasma */
125 {PCI_DEVICE(PCI_VENDOR_ID_LSI_LOGIC, PCI_DEVICE_ID_LSI_INVADER)}, 131 {PCI_DEVICE(PCI_VENDOR_ID_LSI_LOGIC, PCI_DEVICE_ID_LSI_INVADER)},
126 /* Invader */ 132 /* Invader */
127 {PCI_DEVICE(PCI_VENDOR_ID_LSI_LOGIC, PCI_DEVICE_ID_LSI_FURY)}, 133 {PCI_DEVICE(PCI_VENDOR_ID_LSI_LOGIC, PCI_DEVICE_ID_LSI_FURY)},
@@ -132,7 +138,7 @@ static struct pci_device_id megasas_pci_table[] = {
132MODULE_DEVICE_TABLE(pci, megasas_pci_table); 138MODULE_DEVICE_TABLE(pci, megasas_pci_table);
133 139
134static int megasas_mgmt_majorno; 140static int megasas_mgmt_majorno;
135static struct megasas_mgmt_info megasas_mgmt_info; 141struct megasas_mgmt_info megasas_mgmt_info;
136static struct fasync_struct *megasas_async_queue; 142static struct fasync_struct *megasas_async_queue;
137static DEFINE_MUTEX(megasas_async_queue_mutex); 143static DEFINE_MUTEX(megasas_async_queue_mutex);
138 144
@@ -171,10 +177,15 @@ megasas_get_map_info(struct megasas_instance *instance);
171int 177int
172megasas_sync_map_info(struct megasas_instance *instance); 178megasas_sync_map_info(struct megasas_instance *instance);
173int 179int
174wait_and_poll(struct megasas_instance *instance, struct megasas_cmd *cmd); 180wait_and_poll(struct megasas_instance *instance, struct megasas_cmd *cmd,
181 int seconds);
175void megasas_reset_reply_desc(struct megasas_instance *instance); 182void megasas_reset_reply_desc(struct megasas_instance *instance);
176int megasas_reset_fusion(struct Scsi_Host *shost); 183int megasas_reset_fusion(struct Scsi_Host *shost, int iotimeout);
177void megasas_fusion_ocr_wq(struct work_struct *work); 184void megasas_fusion_ocr_wq(struct work_struct *work);
185static int megasas_get_ld_vf_affiliation(struct megasas_instance *instance,
186 int initial);
187int megasas_check_mpio_paths(struct megasas_instance *instance,
188 struct scsi_cmnd *scmd);
178 189
179void 190void
180megasas_issue_dcmd(struct megasas_instance *instance, struct megasas_cmd *cmd) 191megasas_issue_dcmd(struct megasas_instance *instance, struct megasas_cmd *cmd)
@@ -224,6 +235,7 @@ megasas_return_cmd(struct megasas_instance *instance, struct megasas_cmd *cmd)
224 cmd->scmd = NULL; 235 cmd->scmd = NULL;
225 cmd->frame_count = 0; 236 cmd->frame_count = 0;
226 if ((instance->pdev->device != PCI_DEVICE_ID_LSI_FUSION) && 237 if ((instance->pdev->device != PCI_DEVICE_ID_LSI_FUSION) &&
238 (instance->pdev->device != PCI_DEVICE_ID_LSI_PLASMA) &&
227 (instance->pdev->device != PCI_DEVICE_ID_LSI_INVADER) && 239 (instance->pdev->device != PCI_DEVICE_ID_LSI_INVADER) &&
228 (instance->pdev->device != PCI_DEVICE_ID_LSI_FURY) && 240 (instance->pdev->device != PCI_DEVICE_ID_LSI_FURY) &&
229 (reset_devices)) 241 (reset_devices))
@@ -877,6 +889,7 @@ extern struct megasas_instance_template megasas_instance_template_fusion;
877int 889int
878megasas_issue_polled(struct megasas_instance *instance, struct megasas_cmd *cmd) 890megasas_issue_polled(struct megasas_instance *instance, struct megasas_cmd *cmd)
879{ 891{
892 int seconds;
880 893
881 struct megasas_header *frame_hdr = &cmd->frame->hdr; 894 struct megasas_header *frame_hdr = &cmd->frame->hdr;
882 895
@@ -891,7 +904,11 @@ megasas_issue_polled(struct megasas_instance *instance, struct megasas_cmd *cmd)
891 /* 904 /*
892 * Wait for cmd_status to change 905 * Wait for cmd_status to change
893 */ 906 */
894 return wait_and_poll(instance, cmd); 907 if (instance->requestorId)
908 seconds = MEGASAS_ROUTINE_WAIT_TIME_VF;
909 else
910 seconds = MFI_POLL_TIMEOUT_SECS;
911 return wait_and_poll(instance, cmd, seconds);
895} 912}
896 913
897/** 914/**
@@ -1532,9 +1549,23 @@ megasas_queue_command_lck(struct scsi_cmnd *scmd, void (*done) (struct scsi_cmnd
1532 1549
1533 spin_lock_irqsave(&instance->hba_lock, flags); 1550 spin_lock_irqsave(&instance->hba_lock, flags);
1534 1551
1552 /* Check for an mpio path and adjust behavior */
1553 if (instance->adprecovery == MEGASAS_ADPRESET_SM_INFAULT) {
1554 if (megasas_check_mpio_paths(instance, scmd) ==
1555 (DID_RESET << 16)) {
1556 spin_unlock_irqrestore(&instance->hba_lock, flags);
1557 return SCSI_MLQUEUE_HOST_BUSY;
1558 } else {
1559 spin_unlock_irqrestore(&instance->hba_lock, flags);
1560 scmd->result = DID_NO_CONNECT << 16;
1561 done(scmd);
1562 return 0;
1563 }
1564 }
1565
1535 if (instance->adprecovery == MEGASAS_HW_CRITICAL_ERROR) { 1566 if (instance->adprecovery == MEGASAS_HW_CRITICAL_ERROR) {
1536 spin_unlock_irqrestore(&instance->hba_lock, flags); 1567 spin_unlock_irqrestore(&instance->hba_lock, flags);
1537 scmd->result = DID_ERROR << 16; 1568 scmd->result = DID_NO_CONNECT << 16;
1538 done(scmd); 1569 done(scmd);
1539 return 0; 1570 return 0;
1540 } 1571 }
@@ -1659,9 +1690,14 @@ void megaraid_sas_kill_hba(struct megasas_instance *instance)
1659 if ((instance->pdev->device == PCI_DEVICE_ID_LSI_SAS0073SKINNY) || 1690 if ((instance->pdev->device == PCI_DEVICE_ID_LSI_SAS0073SKINNY) ||
1660 (instance->pdev->device == PCI_DEVICE_ID_LSI_SAS0071SKINNY) || 1691 (instance->pdev->device == PCI_DEVICE_ID_LSI_SAS0071SKINNY) ||
1661 (instance->pdev->device == PCI_DEVICE_ID_LSI_FUSION) || 1692 (instance->pdev->device == PCI_DEVICE_ID_LSI_FUSION) ||
1693 (instance->pdev->device == PCI_DEVICE_ID_LSI_PLASMA) ||
1662 (instance->pdev->device == PCI_DEVICE_ID_LSI_INVADER) || 1694 (instance->pdev->device == PCI_DEVICE_ID_LSI_INVADER) ||
1663 (instance->pdev->device == PCI_DEVICE_ID_LSI_FURY)) { 1695 (instance->pdev->device == PCI_DEVICE_ID_LSI_FURY)) {
1664 writel(MFI_STOP_ADP, &instance->reg_set->doorbell); 1696 writel(MFI_STOP_ADP, &instance->reg_set->doorbell);
1697 /* Flush */
1698 readl(&instance->reg_set->doorbell);
1699 if (instance->mpio && instance->requestorId)
1700 memset(instance->ld_ids, 0xff, MEGASAS_MAX_LD_IDS);
1665 } else { 1701 } else {
1666 writel(MFI_STOP_ADP, &instance->reg_set->inbound_doorbell); 1702 writel(MFI_STOP_ADP, &instance->reg_set->inbound_doorbell);
1667 } 1703 }
@@ -1748,6 +1784,25 @@ static void megasas_complete_cmd_dpc(unsigned long instance_addr)
1748 megasas_check_and_restore_queue_depth(instance); 1784 megasas_check_and_restore_queue_depth(instance);
1749} 1785}
1750 1786
1787/**
1788 * megasas_start_timer - Initializes a timer object
1789 * @instance: Adapter soft state
1790 * @timer: timer object to be initialized
1791 * @fn: timer function
1792 * @interval: time interval between timer function call
1793 *
1794 */
1795void megasas_start_timer(struct megasas_instance *instance,
1796 struct timer_list *timer,
1797 void *fn, unsigned long interval)
1798{
1799 init_timer(timer);
1800 timer->expires = jiffies + interval;
1801 timer->data = (unsigned long)instance;
1802 timer->function = fn;
1803 add_timer(timer);
1804}
1805
1751static void 1806static void
1752megasas_internal_reset_defer_cmds(struct megasas_instance *instance); 1807megasas_internal_reset_defer_cmds(struct megasas_instance *instance);
1753 1808
@@ -1770,6 +1825,295 @@ void megasas_do_ocr(struct megasas_instance *instance)
1770 process_fw_state_change_wq(&instance->work_init); 1825 process_fw_state_change_wq(&instance->work_init);
1771} 1826}
1772 1827
1828/* This function will get the current SR-IOV LD/VF affiliation */
1829static int megasas_get_ld_vf_affiliation(struct megasas_instance *instance,
1830 int initial)
1831{
1832 struct megasas_cmd *cmd;
1833 struct megasas_dcmd_frame *dcmd;
1834 struct MR_LD_VF_AFFILIATION *new_affiliation = NULL;
1835 struct MR_LD_VF_AFFILIATION_111 *new_affiliation_111 = NULL;
1836 struct MR_LD_VF_MAP *newmap = NULL, *savedmap = NULL;
1837 dma_addr_t new_affiliation_h;
1838 dma_addr_t new_affiliation_111_h;
1839 int ld, retval = 0;
1840 u8 thisVf;
1841
1842 cmd = megasas_get_cmd(instance);
1843
1844 if (!cmd) {
1845 printk(KERN_DEBUG "megasas: megasas_get_ld_vf_"
1846 "affiliation: Failed to get cmd for scsi%d.\n",
1847 instance->host->host_no);
1848 return -ENOMEM;
1849 }
1850
1851 dcmd = &cmd->frame->dcmd;
1852
1853 if (!instance->vf_affiliation && !instance->vf_affiliation_111) {
1854 printk(KERN_WARNING "megasas: SR-IOV: Couldn't get LD/VF "
1855 "affiliation for scsi%d.\n", instance->host->host_no);
1856 megasas_return_cmd(instance, cmd);
1857 return -ENOMEM;
1858 }
1859
1860 if (initial)
1861 if (instance->PlasmaFW111)
1862 memset(instance->vf_affiliation_111, 0,
1863 sizeof(struct MR_LD_VF_AFFILIATION_111));
1864 else
1865 memset(instance->vf_affiliation, 0,
1866 (MAX_LOGICAL_DRIVES + 1) *
1867 sizeof(struct MR_LD_VF_AFFILIATION));
1868 else {
1869 if (instance->PlasmaFW111)
1870 new_affiliation_111 =
1871 pci_alloc_consistent(instance->pdev,
1872 sizeof(struct MR_LD_VF_AFFILIATION_111),
1873 &new_affiliation_111_h);
1874 else
1875 new_affiliation =
1876 pci_alloc_consistent(instance->pdev,
1877 (MAX_LOGICAL_DRIVES + 1) *
1878 sizeof(struct MR_LD_VF_AFFILIATION),
1879 &new_affiliation_h);
1880 if (!new_affiliation && !new_affiliation_111) {
1881 printk(KERN_DEBUG "megasas: SR-IOV: Couldn't allocate "
1882 "memory for new affiliation for scsi%d.\n",
1883 instance->host->host_no);
1884 megasas_return_cmd(instance, cmd);
1885 return -ENOMEM;
1886 }
1887 if (instance->PlasmaFW111)
1888 memset(new_affiliation_111, 0,
1889 sizeof(struct MR_LD_VF_AFFILIATION_111));
1890 else
1891 memset(new_affiliation, 0, (MAX_LOGICAL_DRIVES + 1) *
1892 sizeof(struct MR_LD_VF_AFFILIATION));
1893 }
1894
1895 memset(dcmd->mbox.b, 0, MFI_MBOX_SIZE);
1896
1897 dcmd->cmd = MFI_CMD_DCMD;
1898 dcmd->cmd_status = 0xFF;
1899 dcmd->sge_count = 1;
1900 dcmd->flags = MFI_FRAME_DIR_BOTH;
1901 dcmd->timeout = 0;
1902 dcmd->pad_0 = 0;
1903 if (instance->PlasmaFW111) {
1904 dcmd->data_xfer_len = sizeof(struct MR_LD_VF_AFFILIATION_111);
1905 dcmd->opcode = MR_DCMD_LD_VF_MAP_GET_ALL_LDS_111;
1906 } else {
1907 dcmd->data_xfer_len = (MAX_LOGICAL_DRIVES + 1) *
1908 sizeof(struct MR_LD_VF_AFFILIATION);
1909 dcmd->opcode = MR_DCMD_LD_VF_MAP_GET_ALL_LDS;
1910 }
1911
1912 if (initial) {
1913 if (instance->PlasmaFW111)
1914 dcmd->sgl.sge32[0].phys_addr =
1915 instance->vf_affiliation_111_h;
1916 else
1917 dcmd->sgl.sge32[0].phys_addr =
1918 instance->vf_affiliation_h;
1919 } else {
1920 if (instance->PlasmaFW111)
1921 dcmd->sgl.sge32[0].phys_addr = new_affiliation_111_h;
1922 else
1923 dcmd->sgl.sge32[0].phys_addr = new_affiliation_h;
1924 }
1925 if (instance->PlasmaFW111)
1926 dcmd->sgl.sge32[0].length =
1927 sizeof(struct MR_LD_VF_AFFILIATION_111);
1928 else
1929 dcmd->sgl.sge32[0].length = (MAX_LOGICAL_DRIVES + 1) *
1930 sizeof(struct MR_LD_VF_AFFILIATION);
1931
1932 printk(KERN_WARNING "megasas: SR-IOV: Getting LD/VF affiliation for "
1933 "scsi%d\n", instance->host->host_no);
1934
1935 megasas_issue_blocked_cmd(instance, cmd, 0);
1936
1937 if (dcmd->cmd_status) {
1938 printk(KERN_WARNING "megasas: SR-IOV: LD/VF affiliation DCMD"
1939 " failed with status 0x%x for scsi%d.\n",
1940 dcmd->cmd_status, instance->host->host_no);
1941 retval = 1; /* Do a scan if we couldn't get affiliation */
1942 goto out;
1943 }
1944
1945 if (!initial) {
1946 if (instance->PlasmaFW111) {
1947 if (!new_affiliation_111->vdCount) {
1948 printk(KERN_WARNING "megasas: SR-IOV: Got new "
1949 "LD/VF affiliation for passive path "
1950 "for scsi%d.\n",
1951 instance->host->host_no);
1952 retval = 1;
1953 goto out;
1954 }
1955 thisVf = new_affiliation_111->thisVf;
1956 for (ld = 0 ; ld < new_affiliation_111->vdCount; ld++)
1957 if (instance->vf_affiliation_111->map[ld].policy[thisVf] != new_affiliation_111->map[ld].policy[thisVf]) {
1958 printk(KERN_WARNING "megasas: SR-IOV: "
1959 "Got new LD/VF affiliation "
1960 "for scsi%d.\n",
1961 instance->host->host_no);
1962 memcpy(instance->vf_affiliation_111,
1963 new_affiliation_111,
1964 sizeof(struct MR_LD_VF_AFFILIATION_111));
1965 retval = 1;
1966 goto out;
1967 }
1968 } else {
1969 if (!new_affiliation->ldCount) {
1970 printk(KERN_WARNING "megasas: SR-IOV: Got new "
1971 "LD/VF affiliation for passive "
1972 "path for scsi%d.\n",
1973 instance->host->host_no);
1974 retval = 1;
1975 goto out;
1976 }
1977 newmap = new_affiliation->map;
1978 savedmap = instance->vf_affiliation->map;
1979 thisVf = new_affiliation->thisVf;
1980 for (ld = 0 ; ld < new_affiliation->ldCount; ld++) {
1981 if (savedmap->policy[thisVf] !=
1982 newmap->policy[thisVf]) {
1983 printk(KERN_WARNING "megasas: SR-IOV: "
1984 "Got new LD/VF affiliation "
1985 "for scsi%d.\n",
1986 instance->host->host_no);
1987 memcpy(instance->vf_affiliation,
1988 new_affiliation,
1989 new_affiliation->size);
1990 retval = 1;
1991 goto out;
1992 }
1993 savedmap = (struct MR_LD_VF_MAP *)
1994 ((unsigned char *)savedmap +
1995 savedmap->size);
1996 newmap = (struct MR_LD_VF_MAP *)
1997 ((unsigned char *)newmap +
1998 newmap->size);
1999 }
2000 }
2001 }
2002out:
2003 if (new_affiliation) {
2004 if (instance->PlasmaFW111)
2005 pci_free_consistent(instance->pdev,
2006 sizeof(struct MR_LD_VF_AFFILIATION_111),
2007 new_affiliation_111,
2008 new_affiliation_111_h);
2009 else
2010 pci_free_consistent(instance->pdev,
2011 (MAX_LOGICAL_DRIVES + 1) *
2012 sizeof(struct MR_LD_VF_AFFILIATION),
2013 new_affiliation, new_affiliation_h);
2014 }
2015 megasas_return_cmd(instance, cmd);
2016
2017 return retval;
2018}
2019
2020/* This function will tell FW to start the SR-IOV heartbeat */
2021int megasas_sriov_start_heartbeat(struct megasas_instance *instance,
2022 int initial)
2023{
2024 struct megasas_cmd *cmd;
2025 struct megasas_dcmd_frame *dcmd;
2026 int retval = 0;
2027
2028 cmd = megasas_get_cmd(instance);
2029
2030 if (!cmd) {
2031 printk(KERN_DEBUG "megasas: megasas_sriov_start_heartbeat: "
2032 "Failed to get cmd for scsi%d.\n",
2033 instance->host->host_no);
2034 return -ENOMEM;
2035 }
2036
2037 dcmd = &cmd->frame->dcmd;
2038
2039 if (initial) {
2040 instance->hb_host_mem =
2041 pci_alloc_consistent(instance->pdev,
2042 sizeof(struct MR_CTRL_HB_HOST_MEM),
2043 &instance->hb_host_mem_h);
2044 if (!instance->hb_host_mem) {
2045 printk(KERN_DEBUG "megasas: SR-IOV: Couldn't allocate"
2046 " memory for heartbeat host memory for "
2047 "scsi%d.\n", instance->host->host_no);
2048 retval = -ENOMEM;
2049 goto out;
2050 }
2051 memset(instance->hb_host_mem, 0,
2052 sizeof(struct MR_CTRL_HB_HOST_MEM));
2053 }
2054
2055 memset(dcmd->mbox.b, 0, MFI_MBOX_SIZE);
2056
2057 dcmd->mbox.s[0] = sizeof(struct MR_CTRL_HB_HOST_MEM);
2058 dcmd->cmd = MFI_CMD_DCMD;
2059 dcmd->cmd_status = 0xFF;
2060 dcmd->sge_count = 1;
2061 dcmd->flags = MFI_FRAME_DIR_BOTH;
2062 dcmd->timeout = 0;
2063 dcmd->pad_0 = 0;
2064 dcmd->data_xfer_len = sizeof(struct MR_CTRL_HB_HOST_MEM);
2065 dcmd->opcode = MR_DCMD_CTRL_SHARED_HOST_MEM_ALLOC;
2066 dcmd->sgl.sge32[0].phys_addr = instance->hb_host_mem_h;
2067 dcmd->sgl.sge32[0].length = sizeof(struct MR_CTRL_HB_HOST_MEM);
2068
2069 printk(KERN_WARNING "megasas: SR-IOV: Starting heartbeat for scsi%d\n",
2070 instance->host->host_no);
2071
2072 if (!megasas_issue_polled(instance, cmd)) {
2073 retval = 0;
2074 } else {
2075 printk(KERN_WARNING "megasas: SR-IOV: MR_DCMD_CTRL_SHARED_HOST"
2076 "_MEM_ALLOC DCMD timed out for scsi%d\n",
2077 instance->host->host_no);
2078 retval = 1;
2079 goto out;
2080 }
2081
2082
2083 if (dcmd->cmd_status) {
2084 printk(KERN_WARNING "megasas: SR-IOV: MR_DCMD_CTRL_SHARED_HOST"
2085 "_MEM_ALLOC DCMD failed with status 0x%x for scsi%d\n",
2086 dcmd->cmd_status,
2087 instance->host->host_no);
2088 retval = 1;
2089 goto out;
2090 }
2091
2092out:
2093 megasas_return_cmd(instance, cmd);
2094
2095 return retval;
2096}
2097
2098/* Handler for SR-IOV heartbeat */
2099void megasas_sriov_heartbeat_handler(unsigned long instance_addr)
2100{
2101 struct megasas_instance *instance =
2102 (struct megasas_instance *)instance_addr;
2103
2104 if (instance->hb_host_mem->HB.fwCounter !=
2105 instance->hb_host_mem->HB.driverCounter) {
2106 instance->hb_host_mem->HB.driverCounter =
2107 instance->hb_host_mem->HB.fwCounter;
2108 mod_timer(&instance->sriov_heartbeat_timer,
2109 jiffies + MEGASAS_SRIOV_HEARTBEAT_INTERVAL_VF);
2110 } else {
2111 printk(KERN_WARNING "megasas: SR-IOV: Heartbeat never "
2112 "completed for scsi%d\n", instance->host->host_no);
2113 schedule_work(&instance->work_init);
2114 }
2115}
2116
1773/** 2117/**
1774 * megasas_wait_for_outstanding - Wait for all outstanding cmds 2118 * megasas_wait_for_outstanding - Wait for all outstanding cmds
1775 * @instance: Adapter soft state 2119 * @instance: Adapter soft state
@@ -2032,9 +2376,10 @@ static int megasas_reset_bus_host(struct scsi_cmnd *scmd)
2032 * First wait for all commands to complete 2376 * First wait for all commands to complete
2033 */ 2377 */
2034 if ((instance->pdev->device == PCI_DEVICE_ID_LSI_FUSION) || 2378 if ((instance->pdev->device == PCI_DEVICE_ID_LSI_FUSION) ||
2379 (instance->pdev->device == PCI_DEVICE_ID_LSI_PLASMA) ||
2035 (instance->pdev->device == PCI_DEVICE_ID_LSI_INVADER) || 2380 (instance->pdev->device == PCI_DEVICE_ID_LSI_INVADER) ||
2036 (instance->pdev->device == PCI_DEVICE_ID_LSI_FURY)) 2381 (instance->pdev->device == PCI_DEVICE_ID_LSI_FURY))
2037 ret = megasas_reset_fusion(scmd->device->host); 2382 ret = megasas_reset_fusion(scmd->device->host, 1);
2038 else 2383 else
2039 ret = megasas_generic_reset(scmd); 2384 ret = megasas_generic_reset(scmd);
2040 2385
@@ -2749,6 +3094,8 @@ megasas_transition_to_ready(struct megasas_instance *instance, int ocr)
2749 (instance->pdev->device == 3094 (instance->pdev->device ==
2750 PCI_DEVICE_ID_LSI_FUSION) || 3095 PCI_DEVICE_ID_LSI_FUSION) ||
2751 (instance->pdev->device == 3096 (instance->pdev->device ==
3097 PCI_DEVICE_ID_LSI_PLASMA) ||
3098 (instance->pdev->device ==
2752 PCI_DEVICE_ID_LSI_INVADER) || 3099 PCI_DEVICE_ID_LSI_INVADER) ||
2753 (instance->pdev->device == 3100 (instance->pdev->device ==
2754 PCI_DEVICE_ID_LSI_FURY)) { 3101 PCI_DEVICE_ID_LSI_FURY)) {
@@ -2773,6 +3120,8 @@ megasas_transition_to_ready(struct megasas_instance *instance, int ocr)
2773 (instance->pdev->device == 3120 (instance->pdev->device ==
2774 PCI_DEVICE_ID_LSI_FUSION) || 3121 PCI_DEVICE_ID_LSI_FUSION) ||
2775 (instance->pdev->device == 3122 (instance->pdev->device ==
3123 PCI_DEVICE_ID_LSI_PLASMA) ||
3124 (instance->pdev->device ==
2776 PCI_DEVICE_ID_LSI_INVADER) || 3125 PCI_DEVICE_ID_LSI_INVADER) ||
2777 (instance->pdev->device == 3126 (instance->pdev->device ==
2778 PCI_DEVICE_ID_LSI_FURY)) { 3127 PCI_DEVICE_ID_LSI_FURY)) {
@@ -2798,6 +3147,8 @@ megasas_transition_to_ready(struct megasas_instance *instance, int ocr)
2798 (instance->pdev->device 3147 (instance->pdev->device
2799 == PCI_DEVICE_ID_LSI_FUSION) || 3148 == PCI_DEVICE_ID_LSI_FUSION) ||
2800 (instance->pdev->device 3149 (instance->pdev->device
3150 == PCI_DEVICE_ID_LSI_PLASMA) ||
3151 (instance->pdev->device
2801 == PCI_DEVICE_ID_LSI_INVADER) || 3152 == PCI_DEVICE_ID_LSI_INVADER) ||
2802 (instance->pdev->device 3153 (instance->pdev->device
2803 == PCI_DEVICE_ID_LSI_FURY)) { 3154 == PCI_DEVICE_ID_LSI_FURY)) {
@@ -2806,6 +3157,8 @@ megasas_transition_to_ready(struct megasas_instance *instance, int ocr)
2806 if ((instance->pdev->device == 3157 if ((instance->pdev->device ==
2807 PCI_DEVICE_ID_LSI_FUSION) || 3158 PCI_DEVICE_ID_LSI_FUSION) ||
2808 (instance->pdev->device == 3159 (instance->pdev->device ==
3160 PCI_DEVICE_ID_LSI_PLASMA) ||
3161 (instance->pdev->device ==
2809 PCI_DEVICE_ID_LSI_INVADER) || 3162 PCI_DEVICE_ID_LSI_INVADER) ||
2810 (instance->pdev->device == 3163 (instance->pdev->device ==
2811 PCI_DEVICE_ID_LSI_FURY)) { 3164 PCI_DEVICE_ID_LSI_FURY)) {
@@ -3032,6 +3385,7 @@ static int megasas_create_frame_pool(struct megasas_instance *instance)
3032 cmd->frame->io.context = cpu_to_le32(cmd->index); 3385 cmd->frame->io.context = cpu_to_le32(cmd->index);
3033 cmd->frame->io.pad_0 = 0; 3386 cmd->frame->io.pad_0 = 0;
3034 if ((instance->pdev->device != PCI_DEVICE_ID_LSI_FUSION) && 3387 if ((instance->pdev->device != PCI_DEVICE_ID_LSI_FUSION) &&
3388 (instance->pdev->device != PCI_DEVICE_ID_LSI_PLASMA) &&
3035 (instance->pdev->device != PCI_DEVICE_ID_LSI_INVADER) && 3389 (instance->pdev->device != PCI_DEVICE_ID_LSI_INVADER) &&
3036 (instance->pdev->device != PCI_DEVICE_ID_LSI_FURY) && 3390 (instance->pdev->device != PCI_DEVICE_ID_LSI_FURY) &&
3037 (reset_devices)) 3391 (reset_devices))
@@ -3638,6 +3992,7 @@ static int megasas_init_fw(struct megasas_instance *instance)
3638 struct megasas_ctrl_info *ctrl_info; 3992 struct megasas_ctrl_info *ctrl_info;
3639 unsigned long bar_list; 3993 unsigned long bar_list;
3640 int i, loop, fw_msix_count = 0; 3994 int i, loop, fw_msix_count = 0;
3995 struct IOV_111 *iovPtr;
3641 3996
3642 /* Find first memory bar */ 3997 /* Find first memory bar */
3643 bar_list = pci_select_bars(instance->pdev, IORESOURCE_MEM); 3998 bar_list = pci_select_bars(instance->pdev, IORESOURCE_MEM);
@@ -3660,6 +4015,7 @@ static int megasas_init_fw(struct megasas_instance *instance)
3660 4015
3661 switch (instance->pdev->device) { 4016 switch (instance->pdev->device) {
3662 case PCI_DEVICE_ID_LSI_FUSION: 4017 case PCI_DEVICE_ID_LSI_FUSION:
4018 case PCI_DEVICE_ID_LSI_PLASMA:
3663 case PCI_DEVICE_ID_LSI_INVADER: 4019 case PCI_DEVICE_ID_LSI_INVADER:
3664 case PCI_DEVICE_ID_LSI_FURY: 4020 case PCI_DEVICE_ID_LSI_FURY:
3665 instance->instancet = &megasas_instance_template_fusion; 4021 instance->instancet = &megasas_instance_template_fusion;
@@ -3714,7 +4070,8 @@ static int megasas_init_fw(struct megasas_instance *instance)
3714 scratch_pad_2 = readl 4070 scratch_pad_2 = readl
3715 (&instance->reg_set->outbound_scratch_pad_2); 4071 (&instance->reg_set->outbound_scratch_pad_2);
3716 /* Check max MSI-X vectors */ 4072 /* Check max MSI-X vectors */
3717 if (instance->pdev->device == PCI_DEVICE_ID_LSI_FUSION) { 4073 if ((instance->pdev->device == PCI_DEVICE_ID_LSI_FUSION) ||
4074 (instance->pdev->device == PCI_DEVICE_ID_LSI_PLASMA)) {
3718 instance->msix_vectors = (scratch_pad_2 4075 instance->msix_vectors = (scratch_pad_2
3719 & MR_MAX_REPLY_QUEUES_OFFSET) + 1; 4076 & MR_MAX_REPLY_QUEUES_OFFSET) + 1;
3720 fw_msix_count = instance->msix_vectors; 4077 fw_msix_count = instance->msix_vectors;
@@ -3828,6 +4185,7 @@ static int megasas_init_fw(struct megasas_instance *instance)
3828 ctrl_info->properties.OnOffProperties.disableOnlineCtrlReset; 4185 ctrl_info->properties.OnOffProperties.disableOnlineCtrlReset;
3829 /* adapterOperations2 are converted into CPU arch*/ 4186 /* adapterOperations2 are converted into CPU arch*/
3830 le32_to_cpus((u32 *)&ctrl_info->adapterOperations2); 4187 le32_to_cpus((u32 *)&ctrl_info->adapterOperations2);
4188 instance->mpio = ctrl_info->adapterOperations2.mpio;
3831 instance->UnevenSpanSupport = 4189 instance->UnevenSpanSupport =
3832 ctrl_info->adapterOperations2.supportUnevenSpans; 4190 ctrl_info->adapterOperations2.supportUnevenSpans;
3833 if (instance->UnevenSpanSupport) { 4191 if (instance->UnevenSpanSupport) {
@@ -3840,6 +4198,20 @@ static int megasas_init_fw(struct megasas_instance *instance)
3840 fusion->fast_path_io = 0; 4198 fusion->fast_path_io = 0;
3841 4199
3842 } 4200 }
4201 if (ctrl_info->host_interface.SRIOV) {
4202 if (!ctrl_info->adapterOperations2.activePassive)
4203 instance->PlasmaFW111 = 1;
4204
4205 if (!instance->PlasmaFW111)
4206 instance->requestorId =
4207 ctrl_info->iov.requestorId;
4208 else {
4209 iovPtr = (struct IOV_111 *)((unsigned char *)ctrl_info + IOV_111_OFFSET);
4210 instance->requestorId = iovPtr->requestorId;
4211 }
4212 printk(KERN_WARNING "megaraid_sas: I am VF "
4213 "requestorId %d\n", instance->requestorId);
4214 }
3843 } 4215 }
3844 instance->max_sectors_per_req = instance->max_num_sge * 4216 instance->max_sectors_per_req = instance->max_num_sge *
3845 PAGE_SIZE / 512; 4217 PAGE_SIZE / 512;
@@ -3872,6 +4244,17 @@ static int megasas_init_fw(struct megasas_instance *instance)
3872 tasklet_init(&instance->isr_tasklet, instance->instancet->tasklet, 4244 tasklet_init(&instance->isr_tasklet, instance->instancet->tasklet,
3873 (unsigned long)instance); 4245 (unsigned long)instance);
3874 4246
4247 /* Launch SR-IOV heartbeat timer */
4248 if (instance->requestorId) {
4249 if (!megasas_sriov_start_heartbeat(instance, 1))
4250 megasas_start_timer(instance,
4251 &instance->sriov_heartbeat_timer,
4252 megasas_sriov_heartbeat_handler,
4253 MEGASAS_SRIOV_HEARTBEAT_INTERVAL_VF);
4254 else
4255 instance->skip_heartbeat_timer_del = 1;
4256 }
4257
3875 return 0; 4258 return 0;
3876 4259
3877fail_init_adapter: 4260fail_init_adapter:
@@ -4184,6 +4567,7 @@ static int megasas_io_attach(struct megasas_instance *instance)
4184 4567
4185 /* Fusion only supports host reset */ 4568 /* Fusion only supports host reset */
4186 if ((instance->pdev->device == PCI_DEVICE_ID_LSI_FUSION) || 4569 if ((instance->pdev->device == PCI_DEVICE_ID_LSI_FUSION) ||
4570 (instance->pdev->device == PCI_DEVICE_ID_LSI_PLASMA) ||
4187 (instance->pdev->device == PCI_DEVICE_ID_LSI_INVADER) || 4571 (instance->pdev->device == PCI_DEVICE_ID_LSI_INVADER) ||
4188 (instance->pdev->device == PCI_DEVICE_ID_LSI_FURY)) { 4572 (instance->pdev->device == PCI_DEVICE_ID_LSI_FURY)) {
4189 host->hostt->eh_device_reset_handler = NULL; 4573 host->hostt->eh_device_reset_handler = NULL;
@@ -4309,6 +4693,7 @@ static int megasas_probe_one(struct pci_dev *pdev,
4309 4693
4310 switch (instance->pdev->device) { 4694 switch (instance->pdev->device) {
4311 case PCI_DEVICE_ID_LSI_FUSION: 4695 case PCI_DEVICE_ID_LSI_FUSION:
4696 case PCI_DEVICE_ID_LSI_PLASMA:
4312 case PCI_DEVICE_ID_LSI_INVADER: 4697 case PCI_DEVICE_ID_LSI_INVADER:
4313 case PCI_DEVICE_ID_LSI_FURY: 4698 case PCI_DEVICE_ID_LSI_FURY:
4314 { 4699 {
@@ -4405,6 +4790,7 @@ static int megasas_probe_one(struct pci_dev *pdev,
4405 instance->UnevenSpanSupport = 0; 4790 instance->UnevenSpanSupport = 0;
4406 4791
4407 if ((instance->pdev->device == PCI_DEVICE_ID_LSI_FUSION) || 4792 if ((instance->pdev->device == PCI_DEVICE_ID_LSI_FUSION) ||
4793 (instance->pdev->device == PCI_DEVICE_ID_LSI_PLASMA) ||
4408 (instance->pdev->device == PCI_DEVICE_ID_LSI_INVADER) || 4794 (instance->pdev->device == PCI_DEVICE_ID_LSI_INVADER) ||
4409 (instance->pdev->device == PCI_DEVICE_ID_LSI_FURY)) 4795 (instance->pdev->device == PCI_DEVICE_ID_LSI_FURY))
4410 INIT_WORK(&instance->work_init, megasas_fusion_ocr_wq); 4796 INIT_WORK(&instance->work_init, megasas_fusion_ocr_wq);
@@ -4417,6 +4803,26 @@ static int megasas_probe_one(struct pci_dev *pdev,
4417 if (megasas_init_fw(instance)) 4803 if (megasas_init_fw(instance))
4418 goto fail_init_mfi; 4804 goto fail_init_mfi;
4419 4805
4806 if (instance->requestorId) {
4807 if (instance->PlasmaFW111) {
4808 instance->vf_affiliation_111 =
4809 pci_alloc_consistent(pdev, sizeof(struct MR_LD_VF_AFFILIATION_111),
4810 &instance->vf_affiliation_111_h);
4811 if (!instance->vf_affiliation_111)
4812 printk(KERN_WARNING "megasas: Can't allocate "
4813 "memory for VF affiliation buffer\n");
4814 } else {
4815 instance->vf_affiliation =
4816 pci_alloc_consistent(pdev,
4817 (MAX_LOGICAL_DRIVES + 1) *
4818 sizeof(struct MR_LD_VF_AFFILIATION),
4819 &instance->vf_affiliation_h);
4820 if (!instance->vf_affiliation)
4821 printk(KERN_WARNING "megasas: Can't allocate "
4822 "memory for VF affiliation buffer\n");
4823 }
4824 }
4825
4420retry_irq_register: 4826retry_irq_register:
4421 /* 4827 /*
4422 * Register IRQ 4828 * Register IRQ
@@ -4511,6 +4917,7 @@ retry_irq_register:
4511 free_irq(instance->pdev->irq, &instance->irq_context[0]); 4917 free_irq(instance->pdev->irq, &instance->irq_context[0]);
4512fail_irq: 4918fail_irq:
4513 if ((instance->pdev->device == PCI_DEVICE_ID_LSI_FUSION) || 4919 if ((instance->pdev->device == PCI_DEVICE_ID_LSI_FUSION) ||
4920 (instance->pdev->device == PCI_DEVICE_ID_LSI_PLASMA) ||
4514 (instance->pdev->device == PCI_DEVICE_ID_LSI_INVADER) || 4921 (instance->pdev->device == PCI_DEVICE_ID_LSI_INVADER) ||
4515 (instance->pdev->device == PCI_DEVICE_ID_LSI_FURY)) 4922 (instance->pdev->device == PCI_DEVICE_ID_LSI_FURY))
4516 megasas_release_fusion(instance); 4923 megasas_release_fusion(instance);
@@ -4644,6 +5051,10 @@ megasas_suspend(struct pci_dev *pdev, pm_message_t state)
4644 host = instance->host; 5051 host = instance->host;
4645 instance->unload = 1; 5052 instance->unload = 1;
4646 5053
5054 /* Shutdown SR-IOV heartbeat timer */
5055 if (instance->requestorId && !instance->skip_heartbeat_timer_del)
5056 del_timer_sync(&instance->sriov_heartbeat_timer);
5057
4647 megasas_flush_cache(instance); 5058 megasas_flush_cache(instance);
4648 megasas_shutdown_controller(instance, MR_DCMD_HIBERNATE_SHUTDOWN); 5059 megasas_shutdown_controller(instance, MR_DCMD_HIBERNATE_SHUTDOWN);
4649 5060
@@ -4730,6 +5141,7 @@ megasas_resume(struct pci_dev *pdev)
4730 5141
4731 switch (instance->pdev->device) { 5142 switch (instance->pdev->device) {
4732 case PCI_DEVICE_ID_LSI_FUSION: 5143 case PCI_DEVICE_ID_LSI_FUSION:
5144 case PCI_DEVICE_ID_LSI_PLASMA:
4733 case PCI_DEVICE_ID_LSI_INVADER: 5145 case PCI_DEVICE_ID_LSI_INVADER:
4734 case PCI_DEVICE_ID_LSI_FURY: 5146 case PCI_DEVICE_ID_LSI_FURY:
4735 { 5147 {
@@ -4795,6 +5207,17 @@ megasas_resume(struct pci_dev *pdev)
4795 } 5207 }
4796 } 5208 }
4797 5209
5210 /* Re-launch SR-IOV heartbeat timer */
5211 if (instance->requestorId) {
5212 if (!megasas_sriov_start_heartbeat(instance, 0))
5213 megasas_start_timer(instance,
5214 &instance->sriov_heartbeat_timer,
5215 megasas_sriov_heartbeat_handler,
5216 MEGASAS_SRIOV_HEARTBEAT_INTERVAL_VF);
5217 else
5218 instance->skip_heartbeat_timer_del = 1;
5219 }
5220
4798 instance->instancet->enable_intr(instance); 5221 instance->instancet->enable_intr(instance);
4799 instance->unload = 0; 5222 instance->unload = 0;
4800 5223
@@ -4849,6 +5272,10 @@ static void megasas_detach_one(struct pci_dev *pdev)
4849 host = instance->host; 5272 host = instance->host;
4850 fusion = instance->ctrl_context; 5273 fusion = instance->ctrl_context;
4851 5274
5275 /* Shutdown SR-IOV heartbeat timer */
5276 if (instance->requestorId && !instance->skip_heartbeat_timer_del)
5277 del_timer_sync(&instance->sriov_heartbeat_timer);
5278
4852 scsi_remove_host(instance->host); 5279 scsi_remove_host(instance->host);
4853 megasas_flush_cache(instance); 5280 megasas_flush_cache(instance);
4854 megasas_shutdown_controller(instance, MR_DCMD_CTRL_SHUTDOWN); 5281 megasas_shutdown_controller(instance, MR_DCMD_CTRL_SHUTDOWN);
@@ -4894,6 +5321,7 @@ static void megasas_detach_one(struct pci_dev *pdev)
4894 5321
4895 switch (instance->pdev->device) { 5322 switch (instance->pdev->device) {
4896 case PCI_DEVICE_ID_LSI_FUSION: 5323 case PCI_DEVICE_ID_LSI_FUSION:
5324 case PCI_DEVICE_ID_LSI_PLASMA:
4897 case PCI_DEVICE_ID_LSI_INVADER: 5325 case PCI_DEVICE_ID_LSI_INVADER:
4898 case PCI_DEVICE_ID_LSI_FURY: 5326 case PCI_DEVICE_ID_LSI_FURY:
4899 megasas_release_fusion(instance); 5327 megasas_release_fusion(instance);
@@ -4920,6 +5348,24 @@ static void megasas_detach_one(struct pci_dev *pdev)
4920 if (instance->evt_detail) 5348 if (instance->evt_detail)
4921 pci_free_consistent(pdev, sizeof(struct megasas_evt_detail), 5349 pci_free_consistent(pdev, sizeof(struct megasas_evt_detail),
4922 instance->evt_detail, instance->evt_detail_h); 5350 instance->evt_detail, instance->evt_detail_h);
5351
5352 if (instance->vf_affiliation)
5353 pci_free_consistent(pdev, (MAX_LOGICAL_DRIVES + 1) *
5354 sizeof(struct MR_LD_VF_AFFILIATION),
5355 instance->vf_affiliation,
5356 instance->vf_affiliation_h);
5357
5358 if (instance->vf_affiliation_111)
5359 pci_free_consistent(pdev,
5360 sizeof(struct MR_LD_VF_AFFILIATION_111),
5361 instance->vf_affiliation_111,
5362 instance->vf_affiliation_111_h);
5363
5364 if (instance->hb_host_mem)
5365 pci_free_consistent(pdev, sizeof(struct MR_CTRL_HB_HOST_MEM),
5366 instance->hb_host_mem,
5367 instance->hb_host_mem_h);
5368
4923 scsi_host_put(host); 5369 scsi_host_put(host);
4924 5370
4925 pci_disable_device(pdev); 5371 pci_disable_device(pdev);
@@ -5208,6 +5654,16 @@ static int megasas_mgmt_ioctl_fw(struct file *file, unsigned long arg)
5208 goto out_kfree_ioc; 5654 goto out_kfree_ioc;
5209 } 5655 }
5210 5656
5657 /* Adjust ioctl wait time for VF mode */
5658 if (instance->requestorId)
5659 wait_time = MEGASAS_ROUTINE_WAIT_TIME_VF;
5660
5661 /* Block ioctls in VF mode */
5662 if (instance->requestorId && !allow_vf_ioctls) {
5663 error = -ENODEV;
5664 goto out_kfree_ioc;
5665 }
5666
5211 if (instance->adprecovery == MEGASAS_HW_CRITICAL_ERROR) { 5667 if (instance->adprecovery == MEGASAS_HW_CRITICAL_ERROR) {
5212 printk(KERN_ERR "Controller in crit error\n"); 5668 printk(KERN_ERR "Controller in crit error\n");
5213 error = -ENODEV; 5669 error = -ENODEV;
@@ -5517,7 +5973,7 @@ megasas_aen_polling(struct work_struct *work)
5517 u16 pd_index = 0; 5973 u16 pd_index = 0;
5518 u16 ld_index = 0; 5974 u16 ld_index = 0;
5519 int i, j, doscan = 0; 5975 int i, j, doscan = 0;
5520 u32 seq_num; 5976 u32 seq_num, wait_time = MEGASAS_RESET_WAIT_TIME;
5521 int error; 5977 int error;
5522 5978
5523 if (!instance) { 5979 if (!instance) {
@@ -5525,6 +5981,23 @@ megasas_aen_polling(struct work_struct *work)
5525 kfree(ev); 5981 kfree(ev);
5526 return; 5982 return;
5527 } 5983 }
5984
5985 /* Adjust event workqueue thread wait time for VF mode */
5986 if (instance->requestorId)
5987 wait_time = MEGASAS_ROUTINE_WAIT_TIME_VF;
5988
5989 /* Don't run the event workqueue thread if OCR is running */
5990 for (i = 0; i < wait_time; i++) {
5991 if (instance->adprecovery == MEGASAS_HBA_OPERATIONAL)
5992 break;
5993 if (!(i % MEGASAS_RESET_NOTICE_INTERVAL)) {
5994 printk(KERN_NOTICE "megasas: %s waiting for "
5995 "controller reset to finish for scsi%d\n",
5996 __func__, instance->host->host_no);
5997 }
5998 msleep(1000);
5999 }
6000
5528 instance->ev = NULL; 6001 instance->ev = NULL;
5529 host = instance->host; 6002 host = instance->host;
5530 if (instance->evt_detail) { 6003 if (instance->evt_detail) {
@@ -5591,65 +6064,64 @@ megasas_aen_polling(struct work_struct *work)
5591 case MR_EVT_LD_OFFLINE: 6064 case MR_EVT_LD_OFFLINE:
5592 case MR_EVT_CFG_CLEARED: 6065 case MR_EVT_CFG_CLEARED:
5593 case MR_EVT_LD_DELETED: 6066 case MR_EVT_LD_DELETED:
5594 if (megasas_ld_list_query(instance, 6067 if (!instance->requestorId ||
5595 MR_LD_QUERY_TYPE_EXPOSED_TO_HOST)) 6068 (instance->requestorId &&
5596 megasas_get_ld_list(instance); 6069 megasas_get_ld_vf_affiliation(instance, 0))) {
5597 for (i = 0; i < MEGASAS_MAX_LD_CHANNELS; i++) { 6070 if (megasas_ld_list_query(instance,
5598 for (j = 0; 6071 MR_LD_QUERY_TYPE_EXPOSED_TO_HOST))
5599 j < MEGASAS_MAX_DEV_PER_CHANNEL; 6072 megasas_get_ld_list(instance);
5600 j++) { 6073 for (i = 0; i < MEGASAS_MAX_LD_CHANNELS; i++) {
5601 6074 for (j = 0;
5602 ld_index = 6075 j < MEGASAS_MAX_DEV_PER_CHANNEL;
5603 (i * MEGASAS_MAX_DEV_PER_CHANNEL) + j; 6076 j++) {
5604 6077
5605 sdev1 = scsi_device_lookup(host, 6078 ld_index =
5606 MEGASAS_MAX_PD_CHANNELS + i, 6079 (i * MEGASAS_MAX_DEV_PER_CHANNEL) + j;
5607 j, 6080
5608 0); 6081 sdev1 = scsi_device_lookup(host, MEGASAS_MAX_PD_CHANNELS + i, j, 0);
5609 6082
5610 if (instance->ld_ids[ld_index] != 0xff) { 6083 if (instance->ld_ids[ld_index]
5611 if (sdev1) { 6084 != 0xff) {
5612 scsi_device_put(sdev1); 6085 if (sdev1)
5613 } 6086 scsi_device_put(sdev1);
5614 } else { 6087 } else {
5615 if (sdev1) { 6088 if (sdev1) {
5616 scsi_remove_device(sdev1); 6089 scsi_remove_device(sdev1);
5617 scsi_device_put(sdev1); 6090 scsi_device_put(sdev1);
6091 }
6092 }
5618 } 6093 }
5619 } 6094 }
5620 } 6095 doscan = 0;
5621 } 6096 }
5622 doscan = 0;
5623 break; 6097 break;
5624 case MR_EVT_LD_CREATED: 6098 case MR_EVT_LD_CREATED:
5625 if (megasas_ld_list_query(instance, 6099 if (!instance->requestorId ||
5626 MR_LD_QUERY_TYPE_EXPOSED_TO_HOST)) 6100 (instance->requestorId &&
5627 megasas_get_ld_list(instance); 6101 megasas_get_ld_vf_affiliation(instance, 0))) {
5628 for (i = 0; i < MEGASAS_MAX_LD_CHANNELS; i++) { 6102 if (megasas_ld_list_query(instance,
5629 for (j = 0; 6103 MR_LD_QUERY_TYPE_EXPOSED_TO_HOST))
5630 j < MEGASAS_MAX_DEV_PER_CHANNEL; 6104 megasas_get_ld_list(instance);
5631 j++) { 6105 for (i = 0; i < MEGASAS_MAX_LD_CHANNELS; i++) {
5632 ld_index = 6106 for (j = 0;
5633 (i * MEGASAS_MAX_DEV_PER_CHANNEL) + j; 6107 j < MEGASAS_MAX_DEV_PER_CHANNEL;
5634 6108 j++) {
5635 sdev1 = scsi_device_lookup(host, 6109 ld_index =
5636 MEGASAS_MAX_PD_CHANNELS + i, 6110 (i * MEGASAS_MAX_DEV_PER_CHANNEL) + j;
5637 j, 0); 6111
5638 6112 sdev1 = scsi_device_lookup(host, MEGASAS_MAX_PD_CHANNELS + i, j, 0);
5639 if (instance->ld_ids[ld_index] != 6113
5640 0xff) { 6114 if (instance->ld_ids[ld_index]
5641 if (!sdev1) { 6115 != 0xff) {
5642 scsi_add_device(host, 6116 if (!sdev1)
5643 MEGASAS_MAX_PD_CHANNELS + i, 6117 scsi_add_device(host, MEGASAS_MAX_PD_CHANNELS + i, j, 0);
5644 j, 0);
5645 } 6118 }
5646 } 6119 if (sdev1)
5647 if (sdev1) { 6120 scsi_device_put(sdev1);
5648 scsi_device_put(sdev1);
5649 } 6121 }
5650 } 6122 }
6123 doscan = 0;
5651 } 6124 }
5652 doscan = 0;
5653 break; 6125 break;
5654 case MR_EVT_CTRL_HOST_BUS_SCAN_REQUESTED: 6126 case MR_EVT_CTRL_HOST_BUS_SCAN_REQUESTED:
5655 case MR_EVT_FOREIGN_CFG_IMPORTED: 6127 case MR_EVT_FOREIGN_CFG_IMPORTED:
@@ -5667,7 +6139,8 @@ megasas_aen_polling(struct work_struct *work)
5667 } 6139 }
5668 6140
5669 if (doscan) { 6141 if (doscan) {
5670 printk(KERN_INFO "scanning ...\n"); 6142 printk(KERN_INFO "megaraid_sas: scanning for scsi%d...\n",
6143 instance->host->host_no);
5671 if (megasas_get_pd_list(instance) == 0) { 6144 if (megasas_get_pd_list(instance) == 0) {
5672 for (i = 0; i < MEGASAS_MAX_PD_CHANNELS; i++) { 6145 for (i = 0; i < MEGASAS_MAX_PD_CHANNELS; i++) {
5673 for (j = 0; j < MEGASAS_MAX_DEV_PER_CHANNEL; j++) { 6146 for (j = 0; j < MEGASAS_MAX_DEV_PER_CHANNEL; j++) {
@@ -5690,28 +6163,31 @@ megasas_aen_polling(struct work_struct *work)
5690 } 6163 }
5691 } 6164 }
5692 6165
5693 if (megasas_ld_list_query(instance, 6166 if (!instance->requestorId ||
5694 MR_LD_QUERY_TYPE_EXPOSED_TO_HOST)) 6167 (instance->requestorId &&
5695 megasas_get_ld_list(instance); 6168 megasas_get_ld_vf_affiliation(instance, 0))) {
5696 for (i = 0; i < MEGASAS_MAX_LD_CHANNELS; i++) { 6169 if (megasas_ld_list_query(instance,
5697 for (j = 0; j < MEGASAS_MAX_DEV_PER_CHANNEL; j++) { 6170 MR_LD_QUERY_TYPE_EXPOSED_TO_HOST))
5698 ld_index = 6171 megasas_get_ld_list(instance);
5699 (i * MEGASAS_MAX_DEV_PER_CHANNEL) + j; 6172 for (i = 0; i < MEGASAS_MAX_LD_CHANNELS; i++) {
6173 for (j = 0; j < MEGASAS_MAX_DEV_PER_CHANNEL;
6174 j++) {
6175 ld_index =
6176 (i * MEGASAS_MAX_DEV_PER_CHANNEL) + j;
5700 6177
5701 sdev1 = scsi_device_lookup(host, 6178 sdev1 = scsi_device_lookup(host,
5702 MEGASAS_MAX_PD_CHANNELS + i, j, 0); 6179 MEGASAS_MAX_PD_CHANNELS + i, j, 0);
5703 if (instance->ld_ids[ld_index] != 0xff) { 6180 if (instance->ld_ids[ld_index]
5704 if (!sdev1) { 6181 != 0xff) {
5705 scsi_add_device(host, 6182 if (!sdev1)
5706 MEGASAS_MAX_PD_CHANNELS + i, 6183 scsi_add_device(host, MEGASAS_MAX_PD_CHANNELS + i, j, 0);
5707 j, 0); 6184 else
6185 scsi_device_put(sdev1);
5708 } else { 6186 } else {
5709 scsi_device_put(sdev1); 6187 if (sdev1) {
5710 } 6188 scsi_remove_device(sdev1);
5711 } else { 6189 scsi_device_put(sdev1);
5712 if (sdev1) { 6190 }
5713 scsi_remove_device(sdev1);
5714 scsi_device_put(sdev1);
5715 } 6191 }
5716 } 6192 }
5717 } 6193 }
diff --git a/drivers/scsi/megaraid/megaraid_sas_fusion.c b/drivers/scsi/megaraid/megaraid_sas_fusion.c
index 99b7bffb36fe..22600419ae9f 100644
--- a/drivers/scsi/megaraid/megaraid_sas_fusion.c
+++ b/drivers/scsi/megaraid/megaraid_sas_fusion.c
@@ -62,7 +62,8 @@ megasas_complete_cmd(struct megasas_instance *instance,
62 struct megasas_cmd *cmd, u8 alt_status); 62 struct megasas_cmd *cmd, u8 alt_status);
63int megasas_is_ldio(struct scsi_cmnd *cmd); 63int megasas_is_ldio(struct scsi_cmnd *cmd);
64int 64int
65wait_and_poll(struct megasas_instance *instance, struct megasas_cmd *cmd); 65wait_and_poll(struct megasas_instance *instance, struct megasas_cmd *cmd,
66 int seconds);
66 67
67void 68void
68megasas_return_cmd(struct megasas_instance *instance, struct megasas_cmd *cmd); 69megasas_return_cmd(struct megasas_instance *instance, struct megasas_cmd *cmd);
@@ -81,6 +82,13 @@ int megasas_transition_to_ready(struct megasas_instance *instance, int ocr);
81void megaraid_sas_kill_hba(struct megasas_instance *instance); 82void megaraid_sas_kill_hba(struct megasas_instance *instance);
82 83
83extern u32 megasas_dbg_lvl; 84extern u32 megasas_dbg_lvl;
85void megasas_sriov_heartbeat_handler(unsigned long instance_addr);
86int megasas_sriov_start_heartbeat(struct megasas_instance *instance,
87 int initial);
88void megasas_start_timer(struct megasas_instance *instance,
89 struct timer_list *timer,
90 void *fn, unsigned long interval);
91extern struct megasas_mgmt_info megasas_mgmt_info;
84extern int resetwaittime; 92extern int resetwaittime;
85 93
86/** 94/**
@@ -549,12 +557,13 @@ fail_req_desc:
549 * For polling, MFI requires the cmd_status to be set to 0xFF before posting. 557 * For polling, MFI requires the cmd_status to be set to 0xFF before posting.
550 */ 558 */
551int 559int
552wait_and_poll(struct megasas_instance *instance, struct megasas_cmd *cmd) 560wait_and_poll(struct megasas_instance *instance, struct megasas_cmd *cmd,
561 int seconds)
553{ 562{
554 int i; 563 int i;
555 struct megasas_header *frame_hdr = &cmd->frame->hdr; 564 struct megasas_header *frame_hdr = &cmd->frame->hdr;
556 565
557 u32 msecs = MFI_POLL_TIMEOUT_SECS * 1000; 566 u32 msecs = seconds * 1000;
558 567
559 /* 568 /*
560 * Wait for cmd_status to change 569 * Wait for cmd_status to change
@@ -672,7 +681,7 @@ megasas_ioc_init_fusion(struct megasas_instance *instance)
672 instance->instancet->fire_cmd(instance, req_desc.u.low, 681 instance->instancet->fire_cmd(instance, req_desc.u.low,
673 req_desc.u.high, instance->reg_set); 682 req_desc.u.high, instance->reg_set);
674 683
675 wait_and_poll(instance, cmd); 684 wait_and_poll(instance, cmd, MFI_POLL_TIMEOUT_SECS);
676 685
677 frame_hdr = &cmd->frame->hdr; 686 frame_hdr = &cmd->frame->hdr;
678 if (frame_hdr->cmd_status != 0) { 687 if (frame_hdr->cmd_status != 0) {
@@ -1772,7 +1781,8 @@ megasas_get_request_descriptor(struct megasas_instance *instance, u16 index)
1772 1781
1773 if (index >= instance->max_fw_cmds) { 1782 if (index >= instance->max_fw_cmds) {
1774 printk(KERN_ERR "megasas: Invalid SMID (0x%x)request for " 1783 printk(KERN_ERR "megasas: Invalid SMID (0x%x)request for "
1775 "descriptor\n", index); 1784 "descriptor for scsi%d\n", index,
1785 instance->host->host_no);
1776 return NULL; 1786 return NULL;
1777 } 1787 }
1778 fusion = instance->ctrl_context; 1788 fusion = instance->ctrl_context;
@@ -2040,8 +2050,11 @@ irqreturn_t megasas_isr_fusion(int irq, void *devp)
2040 /* If we didn't complete any commands, check for FW fault */ 2050 /* If we didn't complete any commands, check for FW fault */
2041 fw_state = instance->instancet->read_fw_status_reg( 2051 fw_state = instance->instancet->read_fw_status_reg(
2042 instance->reg_set) & MFI_STATE_MASK; 2052 instance->reg_set) & MFI_STATE_MASK;
2043 if (fw_state == MFI_STATE_FAULT) 2053 if (fw_state == MFI_STATE_FAULT) {
2054 printk(KERN_WARNING "megaraid_sas: Iop2SysDoorbellInt"
2055 "for scsi%d\n", instance->host->host_no);
2044 schedule_work(&instance->work_init); 2056 schedule_work(&instance->work_init);
2057 }
2045 } 2058 }
2046 2059
2047 return IRQ_HANDLED; 2060 return IRQ_HANDLED;
@@ -2212,9 +2225,10 @@ megasas_check_reset_fusion(struct megasas_instance *instance,
2212} 2225}
2213 2226
2214/* This function waits for outstanding commands on fusion to complete */ 2227/* This function waits for outstanding commands on fusion to complete */
2215int megasas_wait_for_outstanding_fusion(struct megasas_instance *instance) 2228int megasas_wait_for_outstanding_fusion(struct megasas_instance *instance,
2229 int iotimeout, int *convert)
2216{ 2230{
2217 int i, outstanding, retval = 0; 2231 int i, outstanding, retval = 0, hb_seconds_missed = 0;
2218 u32 fw_state; 2232 u32 fw_state;
2219 2233
2220 for (i = 0; i < resetwaittime; i++) { 2234 for (i = 0; i < resetwaittime; i++) {
@@ -2223,18 +2237,49 @@ int megasas_wait_for_outstanding_fusion(struct megasas_instance *instance)
2223 instance->reg_set) & MFI_STATE_MASK; 2237 instance->reg_set) & MFI_STATE_MASK;
2224 if (fw_state == MFI_STATE_FAULT) { 2238 if (fw_state == MFI_STATE_FAULT) {
2225 printk(KERN_WARNING "megasas: Found FW in FAULT state," 2239 printk(KERN_WARNING "megasas: Found FW in FAULT state,"
2226 " will reset adapter.\n"); 2240 " will reset adapter scsi%d.\n",
2241 instance->host->host_no);
2242 retval = 1;
2243 goto out;
2244 }
2245 /* If SR-IOV VF mode & heartbeat timeout, don't wait */
2246 if (instance->requestorId && !iotimeout) {
2227 retval = 1; 2247 retval = 1;
2228 goto out; 2248 goto out;
2229 } 2249 }
2230 2250
2251 /* If SR-IOV VF mode & I/O timeout, check for HB timeout */
2252 if (instance->requestorId && iotimeout) {
2253 if (instance->hb_host_mem->HB.fwCounter !=
2254 instance->hb_host_mem->HB.driverCounter) {
2255 instance->hb_host_mem->HB.driverCounter =
2256 instance->hb_host_mem->HB.fwCounter;
2257 hb_seconds_missed = 0;
2258 } else {
2259 hb_seconds_missed++;
2260 if (hb_seconds_missed ==
2261 (MEGASAS_SRIOV_HEARTBEAT_INTERVAL_VF/HZ)) {
2262 printk(KERN_WARNING "megasas: SR-IOV:"
2263 " Heartbeat never completed "
2264 " while polling during I/O "
2265 " timeout handling for "
2266 "scsi%d.\n",
2267 instance->host->host_no);
2268 *convert = 1;
2269 retval = 1;
2270 goto out;
2271 }
2272 }
2273 }
2274
2231 outstanding = atomic_read(&instance->fw_outstanding); 2275 outstanding = atomic_read(&instance->fw_outstanding);
2232 if (!outstanding) 2276 if (!outstanding)
2233 goto out; 2277 goto out;
2234 2278
2235 if (!(i % MEGASAS_RESET_NOTICE_INTERVAL)) { 2279 if (!(i % MEGASAS_RESET_NOTICE_INTERVAL)) {
2236 printk(KERN_NOTICE "megasas: [%2d]waiting for %d " 2280 printk(KERN_NOTICE "megasas: [%2d]waiting for %d "
2237 "commands to complete\n", i, outstanding); 2281 "commands to complete for scsi%d\n", i,
2282 outstanding, instance->host->host_no);
2238 megasas_complete_cmd_dpc_fusion( 2283 megasas_complete_cmd_dpc_fusion(
2239 (unsigned long)instance); 2284 (unsigned long)instance);
2240 } 2285 }
@@ -2243,7 +2288,8 @@ int megasas_wait_for_outstanding_fusion(struct megasas_instance *instance)
2243 2288
2244 if (atomic_read(&instance->fw_outstanding)) { 2289 if (atomic_read(&instance->fw_outstanding)) {
2245 printk("megaraid_sas: pending commands remain after waiting, " 2290 printk("megaraid_sas: pending commands remain after waiting, "
2246 "will reset adapter.\n"); 2291 "will reset adapter scsi%d.\n",
2292 instance->host->host_no);
2247 retval = 1; 2293 retval = 1;
2248 } 2294 }
2249out: 2295out:
@@ -2265,10 +2311,34 @@ void megasas_reset_reply_desc(struct megasas_instance *instance)
2265 reply_desc->Words = ULLONG_MAX; 2311 reply_desc->Words = ULLONG_MAX;
2266} 2312}
2267 2313
2314/* Check for a second path that is currently UP */
2315int megasas_check_mpio_paths(struct megasas_instance *instance,
2316 struct scsi_cmnd *scmd)
2317{
2318 int i, j, retval = (DID_RESET << 16);
2319
2320 if (instance->mpio && instance->requestorId) {
2321 for (i = 0 ; i < MAX_MGMT_ADAPTERS ; i++)
2322 for (j = 0 ; j < MAX_LOGICAL_DRIVES; j++)
2323 if (megasas_mgmt_info.instance[i] &&
2324 (megasas_mgmt_info.instance[i] != instance) &&
2325 megasas_mgmt_info.instance[i]->mpio &&
2326 megasas_mgmt_info.instance[i]->requestorId
2327 &&
2328 (megasas_mgmt_info.instance[i]->ld_ids[j]
2329 == scmd->device->id)) {
2330 retval = (DID_NO_CONNECT << 16);
2331 goto out;
2332 }
2333 }
2334out:
2335 return retval;
2336}
2337
2268/* Core fusion reset function */ 2338/* Core fusion reset function */
2269int megasas_reset_fusion(struct Scsi_Host *shost) 2339int megasas_reset_fusion(struct Scsi_Host *shost, int iotimeout)
2270{ 2340{
2271 int retval = SUCCESS, i, j, retry = 0; 2341 int retval = SUCCESS, i, j, retry = 0, convert = 0;
2272 struct megasas_instance *instance; 2342 struct megasas_instance *instance;
2273 struct megasas_cmd_fusion *cmd_fusion; 2343 struct megasas_cmd_fusion *cmd_fusion;
2274 struct fusion_context *fusion; 2344 struct fusion_context *fusion;
@@ -2279,28 +2349,39 @@ int megasas_reset_fusion(struct Scsi_Host *shost)
2279 instance = (struct megasas_instance *)shost->hostdata; 2349 instance = (struct megasas_instance *)shost->hostdata;
2280 fusion = instance->ctrl_context; 2350 fusion = instance->ctrl_context;
2281 2351
2352 mutex_lock(&instance->reset_mutex);
2353
2282 if (instance->adprecovery == MEGASAS_HW_CRITICAL_ERROR) { 2354 if (instance->adprecovery == MEGASAS_HW_CRITICAL_ERROR) {
2283 printk(KERN_WARNING "megaraid_sas: Hardware critical error, " 2355 printk(KERN_WARNING "megaraid_sas: Hardware critical error, "
2284 "returning FAILED.\n"); 2356 "returning FAILED for scsi%d.\n",
2357 instance->host->host_no);
2285 return FAILED; 2358 return FAILED;
2286 } 2359 }
2287 2360
2288 mutex_lock(&instance->reset_mutex); 2361 if (instance->requestorId && !instance->skip_heartbeat_timer_del)
2362 del_timer_sync(&instance->sriov_heartbeat_timer);
2289 set_bit(MEGASAS_FUSION_IN_RESET, &instance->reset_flags); 2363 set_bit(MEGASAS_FUSION_IN_RESET, &instance->reset_flags);
2290 instance->adprecovery = MEGASAS_ADPRESET_SM_INFAULT; 2364 instance->adprecovery = MEGASAS_ADPRESET_SM_POLLING;
2291 instance->instancet->disable_intr(instance); 2365 instance->instancet->disable_intr(instance);
2292 msleep(1000); 2366 msleep(1000);
2293 2367
2294 /* First try waiting for commands to complete */ 2368 /* First try waiting for commands to complete */
2295 if (megasas_wait_for_outstanding_fusion(instance)) { 2369 if (megasas_wait_for_outstanding_fusion(instance, iotimeout,
2370 &convert)) {
2371 instance->adprecovery = MEGASAS_ADPRESET_SM_INFAULT;
2296 printk(KERN_WARNING "megaraid_sas: resetting fusion " 2372 printk(KERN_WARNING "megaraid_sas: resetting fusion "
2297 "adapter.\n"); 2373 "adapter scsi%d.\n", instance->host->host_no);
2374 if (convert)
2375 iotimeout = 0;
2376
2298 /* Now return commands back to the OS */ 2377 /* Now return commands back to the OS */
2299 for (i = 0 ; i < instance->max_fw_cmds; i++) { 2378 for (i = 0 ; i < instance->max_fw_cmds; i++) {
2300 cmd_fusion = fusion->cmd_list[i]; 2379 cmd_fusion = fusion->cmd_list[i];
2301 if (cmd_fusion->scmd) { 2380 if (cmd_fusion->scmd) {
2302 scsi_dma_unmap(cmd_fusion->scmd); 2381 scsi_dma_unmap(cmd_fusion->scmd);
2303 cmd_fusion->scmd->result = (DID_RESET << 16); 2382 cmd_fusion->scmd->result =
2383 megasas_check_mpio_paths(instance,
2384 cmd_fusion->scmd);
2304 cmd_fusion->scmd->scsi_done(cmd_fusion->scmd); 2385 cmd_fusion->scmd->scsi_done(cmd_fusion->scmd);
2305 megasas_return_cmd_fusion(instance, cmd_fusion); 2386 megasas_return_cmd_fusion(instance, cmd_fusion);
2306 atomic_dec(&instance->fw_outstanding); 2387 atomic_dec(&instance->fw_outstanding);
@@ -2315,13 +2396,67 @@ int megasas_reset_fusion(struct Scsi_Host *shost)
2315 (abs_state == MFI_STATE_FAULT && !reset_adapter)) { 2396 (abs_state == MFI_STATE_FAULT && !reset_adapter)) {
2316 /* Reset not supported, kill adapter */ 2397 /* Reset not supported, kill adapter */
2317 printk(KERN_WARNING "megaraid_sas: Reset not supported" 2398 printk(KERN_WARNING "megaraid_sas: Reset not supported"
2318 ", killing adapter.\n"); 2399 ", killing adapter scsi%d.\n",
2400 instance->host->host_no);
2319 megaraid_sas_kill_hba(instance); 2401 megaraid_sas_kill_hba(instance);
2402 instance->skip_heartbeat_timer_del = 1;
2320 instance->adprecovery = MEGASAS_HW_CRITICAL_ERROR; 2403 instance->adprecovery = MEGASAS_HW_CRITICAL_ERROR;
2321 retval = FAILED; 2404 retval = FAILED;
2322 goto out; 2405 goto out;
2323 } 2406 }
2324 2407
2408 /* Let SR-IOV VF & PF sync up if there was a HB failure */
2409 if (instance->requestorId && !iotimeout) {
2410 msleep(MEGASAS_OCR_SETTLE_TIME_VF);
2411 /* Look for a late HB update after VF settle time */
2412 if (abs_state == MFI_STATE_OPERATIONAL &&
2413 (instance->hb_host_mem->HB.fwCounter !=
2414 instance->hb_host_mem->HB.driverCounter)) {
2415 instance->hb_host_mem->HB.driverCounter =
2416 instance->hb_host_mem->HB.fwCounter;
2417 printk(KERN_WARNING "megasas: SR-IOV:"
2418 "Late FW heartbeat update for "
2419 "scsi%d.\n",
2420 instance->host->host_no);
2421 } else {
2422 /* In VF mode, first poll for FW ready */
2423 for (i = 0;
2424 i < (MEGASAS_RESET_WAIT_TIME * 1000);
2425 i += 20) {
2426 status_reg =
2427 instance->instancet->
2428 read_fw_status_reg(
2429 instance->reg_set);
2430 abs_state = status_reg &
2431 MFI_STATE_MASK;
2432 if (abs_state == MFI_STATE_READY) {
2433 printk(KERN_WARNING "megasas"
2434 ": SR-IOV: FW was found"
2435 "to be in ready state "
2436 "for scsi%d.\n",
2437 instance->host->host_no);
2438 break;
2439 }
2440 msleep(20);
2441 }
2442 if (abs_state != MFI_STATE_READY) {
2443 printk(KERN_WARNING "megasas: SR-IOV: "
2444 "FW not in ready state after %d"
2445 " seconds for scsi%d, status_reg = "
2446 "0x%x.\n",
2447 MEGASAS_RESET_WAIT_TIME,
2448 instance->host->host_no,
2449 status_reg);
2450 megaraid_sas_kill_hba(instance);
2451 instance->skip_heartbeat_timer_del = 1;
2452 instance->adprecovery =
2453 MEGASAS_HW_CRITICAL_ERROR;
2454 retval = FAILED;
2455 goto out;
2456 }
2457 }
2458 }
2459
2325 /* Now try to reset the chip */ 2460 /* Now try to reset the chip */
2326 for (i = 0; i < MEGASAS_FUSION_MAX_RESET_TRIES; i++) { 2461 for (i = 0; i < MEGASAS_FUSION_MAX_RESET_TRIES; i++) {
2327 writel(MPI2_WRSEQ_FLUSH_KEY_VALUE, 2462 writel(MPI2_WRSEQ_FLUSH_KEY_VALUE,
@@ -2348,7 +2483,9 @@ int megasas_reset_fusion(struct Scsi_Host *shost)
2348 readl(&instance->reg_set->fusion_host_diag); 2483 readl(&instance->reg_set->fusion_host_diag);
2349 if (retry++ == 100) { 2484 if (retry++ == 100) {
2350 printk(KERN_WARNING "megaraid_sas: " 2485 printk(KERN_WARNING "megaraid_sas: "
2351 "Host diag unlock failed!\n"); 2486 "Host diag unlock failed! "
2487 "for scsi%d\n",
2488 instance->host->host_no);
2352 break; 2489 break;
2353 } 2490 }
2354 } 2491 }
@@ -2370,7 +2507,8 @@ int megasas_reset_fusion(struct Scsi_Host *shost)
2370 if (retry++ == 1000) { 2507 if (retry++ == 1000) {
2371 printk(KERN_WARNING "megaraid_sas: " 2508 printk(KERN_WARNING "megaraid_sas: "
2372 "Diag reset adapter never " 2509 "Diag reset adapter never "
2373 "cleared!\n"); 2510 "cleared for scsi%d!\n",
2511 instance->host->host_no);
2374 break; 2512 break;
2375 } 2513 }
2376 } 2514 }
@@ -2392,29 +2530,29 @@ int megasas_reset_fusion(struct Scsi_Host *shost)
2392 if (abs_state <= MFI_STATE_FW_INIT) { 2530 if (abs_state <= MFI_STATE_FW_INIT) {
2393 printk(KERN_WARNING "megaraid_sas: firmware " 2531 printk(KERN_WARNING "megaraid_sas: firmware "
2394 "state < MFI_STATE_FW_INIT, state = " 2532 "state < MFI_STATE_FW_INIT, state = "
2395 "0x%x\n", abs_state); 2533 "0x%x for scsi%d\n", abs_state,
2534 instance->host->host_no);
2396 continue; 2535 continue;
2397 } 2536 }
2398 2537
2399 /* Wait for FW to become ready */ 2538 /* Wait for FW to become ready */
2400 if (megasas_transition_to_ready(instance, 1)) { 2539 if (megasas_transition_to_ready(instance, 1)) {
2401 printk(KERN_WARNING "megaraid_sas: Failed to " 2540 printk(KERN_WARNING "megaraid_sas: Failed to "
2402 "transition controller to ready.\n"); 2541 "transition controller to ready "
2542 "for scsi%d.\n",
2543 instance->host->host_no);
2403 continue; 2544 continue;
2404 } 2545 }
2405 2546
2406 megasas_reset_reply_desc(instance); 2547 megasas_reset_reply_desc(instance);
2407 if (megasas_ioc_init_fusion(instance)) { 2548 if (megasas_ioc_init_fusion(instance)) {
2408 printk(KERN_WARNING "megaraid_sas: " 2549 printk(KERN_WARNING "megaraid_sas: "
2409 "megasas_ioc_init_fusion() failed!\n"); 2550 "megasas_ioc_init_fusion() failed!"
2551 " for scsi%d\n",
2552 instance->host->host_no);
2410 continue; 2553 continue;
2411 } 2554 }
2412 2555
2413 clear_bit(MEGASAS_FUSION_IN_RESET,
2414 &instance->reset_flags);
2415 instance->instancet->enable_intr(instance);
2416 instance->adprecovery = MEGASAS_HBA_OPERATIONAL;
2417
2418 /* Re-fire management commands */ 2556 /* Re-fire management commands */
2419 for (j = 0 ; j < instance->max_fw_cmds; j++) { 2557 for (j = 0 ; j < instance->max_fw_cmds; j++) {
2420 cmd_fusion = fusion->cmd_list[j]; 2558 cmd_fusion = fusion->cmd_list[j];
@@ -2438,7 +2576,8 @@ int megasas_reset_fusion(struct Scsi_Host *shost)
2438 if (!req_desc) { 2576 if (!req_desc) {
2439 printk(KERN_WARNING 2577 printk(KERN_WARNING
2440 "req_desc NULL" 2578 "req_desc NULL"
2441 "\n"); 2579 " for scsi%d\n",
2580 instance->host->host_no);
2442 /* Return leaked MPT 2581 /* Return leaked MPT
2443 frame */ 2582 frame */
2444 megasas_return_cmd_fusion(instance, cmd_fusion); 2583 megasas_return_cmd_fusion(instance, cmd_fusion);
@@ -2456,6 +2595,11 @@ int megasas_reset_fusion(struct Scsi_Host *shost)
2456 } 2595 }
2457 } 2596 }
2458 2597
2598 clear_bit(MEGASAS_FUSION_IN_RESET,
2599 &instance->reset_flags);
2600 instance->instancet->enable_intr(instance);
2601 instance->adprecovery = MEGASAS_HBA_OPERATIONAL;
2602
2459 /* Reset load balance info */ 2603 /* Reset load balance info */
2460 memset(fusion->load_balance_info, 0, 2604 memset(fusion->load_balance_info, 0,
2461 sizeof(struct LD_LOAD_BALANCE_INFO) 2605 sizeof(struct LD_LOAD_BALANCE_INFO)
@@ -2464,19 +2608,39 @@ int megasas_reset_fusion(struct Scsi_Host *shost)
2464 if (!megasas_get_map_info(instance)) 2608 if (!megasas_get_map_info(instance))
2465 megasas_sync_map_info(instance); 2609 megasas_sync_map_info(instance);
2466 2610
2611 /* Restart SR-IOV heartbeat */
2612 if (instance->requestorId) {
2613 if (!megasas_sriov_start_heartbeat(instance, 0))
2614 megasas_start_timer(instance,
2615 &instance->sriov_heartbeat_timer,
2616 megasas_sriov_heartbeat_handler,
2617 MEGASAS_SRIOV_HEARTBEAT_INTERVAL_VF);
2618 else
2619 instance->skip_heartbeat_timer_del = 1;
2620 }
2621
2467 /* Adapter reset completed successfully */ 2622 /* Adapter reset completed successfully */
2468 printk(KERN_WARNING "megaraid_sas: Reset " 2623 printk(KERN_WARNING "megaraid_sas: Reset "
2469 "successful.\n"); 2624 "successful for scsi%d.\n",
2625 instance->host->host_no);
2470 retval = SUCCESS; 2626 retval = SUCCESS;
2471 goto out; 2627 goto out;
2472 } 2628 }
2473 /* Reset failed, kill the adapter */ 2629 /* Reset failed, kill the adapter */
2474 printk(KERN_WARNING "megaraid_sas: Reset failed, killing " 2630 printk(KERN_WARNING "megaraid_sas: Reset failed, killing "
2475 "adapter.\n"); 2631 "adapter scsi%d.\n", instance->host->host_no);
2476 megaraid_sas_kill_hba(instance); 2632 megaraid_sas_kill_hba(instance);
2633 instance->skip_heartbeat_timer_del = 1;
2477 instance->adprecovery = MEGASAS_HW_CRITICAL_ERROR; 2634 instance->adprecovery = MEGASAS_HW_CRITICAL_ERROR;
2478 retval = FAILED; 2635 retval = FAILED;
2479 } else { 2636 } else {
2637 /* For VF: Restart HB timer if we didn't OCR */
2638 if (instance->requestorId) {
2639 megasas_start_timer(instance,
2640 &instance->sriov_heartbeat_timer,
2641 megasas_sriov_heartbeat_handler,
2642 MEGASAS_SRIOV_HEARTBEAT_INTERVAL_VF);
2643 }
2480 clear_bit(MEGASAS_FUSION_IN_RESET, &instance->reset_flags); 2644 clear_bit(MEGASAS_FUSION_IN_RESET, &instance->reset_flags);
2481 instance->instancet->enable_intr(instance); 2645 instance->instancet->enable_intr(instance);
2482 instance->adprecovery = MEGASAS_HBA_OPERATIONAL; 2646 instance->adprecovery = MEGASAS_HBA_OPERATIONAL;
@@ -2493,7 +2657,7 @@ void megasas_fusion_ocr_wq(struct work_struct *work)
2493 struct megasas_instance *instance = 2657 struct megasas_instance *instance =
2494 container_of(work, struct megasas_instance, work_init); 2658 container_of(work, struct megasas_instance, work_init);
2495 2659
2496 megasas_reset_fusion(instance->host); 2660 megasas_reset_fusion(instance->host, 0);
2497} 2661}
2498 2662
2499struct megasas_instance_template megasas_instance_template_fusion = { 2663struct megasas_instance_template megasas_instance_template_fusion = {
diff --git a/drivers/scsi/megaraid/megaraid_sas_fusion.h b/drivers/scsi/megaraid/megaraid_sas_fusion.h
index 35a51397b364..e76af5459a09 100644
--- a/drivers/scsi/megaraid/megaraid_sas_fusion.h
+++ b/drivers/scsi/megaraid/megaraid_sas_fusion.h
@@ -485,6 +485,9 @@ struct MPI2_IOC_INIT_REQUEST {
485#define MAX_PHYSICAL_DEVICES 256 485#define MAX_PHYSICAL_DEVICES 256
486#define MAX_RAIDMAP_PHYSICAL_DEVICES (MAX_PHYSICAL_DEVICES) 486#define MAX_RAIDMAP_PHYSICAL_DEVICES (MAX_PHYSICAL_DEVICES)
487#define MR_DCMD_LD_MAP_GET_INFO 0x0300e101 487#define MR_DCMD_LD_MAP_GET_INFO 0x0300e101
488#define MR_DCMD_CTRL_SHARED_HOST_MEM_ALLOC 0x010e8485 /* SR-IOV HB alloc*/
489#define MR_DCMD_LD_VF_MAP_GET_ALL_LDS_111 0x03200200
490#define MR_DCMD_LD_VF_MAP_GET_ALL_LDS 0x03150200
488 491
489struct MR_DEV_HANDLE_INFO { 492struct MR_DEV_HANDLE_INFO {
490 u16 curDevHdl; 493 u16 curDevHdl;