diff options
author | Michael Chan <mchan@broadcom.com> | 2008-10-09 15:21:46 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2008-10-09 15:21:46 -0400 |
commit | 9f52b564b7162ede5a73a4f4b421ccf93c55b025 (patch) | |
tree | 1bc5a044492c5e8bf76115ebddb34fd85b6b52d7 /drivers/net/bnx2.c | |
parent | 74bf4ba3d367aacbc04fef167289767f162cd730 (diff) |
bnx2: Check netif_running() in all ethtool operations.
We need to check netif_running() state in most ethtool operations
and properly handle the !netif_running() state where the chip is
in an uninitailzed state or low power state that may not accept
any MMIO.
Signed-off-by: Michael Chan <mchan@broadcom.com>
Signed-off-by: Benjamin Li <benli@broadcom.com>
Signed-off-by: Matt Carlson <mcarlson@broadcom.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/bnx2.c')
-rw-r--r-- | drivers/net/bnx2.c | 40 |
1 files changed, 32 insertions, 8 deletions
diff --git a/drivers/net/bnx2.c b/drivers/net/bnx2.c index b35f440361d..21711c753a0 100644 --- a/drivers/net/bnx2.c +++ b/drivers/net/bnx2.c | |||
@@ -3248,6 +3248,9 @@ bnx2_set_rx_mode(struct net_device *dev) | |||
3248 | struct dev_addr_list *uc_ptr; | 3248 | struct dev_addr_list *uc_ptr; |
3249 | int i; | 3249 | int i; |
3250 | 3250 | ||
3251 | if (!netif_running(dev)) | ||
3252 | return; | ||
3253 | |||
3251 | spin_lock_bh(&bp->phy_lock); | 3254 | spin_lock_bh(&bp->phy_lock); |
3252 | 3255 | ||
3253 | rx_mode = bp->rx_mode & ~(BNX2_EMAC_RX_MODE_PROMISCUOUS | | 3256 | rx_mode = bp->rx_mode & ~(BNX2_EMAC_RX_MODE_PROMISCUOUS | |
@@ -5521,6 +5524,9 @@ bnx2_test_link(struct bnx2 *bp) | |||
5521 | { | 5524 | { |
5522 | u32 bmsr; | 5525 | u32 bmsr; |
5523 | 5526 | ||
5527 | if (!netif_running(bp->dev)) | ||
5528 | return -ENODEV; | ||
5529 | |||
5524 | if (bp->phy_flags & BNX2_PHY_FLAG_REMOTE_PHY_CAP) { | 5530 | if (bp->phy_flags & BNX2_PHY_FLAG_REMOTE_PHY_CAP) { |
5525 | if (bp->link_up) | 5531 | if (bp->link_up) |
5526 | return 0; | 5532 | return 0; |
@@ -6485,6 +6491,9 @@ bnx2_nway_reset(struct net_device *dev) | |||
6485 | struct bnx2 *bp = netdev_priv(dev); | 6491 | struct bnx2 *bp = netdev_priv(dev); |
6486 | u32 bmcr; | 6492 | u32 bmcr; |
6487 | 6493 | ||
6494 | if (!netif_running(dev)) | ||
6495 | return -EAGAIN; | ||
6496 | |||
6488 | if (!(bp->autoneg & AUTONEG_SPEED)) { | 6497 | if (!(bp->autoneg & AUTONEG_SPEED)) { |
6489 | return -EINVAL; | 6498 | return -EINVAL; |
6490 | } | 6499 | } |
@@ -6540,6 +6549,9 @@ bnx2_get_eeprom(struct net_device *dev, struct ethtool_eeprom *eeprom, | |||
6540 | struct bnx2 *bp = netdev_priv(dev); | 6549 | struct bnx2 *bp = netdev_priv(dev); |
6541 | int rc; | 6550 | int rc; |
6542 | 6551 | ||
6552 | if (!netif_running(dev)) | ||
6553 | return -EAGAIN; | ||
6554 | |||
6543 | /* parameters already validated in ethtool_get_eeprom */ | 6555 | /* parameters already validated in ethtool_get_eeprom */ |
6544 | 6556 | ||
6545 | rc = bnx2_nvram_read(bp, eeprom->offset, eebuf, eeprom->len); | 6557 | rc = bnx2_nvram_read(bp, eeprom->offset, eebuf, eeprom->len); |
@@ -6554,6 +6566,9 @@ bnx2_set_eeprom(struct net_device *dev, struct ethtool_eeprom *eeprom, | |||
6554 | struct bnx2 *bp = netdev_priv(dev); | 6566 | struct bnx2 *bp = netdev_priv(dev); |
6555 | int rc; | 6567 | int rc; |
6556 | 6568 | ||
6569 | if (!netif_running(dev)) | ||
6570 | return -EAGAIN; | ||
6571 | |||
6557 | /* parameters already validated in ethtool_set_eeprom */ | 6572 | /* parameters already validated in ethtool_set_eeprom */ |
6558 | 6573 | ||
6559 | rc = bnx2_nvram_write(bp, eeprom->offset, eebuf, eeprom->len); | 6574 | rc = bnx2_nvram_write(bp, eeprom->offset, eebuf, eeprom->len); |
@@ -6718,11 +6733,11 @@ bnx2_set_pauseparam(struct net_device *dev, struct ethtool_pauseparam *epause) | |||
6718 | bp->autoneg &= ~AUTONEG_FLOW_CTRL; | 6733 | bp->autoneg &= ~AUTONEG_FLOW_CTRL; |
6719 | } | 6734 | } |
6720 | 6735 | ||
6721 | spin_lock_bh(&bp->phy_lock); | 6736 | if (netif_running(dev)) { |
6722 | 6737 | spin_lock_bh(&bp->phy_lock); | |
6723 | bnx2_setup_phy(bp, bp->phy_port); | 6738 | bnx2_setup_phy(bp, bp->phy_port); |
6724 | 6739 | spin_unlock_bh(&bp->phy_lock); | |
6725 | spin_unlock_bh(&bp->phy_lock); | 6740 | } |
6726 | 6741 | ||
6727 | return 0; | 6742 | return 0; |
6728 | } | 6743 | } |
@@ -6913,6 +6928,8 @@ bnx2_self_test(struct net_device *dev, struct ethtool_test *etest, u64 *buf) | |||
6913 | { | 6928 | { |
6914 | struct bnx2 *bp = netdev_priv(dev); | 6929 | struct bnx2 *bp = netdev_priv(dev); |
6915 | 6930 | ||
6931 | bnx2_set_power_state(bp, PCI_D0); | ||
6932 | |||
6916 | memset(buf, 0, sizeof(u64) * BNX2_NUM_TESTS); | 6933 | memset(buf, 0, sizeof(u64) * BNX2_NUM_TESTS); |
6917 | if (etest->flags & ETH_TEST_FL_OFFLINE) { | 6934 | if (etest->flags & ETH_TEST_FL_OFFLINE) { |
6918 | int i; | 6935 | int i; |
@@ -6932,9 +6949,8 @@ bnx2_self_test(struct net_device *dev, struct ethtool_test *etest, u64 *buf) | |||
6932 | if ((buf[2] = bnx2_test_loopback(bp)) != 0) | 6949 | if ((buf[2] = bnx2_test_loopback(bp)) != 0) |
6933 | etest->flags |= ETH_TEST_FL_FAILED; | 6950 | etest->flags |= ETH_TEST_FL_FAILED; |
6934 | 6951 | ||
6935 | if (!netif_running(bp->dev)) { | 6952 | if (!netif_running(bp->dev)) |
6936 | bnx2_reset_chip(bp, BNX2_DRV_MSG_CODE_RESET); | 6953 | bnx2_shutdown_chip(bp); |
6937 | } | ||
6938 | else { | 6954 | else { |
6939 | bnx2_init_nic(bp, 1); | 6955 | bnx2_init_nic(bp, 1); |
6940 | bnx2_netif_start(bp); | 6956 | bnx2_netif_start(bp); |
@@ -6962,6 +6978,8 @@ bnx2_self_test(struct net_device *dev, struct ethtool_test *etest, u64 *buf) | |||
6962 | etest->flags |= ETH_TEST_FL_FAILED; | 6978 | etest->flags |= ETH_TEST_FL_FAILED; |
6963 | 6979 | ||
6964 | } | 6980 | } |
6981 | if (!netif_running(bp->dev)) | ||
6982 | bnx2_set_power_state(bp, PCI_D3hot); | ||
6965 | } | 6983 | } |
6966 | 6984 | ||
6967 | static void | 6985 | static void |
@@ -7027,6 +7045,8 @@ bnx2_phys_id(struct net_device *dev, u32 data) | |||
7027 | int i; | 7045 | int i; |
7028 | u32 save; | 7046 | u32 save; |
7029 | 7047 | ||
7048 | bnx2_set_power_state(bp, PCI_D0); | ||
7049 | |||
7030 | if (data == 0) | 7050 | if (data == 0) |
7031 | data = 2; | 7051 | data = 2; |
7032 | 7052 | ||
@@ -7051,6 +7071,10 @@ bnx2_phys_id(struct net_device *dev, u32 data) | |||
7051 | } | 7071 | } |
7052 | REG_WR(bp, BNX2_EMAC_LED, 0); | 7072 | REG_WR(bp, BNX2_EMAC_LED, 0); |
7053 | REG_WR(bp, BNX2_MISC_CFG, save); | 7073 | REG_WR(bp, BNX2_MISC_CFG, save); |
7074 | |||
7075 | if (!netif_running(dev)) | ||
7076 | bnx2_set_power_state(bp, PCI_D3hot); | ||
7077 | |||
7054 | return 0; | 7078 | return 0; |
7055 | } | 7079 | } |
7056 | 7080 | ||