aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorMitch A Williams <mitch.a.williams@intel.com>2014-12-09 08:53:01 +0000
committerJeff Kirsher <jeffrey.t.kirsher@intel.com>2015-01-13 11:28:47 -0800
commit6a9ddb36eeb897807341fc92d35b71b2d5d6d67d (patch)
tree11fe74384d3fe29b4f9f512cb3a34b57f2c5b086 /drivers
parentMerge branch 'rhashtable-next' (diff)
downloadlinux-dev-6a9ddb36eeb897807341fc92d35b71b2d5d6d67d.tar.xz
linux-dev-6a9ddb36eeb897807341fc92d35b71b2d5d6d67d.zip
i40e: disable IOV before freeing resources
If VF drivers are loaded in the host OS, the call to pci_disable_sriov() will cause these drivers' remove routines to be called. If the PF driver has already freed VF resources before this happens, then the VF remove routine can't properly communicate with the PF driver causing all sorts of mayhem and error messages and hurt feelings. To fix this, we move the call to pci_disable_sriov() up to the top of the function and let it complete before freeing any VF resources. Change-ID: I397c3997a00f6408e32b7735273911e499600236 Signed-off-by: Mitch Williams <mitch.a.williams@intel.com> Acked-by: Shannon Nelson <shannon.nelson@intel.com> Tested-by: Jim Young <james.m.young@intel.com> Signed-off-by: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c11
1 files changed, 9 insertions, 2 deletions
diff --git a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
index 5bae89550657..044019b9d406 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
@@ -791,10 +791,18 @@ void i40e_free_vfs(struct i40e_pf *pf)
if (!pf->vf)
return;
+ /* Disable IOV before freeing resources. This lets any VF drivers
+ * running in the host get themselves cleaned up before we yank
+ * the carpet out from underneath their feet.
+ */
+ if (!pci_vfs_assigned(pf->pdev))
+ pci_disable_sriov(pf->pdev);
+
+ msleep(20); /* let any messages in transit get finished up */
+
/* Disable interrupt 0 so we don't try to handle the VFLR. */
i40e_irq_dynamic_disable_icr0(pf);
- mdelay(10); /* let any messages in transit get finished up */
/* free up vf resources */
tmp = pf->num_alloc_vfs;
pf->num_alloc_vfs = 0;
@@ -813,7 +821,6 @@ void i40e_free_vfs(struct i40e_pf *pf)
* before this function ever gets called.
*/
if (!pci_vfs_assigned(pf->pdev)) {
- pci_disable_sriov(pf->pdev);
/* Acknowledge VFLR for all VFS. Without this, VFs will fail to
* work correctly when SR-IOV gets re-enabled.
*/