diff options
Diffstat (limited to 'drivers/net/bnx2x_main.c')
-rw-r--r-- | drivers/net/bnx2x_main.c | 42 |
1 files changed, 27 insertions, 15 deletions
diff --git a/drivers/net/bnx2x_main.c b/drivers/net/bnx2x_main.c index 57ff5b3bcce6..46167c081727 100644 --- a/drivers/net/bnx2x_main.c +++ b/drivers/net/bnx2x_main.c | |||
@@ -57,8 +57,8 @@ | |||
57 | #include "bnx2x_init_ops.h" | 57 | #include "bnx2x_init_ops.h" |
58 | #include "bnx2x_dump.h" | 58 | #include "bnx2x_dump.h" |
59 | 59 | ||
60 | #define DRV_MODULE_VERSION "1.52.53-1" | 60 | #define DRV_MODULE_VERSION "1.52.53-2" |
61 | #define DRV_MODULE_RELDATE "2010/18/04" | 61 | #define DRV_MODULE_RELDATE "2010/21/07" |
62 | #define BNX2X_BC_VER 0x040200 | 62 | #define BNX2X_BC_VER 0x040200 |
63 | 63 | ||
64 | #include <linux/firmware.h> | 64 | #include <linux/firmware.h> |
@@ -3789,6 +3789,8 @@ static void bnx2x_storm_stats_post(struct bnx2x *bp) | |||
3789 | struct eth_query_ramrod_data ramrod_data = {0}; | 3789 | struct eth_query_ramrod_data ramrod_data = {0}; |
3790 | int i, rc; | 3790 | int i, rc; |
3791 | 3791 | ||
3792 | spin_lock_bh(&bp->stats_lock); | ||
3793 | |||
3792 | ramrod_data.drv_counter = bp->stats_counter++; | 3794 | ramrod_data.drv_counter = bp->stats_counter++; |
3793 | ramrod_data.collect_port = bp->port.pmf ? 1 : 0; | 3795 | ramrod_data.collect_port = bp->port.pmf ? 1 : 0; |
3794 | for_each_queue(bp, i) | 3796 | for_each_queue(bp, i) |
@@ -3802,6 +3804,8 @@ static void bnx2x_storm_stats_post(struct bnx2x *bp) | |||
3802 | bp->spq_left++; | 3804 | bp->spq_left++; |
3803 | bp->stats_pending = 1; | 3805 | bp->stats_pending = 1; |
3804 | } | 3806 | } |
3807 | |||
3808 | spin_unlock_bh(&bp->stats_lock); | ||
3805 | } | 3809 | } |
3806 | } | 3810 | } |
3807 | 3811 | ||
@@ -4367,6 +4371,14 @@ static int bnx2x_storm_stats_update(struct bnx2x *bp) | |||
4367 | struct host_func_stats *fstats = bnx2x_sp(bp, func_stats); | 4371 | struct host_func_stats *fstats = bnx2x_sp(bp, func_stats); |
4368 | struct bnx2x_eth_stats *estats = &bp->eth_stats; | 4372 | struct bnx2x_eth_stats *estats = &bp->eth_stats; |
4369 | int i; | 4373 | int i; |
4374 | u16 cur_stats_counter; | ||
4375 | |||
4376 | /* Make sure we use the value of the counter | ||
4377 | * used for sending the last stats ramrod. | ||
4378 | */ | ||
4379 | spin_lock_bh(&bp->stats_lock); | ||
4380 | cur_stats_counter = bp->stats_counter - 1; | ||
4381 | spin_unlock_bh(&bp->stats_lock); | ||
4370 | 4382 | ||
4371 | memcpy(&(fstats->total_bytes_received_hi), | 4383 | memcpy(&(fstats->total_bytes_received_hi), |
4372 | &(bnx2x_sp(bp, func_stats_base)->total_bytes_received_hi), | 4384 | &(bnx2x_sp(bp, func_stats_base)->total_bytes_received_hi), |
@@ -4394,25 +4406,22 @@ static int bnx2x_storm_stats_update(struct bnx2x *bp) | |||
4394 | u32 diff; | 4406 | u32 diff; |
4395 | 4407 | ||
4396 | /* are storm stats valid? */ | 4408 | /* are storm stats valid? */ |
4397 | if ((u16)(le16_to_cpu(xclient->stats_counter) + 1) != | 4409 | if (le16_to_cpu(xclient->stats_counter) != cur_stats_counter) { |
4398 | bp->stats_counter) { | ||
4399 | DP(BNX2X_MSG_STATS, "[%d] stats not updated by xstorm" | 4410 | DP(BNX2X_MSG_STATS, "[%d] stats not updated by xstorm" |
4400 | " xstorm counter (0x%x) != stats_counter (0x%x)\n", | 4411 | " xstorm counter (0x%x) != stats_counter (0x%x)\n", |
4401 | i, xclient->stats_counter, bp->stats_counter); | 4412 | i, xclient->stats_counter, cur_stats_counter + 1); |
4402 | return -1; | 4413 | return -1; |
4403 | } | 4414 | } |
4404 | if ((u16)(le16_to_cpu(tclient->stats_counter) + 1) != | 4415 | if (le16_to_cpu(tclient->stats_counter) != cur_stats_counter) { |
4405 | bp->stats_counter) { | ||
4406 | DP(BNX2X_MSG_STATS, "[%d] stats not updated by tstorm" | 4416 | DP(BNX2X_MSG_STATS, "[%d] stats not updated by tstorm" |
4407 | " tstorm counter (0x%x) != stats_counter (0x%x)\n", | 4417 | " tstorm counter (0x%x) != stats_counter (0x%x)\n", |
4408 | i, tclient->stats_counter, bp->stats_counter); | 4418 | i, tclient->stats_counter, cur_stats_counter + 1); |
4409 | return -2; | 4419 | return -2; |
4410 | } | 4420 | } |
4411 | if ((u16)(le16_to_cpu(uclient->stats_counter) + 1) != | 4421 | if (le16_to_cpu(uclient->stats_counter) != cur_stats_counter) { |
4412 | bp->stats_counter) { | ||
4413 | DP(BNX2X_MSG_STATS, "[%d] stats not updated by ustorm" | 4422 | DP(BNX2X_MSG_STATS, "[%d] stats not updated by ustorm" |
4414 | " ustorm counter (0x%x) != stats_counter (0x%x)\n", | 4423 | " ustorm counter (0x%x) != stats_counter (0x%x)\n", |
4415 | i, uclient->stats_counter, bp->stats_counter); | 4424 | i, uclient->stats_counter, cur_stats_counter + 1); |
4416 | return -4; | 4425 | return -4; |
4417 | } | 4426 | } |
4418 | 4427 | ||
@@ -4849,16 +4858,18 @@ static const struct { | |||
4849 | 4858 | ||
4850 | static void bnx2x_stats_handle(struct bnx2x *bp, enum bnx2x_stats_event event) | 4859 | static void bnx2x_stats_handle(struct bnx2x *bp, enum bnx2x_stats_event event) |
4851 | { | 4860 | { |
4852 | enum bnx2x_stats_state state = bp->stats_state; | 4861 | enum bnx2x_stats_state state; |
4853 | 4862 | ||
4854 | if (unlikely(bp->panic)) | 4863 | if (unlikely(bp->panic)) |
4855 | return; | 4864 | return; |
4856 | 4865 | ||
4857 | bnx2x_stats_stm[state][event].action(bp); | 4866 | /* Protect a state change flow */ |
4867 | spin_lock_bh(&bp->stats_lock); | ||
4868 | state = bp->stats_state; | ||
4858 | bp->stats_state = bnx2x_stats_stm[state][event].next_state; | 4869 | bp->stats_state = bnx2x_stats_stm[state][event].next_state; |
4870 | spin_unlock_bh(&bp->stats_lock); | ||
4859 | 4871 | ||
4860 | /* Make sure the state has been "changed" */ | 4872 | bnx2x_stats_stm[state][event].action(bp); |
4861 | smp_wmb(); | ||
4862 | 4873 | ||
4863 | if ((event != STATS_EVENT_UPDATE) || netif_msg_timer(bp)) | 4874 | if ((event != STATS_EVENT_UPDATE) || netif_msg_timer(bp)) |
4864 | DP(BNX2X_MSG_STATS, "state %d -> event %d -> state %d\n", | 4875 | DP(BNX2X_MSG_STATS, "state %d -> event %d -> state %d\n", |
@@ -9908,6 +9919,7 @@ static int __devinit bnx2x_init_bp(struct bnx2x *bp) | |||
9908 | 9919 | ||
9909 | mutex_init(&bp->port.phy_mutex); | 9920 | mutex_init(&bp->port.phy_mutex); |
9910 | mutex_init(&bp->fw_mb_mutex); | 9921 | mutex_init(&bp->fw_mb_mutex); |
9922 | spin_lock_init(&bp->stats_lock); | ||
9911 | #ifdef BCM_CNIC | 9923 | #ifdef BCM_CNIC |
9912 | mutex_init(&bp->cnic_mutex); | 9924 | mutex_init(&bp->cnic_mutex); |
9913 | #endif | 9925 | #endif |