]> www.infradead.org Git - users/dwmw2/linux.git/commitdiff
ice: Gracefully handle reset failure in ice_alloc_vfs()
authorBrett Creeley <brett.creeley@intel.com>
Tue, 16 Apr 2019 17:24:32 +0000 (10:24 -0700)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Fri, 26 Jul 2019 07:10:14 +0000 (09:10 +0200)
[ Upstream commit 72f9c2039859e6303550f202d6cc6b8d8af0178c ]

Currently if ice_reset_all_vfs() fails in ice_alloc_vfs() we fail to
free some resources, reset variables, and return an error value.
Fix this by adding another unroll case to free the pf->vf array, set
the pf->num_alloc_vfs to 0, and return an error code.

Without this, if ice_reset_all_vfs() fails in ice_alloc_vfs() we will
not be able to do SRIOV without hard rebooting the system because
rmmod'ing the driver does not work.

Signed-off-by: Brett Creeley <brett.creeley@intel.com>
Signed-off-by: Anirudh Venkataramanan <anirudh.venkataramanan@intel.com>
Tested-by: Andrew Bowers <andrewx.bowers@intel.com>
Signed-off-by: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
Signed-off-by: Sasha Levin <sashal@kernel.org>
drivers/net/ethernet/intel/ice/ice_virtchnl_pf.c

index a805cbdd69be16aa1d96b8008de4f4a3ec9836f8..81ea779783551506cdeee5fc7b1c86fcbd460278 100644 (file)
@@ -1134,7 +1134,7 @@ static int ice_alloc_vfs(struct ice_pf *pf, u16 num_alloc_vfs)
                           GFP_KERNEL);
        if (!vfs) {
                ret = -ENOMEM;
-               goto err_unroll_sriov;
+               goto err_pci_disable_sriov;
        }
        pf->vf = vfs;
 
@@ -1154,12 +1154,19 @@ static int ice_alloc_vfs(struct ice_pf *pf, u16 num_alloc_vfs)
        pf->num_alloc_vfs = num_alloc_vfs;
 
        /* VF resources get allocated during reset */
-       if (!ice_reset_all_vfs(pf, true))
+       if (!ice_reset_all_vfs(pf, true)) {
+               ret = -EIO;
                goto err_unroll_sriov;
+       }
 
        goto err_unroll_intr;
 
 err_unroll_sriov:
+       pf->vf = NULL;
+       devm_kfree(&pf->pdev->dev, vfs);
+       vfs = NULL;
+       pf->num_alloc_vfs = 0;
+err_pci_disable_sriov:
        pci_disable_sriov(pf->pdev);
 err_unroll_intr:
        /* rearm interrupts here */