/* MSI-X */
        bool                    msix_enabled;
        u8                      num_vec;
-       struct msix_entry       msix_entries[NIC_PF_MSIX_VECTORS];
+       struct msix_entry       *msix_entries;
        bool                    irq_allocated[NIC_PF_MSIX_VECTORS];
+       char                    irq_name[NIC_PF_MSIX_VECTORS][20];
 };
 
 /* Supported devices */
 /* PF -> VF mailbox communication APIs */
 static void nic_enable_mbx_intr(struct nicpf *nic)
 {
-       /* Enable mailbox interrupt for all 128 VFs */
-       nic_reg_write(nic, NIC_PF_MAILBOX_ENA_W1S, ~0ull);
-       nic_reg_write(nic, NIC_PF_MAILBOX_ENA_W1S + sizeof(u64), ~0ull);
+       int vf_cnt = pci_sriov_get_totalvfs(nic->pdev);
+
+#define INTR_MASK(vfs) ((vfs < 64) ? (BIT_ULL(vfs) - 1) : (~0ull))
+
+       /* Clear it, to avoid spurious interrupts (if any) */
+       nic_reg_write(nic, NIC_PF_MAILBOX_INT, INTR_MASK(vf_cnt));
+
+       /* Enable mailbox interrupt for all VFs */
+       nic_reg_write(nic, NIC_PF_MAILBOX_ENA_W1S, INTR_MASK(vf_cnt));
+       /* One mailbox intr enable reg per 64 VFs */
+       if (vf_cnt > 64) {
+               nic_reg_write(nic, NIC_PF_MAILBOX_INT + sizeof(u64),
+                             INTR_MASK(vf_cnt - 64));
+               nic_reg_write(nic, NIC_PF_MAILBOX_ENA_W1S + sizeof(u64),
+                             INTR_MASK(vf_cnt - 64));
+       }
 }
 
 static void nic_clear_mbx_intr(struct nicpf *nic, int vf, int mbx_reg)
        nic->mbx_lock[vf] = false;
 }
 
-static void nic_mbx_intr_handler (struct nicpf *nic, int mbx)
+static irqreturn_t nic_mbx_intr_handler(int irq, void *nic_irq)
 {
+       struct nicpf *nic = (struct nicpf *)nic_irq;
+       int mbx;
        u64 intr;
        u8  vf, vf_per_mbx_reg = 64;
 
+       if (irq == nic->msix_entries[NIC_PF_INTR_ID_MBOX0].vector)
+               mbx = 0;
+       else
+               mbx = 1;
+
        intr = nic_reg_read(nic, NIC_PF_MAILBOX_INT + (mbx << 3));
        dev_dbg(&nic->pdev->dev, "PF interrupt Mbox%d 0x%llx\n", mbx, intr);
        for (vf = 0; vf < vf_per_mbx_reg; vf++) {
                        nic_clear_mbx_intr(nic, vf, mbx);
                }
        }
-}
-
-static irqreturn_t nic_mbx0_intr_handler (int irq, void *nic_irq)
-{
-       struct nicpf *nic = (struct nicpf *)nic_irq;
-
-       nic_mbx_intr_handler(nic, 0);
-
-       return IRQ_HANDLED;
-}
-
-static irqreturn_t nic_mbx1_intr_handler (int irq, void *nic_irq)
-{
-       struct nicpf *nic = (struct nicpf *)nic_irq;
-
-       nic_mbx_intr_handler(nic, 1);
-
        return IRQ_HANDLED;
 }
 
 {
        int i, ret;
 
-       nic->num_vec = NIC_PF_MSIX_VECTORS;
+       nic->num_vec = pci_msix_vec_count(nic->pdev);
+
+       nic->msix_entries = kmalloc_array(nic->num_vec,
+                                         sizeof(struct msix_entry),
+                                         GFP_KERNEL);
+       if (!nic->msix_entries)
+               return -ENOMEM;
 
        for (i = 0; i < nic->num_vec; i++)
                nic->msix_entries[i].entry = i;
        ret = pci_enable_msix(nic->pdev, nic->msix_entries, nic->num_vec);
        if (ret) {
                dev_err(&nic->pdev->dev,
-                       "Request for #%d msix vectors failed\n",
-                          nic->num_vec);
+                       "Request for #%d msix vectors failed, returned %d\n",
+                          nic->num_vec, ret);
+               kfree(nic->msix_entries);
                return ret;
        }
 
 {
        if (nic->msix_enabled) {
                pci_disable_msix(nic->pdev);
+               kfree(nic->msix_entries);
                nic->msix_enabled = 0;
                nic->num_vec = 0;
        }
 
 static int nic_register_interrupts(struct nicpf *nic)
 {
-       int ret;
+       int i, ret;
 
        /* Enable MSI-X */
        ret = nic_enable_msix(nic);
        if (ret)
                return ret;
 
-       /* Register mailbox interrupt handlers */
-       ret = request_irq(nic->msix_entries[NIC_PF_INTR_ID_MBOX0].vector,
-                         nic_mbx0_intr_handler, 0, "NIC Mbox0", nic);
-       if (ret)
-               goto fail;
+       /* Register mailbox interrupt handler */
+       for (i = NIC_PF_INTR_ID_MBOX0; i < nic->num_vec; i++) {
+               sprintf(nic->irq_name[i],
+                       "NICPF Mbox%d", (i - NIC_PF_INTR_ID_MBOX0));
 
-       nic->irq_allocated[NIC_PF_INTR_ID_MBOX0] = true;
+               ret = request_irq(nic->msix_entries[i].vector,
+                                 nic_mbx_intr_handler, 0,
+                                 nic->irq_name[i], nic);
+               if (ret)
+                       goto fail;
 
-       ret = request_irq(nic->msix_entries[NIC_PF_INTR_ID_MBOX1].vector,
-                         nic_mbx1_intr_handler, 0, "NIC Mbox1", nic);
-       if (ret)
-               goto fail;
-
-       nic->irq_allocated[NIC_PF_INTR_ID_MBOX1] = true;
+               nic->irq_allocated[i] = true;
+       }
 
        /* Enable mailbox interrupt */
        nic_enable_mbx_intr(nic);
 fail:
        dev_err(&nic->pdev->dev, "Request irq failed\n");
        nic_free_all_interrupts(nic);
+       nic_disable_msix(nic);
        return ret;
 }