diff options
author | Greg Rose <gregory.v.rose@intel.com> | 2010-01-22 17:47:18 -0500 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2010-01-23 04:13:56 -0500 |
commit | c0456c231a8b2981128cc29e211b7bad1bd997df (patch) | |
tree | 9e69393a45b302f3b8702ebfa848a56cfe2fe646 /drivers/net/ixgbevf | |
parent | a9ee25a2b87c8077042ce23d3231f67f026719b0 (diff) |
ixgbevf: Fix panics in the VF driver
Fix panics in the VF driver that occur when you bring it down after
having already brought the PF down.
Signed-off-by: Greg Rose <gregory.v.rose@intel.com>
Signed-off-by: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/ixgbevf')
-rw-r--r-- | drivers/net/ixgbevf/ixgbevf_main.c | 24 |
1 files changed, 20 insertions, 4 deletions
diff --git a/drivers/net/ixgbevf/ixgbevf_main.c b/drivers/net/ixgbevf/ixgbevf_main.c index bd2fd4608ed7..0a27fa17e7ff 100644 --- a/drivers/net/ixgbevf/ixgbevf_main.c +++ b/drivers/net/ixgbevf/ixgbevf_main.c | |||
@@ -1693,8 +1693,10 @@ static void ixgbevf_clean_rx_ring(struct ixgbevf_adapter *adapter, | |||
1693 | unsigned long size; | 1693 | unsigned long size; |
1694 | unsigned int i; | 1694 | unsigned int i; |
1695 | 1695 | ||
1696 | /* Free all the Rx ring sk_buffs */ | 1696 | if (!rx_ring->rx_buffer_info) |
1697 | return; | ||
1697 | 1698 | ||
1699 | /* Free all the Rx ring sk_buffs */ | ||
1698 | for (i = 0; i < rx_ring->count; i++) { | 1700 | for (i = 0; i < rx_ring->count; i++) { |
1699 | struct ixgbevf_rx_buffer *rx_buffer_info; | 1701 | struct ixgbevf_rx_buffer *rx_buffer_info; |
1700 | 1702 | ||
@@ -1751,6 +1753,9 @@ static void ixgbevf_clean_tx_ring(struct ixgbevf_adapter *adapter, | |||
1751 | unsigned long size; | 1753 | unsigned long size; |
1752 | unsigned int i; | 1754 | unsigned int i; |
1753 | 1755 | ||
1756 | if (!tx_ring->tx_buffer_info) | ||
1757 | return; | ||
1758 | |||
1754 | /* Free all the Tx ring sk_buffs */ | 1759 | /* Free all the Tx ring sk_buffs */ |
1755 | 1760 | ||
1756 | for (i = 0; i < tx_ring->count; i++) { | 1761 | for (i = 0; i < tx_ring->count; i++) { |
@@ -1843,12 +1848,24 @@ void ixgbevf_down(struct ixgbevf_adapter *adapter) | |||
1843 | 1848 | ||
1844 | void ixgbevf_reinit_locked(struct ixgbevf_adapter *adapter) | 1849 | void ixgbevf_reinit_locked(struct ixgbevf_adapter *adapter) |
1845 | { | 1850 | { |
1851 | struct ixgbe_hw *hw = &adapter->hw; | ||
1852 | |||
1846 | WARN_ON(in_interrupt()); | 1853 | WARN_ON(in_interrupt()); |
1854 | |||
1847 | while (test_and_set_bit(__IXGBEVF_RESETTING, &adapter->state)) | 1855 | while (test_and_set_bit(__IXGBEVF_RESETTING, &adapter->state)) |
1848 | msleep(1); | 1856 | msleep(1); |
1849 | 1857 | ||
1850 | ixgbevf_down(adapter); | 1858 | /* |
1851 | ixgbevf_up(adapter); | 1859 | * Check if PF is up before re-init. If not then skip until |
1860 | * later when the PF is up and ready to service requests from | ||
1861 | * the VF via mailbox. If the VF is up and running then the | ||
1862 | * watchdog task will continue to schedule reset tasks until | ||
1863 | * the PF is up and running. | ||
1864 | */ | ||
1865 | if (!hw->mac.ops.reset_hw(hw)) { | ||
1866 | ixgbevf_down(adapter); | ||
1867 | ixgbevf_up(adapter); | ||
1868 | } | ||
1852 | 1869 | ||
1853 | clear_bit(__IXGBEVF_RESETTING, &adapter->state); | 1870 | clear_bit(__IXGBEVF_RESETTING, &adapter->state); |
1854 | } | 1871 | } |
@@ -2423,7 +2440,6 @@ void ixgbevf_free_tx_resources(struct ixgbevf_adapter *adapter, | |||
2423 | { | 2440 | { |
2424 | struct pci_dev *pdev = adapter->pdev; | 2441 | struct pci_dev *pdev = adapter->pdev; |
2425 | 2442 | ||
2426 | |||
2427 | ixgbevf_clean_tx_ring(adapter, tx_ring); | 2443 | ixgbevf_clean_tx_ring(adapter, tx_ring); |
2428 | 2444 | ||
2429 | vfree(tx_ring->tx_buffer_info); | 2445 | vfree(tx_ring->tx_buffer_info); |