diff options
Diffstat (limited to 'drivers/net/ethernet/intel/e1000e')
-rw-r--r-- | drivers/net/ethernet/intel/e1000e/82571.c | 6 | ||||
-rw-r--r-- | drivers/net/ethernet/intel/e1000e/e1000.h | 1 | ||||
-rw-r--r-- | drivers/net/ethernet/intel/e1000e/ich8lan.c | 3 | ||||
-rw-r--r-- | drivers/net/ethernet/intel/e1000e/netdev.c | 66 |
4 files changed, 46 insertions, 30 deletions
diff --git a/drivers/net/ethernet/intel/e1000e/82571.c b/drivers/net/ethernet/intel/e1000e/82571.c index 7fd4d54599e4..6b03c8553e59 100644 --- a/drivers/net/ethernet/intel/e1000e/82571.c +++ b/drivers/net/ethernet/intel/e1000e/82571.c | |||
@@ -2032,7 +2032,8 @@ const struct e1000_info e1000_82574_info = { | |||
2032 | | FLAG2_DISABLE_ASPM_L0S | 2032 | | FLAG2_DISABLE_ASPM_L0S |
2033 | | FLAG2_DISABLE_ASPM_L1 | 2033 | | FLAG2_DISABLE_ASPM_L1 |
2034 | | FLAG2_NO_DISABLE_RX | 2034 | | FLAG2_NO_DISABLE_RX |
2035 | | FLAG2_DMA_BURST, | 2035 | | FLAG2_DMA_BURST |
2036 | | FLAG2_CHECK_SYSTIM_OVERFLOW, | ||
2036 | .pba = 32, | 2037 | .pba = 32, |
2037 | .max_hw_frame_size = DEFAULT_JUMBO, | 2038 | .max_hw_frame_size = DEFAULT_JUMBO, |
2038 | .get_variants = e1000_get_variants_82571, | 2039 | .get_variants = e1000_get_variants_82571, |
@@ -2053,7 +2054,8 @@ const struct e1000_info e1000_82583_info = { | |||
2053 | | FLAG_HAS_CTRLEXT_ON_LOAD, | 2054 | | FLAG_HAS_CTRLEXT_ON_LOAD, |
2054 | .flags2 = FLAG2_DISABLE_ASPM_L0S | 2055 | .flags2 = FLAG2_DISABLE_ASPM_L0S |
2055 | | FLAG2_DISABLE_ASPM_L1 | 2056 | | FLAG2_DISABLE_ASPM_L1 |
2056 | | FLAG2_NO_DISABLE_RX, | 2057 | | FLAG2_NO_DISABLE_RX |
2058 | | FLAG2_CHECK_SYSTIM_OVERFLOW, | ||
2057 | .pba = 32, | 2059 | .pba = 32, |
2058 | .max_hw_frame_size = DEFAULT_JUMBO, | 2060 | .max_hw_frame_size = DEFAULT_JUMBO, |
2059 | .get_variants = e1000_get_variants_82571, | 2061 | .get_variants = e1000_get_variants_82571, |
diff --git a/drivers/net/ethernet/intel/e1000e/e1000.h b/drivers/net/ethernet/intel/e1000e/e1000.h index ef96cd11d6d2..879cca47b021 100644 --- a/drivers/net/ethernet/intel/e1000e/e1000.h +++ b/drivers/net/ethernet/intel/e1000e/e1000.h | |||
@@ -452,6 +452,7 @@ s32 e1000e_get_base_timinca(struct e1000_adapter *adapter, u32 *timinca); | |||
452 | #define FLAG2_PCIM2PCI_ARBITER_WA BIT(11) | 452 | #define FLAG2_PCIM2PCI_ARBITER_WA BIT(11) |
453 | #define FLAG2_DFLT_CRC_STRIPPING BIT(12) | 453 | #define FLAG2_DFLT_CRC_STRIPPING BIT(12) |
454 | #define FLAG2_CHECK_RX_HWTSTAMP BIT(13) | 454 | #define FLAG2_CHECK_RX_HWTSTAMP BIT(13) |
455 | #define FLAG2_CHECK_SYSTIM_OVERFLOW BIT(14) | ||
455 | 456 | ||
456 | #define E1000_RX_DESC_PS(R, i) \ | 457 | #define E1000_RX_DESC_PS(R, i) \ |
457 | (&(((union e1000_rx_desc_packet_split *)((R).desc))[i])) | 458 | (&(((union e1000_rx_desc_packet_split *)((R).desc))[i])) |
diff --git a/drivers/net/ethernet/intel/e1000e/ich8lan.c b/drivers/net/ethernet/intel/e1000e/ich8lan.c index 3e11322d8d58..f3aaca743ea3 100644 --- a/drivers/net/ethernet/intel/e1000e/ich8lan.c +++ b/drivers/net/ethernet/intel/e1000e/ich8lan.c | |||
@@ -5885,7 +5885,8 @@ const struct e1000_info e1000_pch_lpt_info = { | |||
5885 | | FLAG_HAS_JUMBO_FRAMES | 5885 | | FLAG_HAS_JUMBO_FRAMES |
5886 | | FLAG_APME_IN_WUC, | 5886 | | FLAG_APME_IN_WUC, |
5887 | .flags2 = FLAG2_HAS_PHY_STATS | 5887 | .flags2 = FLAG2_HAS_PHY_STATS |
5888 | | FLAG2_HAS_EEE, | 5888 | | FLAG2_HAS_EEE |
5889 | | FLAG2_CHECK_SYSTIM_OVERFLOW, | ||
5889 | .pba = 26, | 5890 | .pba = 26, |
5890 | .max_hw_frame_size = 9022, | 5891 | .max_hw_frame_size = 9022, |
5891 | .get_variants = e1000_get_variants_ich8lan, | 5892 | .get_variants = e1000_get_variants_ich8lan, |
diff --git a/drivers/net/ethernet/intel/e1000e/netdev.c b/drivers/net/ethernet/intel/e1000e/netdev.c index 02f443958f31..7017281ba2dc 100644 --- a/drivers/net/ethernet/intel/e1000e/netdev.c +++ b/drivers/net/ethernet/intel/e1000e/netdev.c | |||
@@ -4303,6 +4303,42 @@ void e1000e_reinit_locked(struct e1000_adapter *adapter) | |||
4303 | } | 4303 | } |
4304 | 4304 | ||
4305 | /** | 4305 | /** |
4306 | * e1000e_sanitize_systim - sanitize raw cycle counter reads | ||
4307 | * @hw: pointer to the HW structure | ||
4308 | * @systim: cycle_t value read, sanitized and returned | ||
4309 | * | ||
4310 | * Errata for 82574/82583 possible bad bits read from SYSTIMH/L: | ||
4311 | * check to see that the time is incrementing at a reasonable | ||
4312 | * rate and is a multiple of incvalue. | ||
4313 | **/ | ||
4314 | static cycle_t e1000e_sanitize_systim(struct e1000_hw *hw, cycle_t systim) | ||
4315 | { | ||
4316 | u64 time_delta, rem, temp; | ||
4317 | cycle_t systim_next; | ||
4318 | u32 incvalue; | ||
4319 | int i; | ||
4320 | |||
4321 | incvalue = er32(TIMINCA) & E1000_TIMINCA_INCVALUE_MASK; | ||
4322 | for (i = 0; i < E1000_MAX_82574_SYSTIM_REREADS; i++) { | ||
4323 | /* latch SYSTIMH on read of SYSTIML */ | ||
4324 | systim_next = (cycle_t)er32(SYSTIML); | ||
4325 | systim_next |= (cycle_t)er32(SYSTIMH) << 32; | ||
4326 | |||
4327 | time_delta = systim_next - systim; | ||
4328 | temp = time_delta; | ||
4329 | /* VMWare users have seen incvalue of zero, don't div / 0 */ | ||
4330 | rem = incvalue ? do_div(temp, incvalue) : (time_delta != 0); | ||
4331 | |||
4332 | systim = systim_next; | ||
4333 | |||
4334 | if ((time_delta < E1000_82574_SYSTIM_EPSILON) && (rem == 0)) | ||
4335 | break; | ||
4336 | } | ||
4337 | |||
4338 | return systim; | ||
4339 | } | ||
4340 | |||
4341 | /** | ||
4306 | * e1000e_cyclecounter_read - read raw cycle counter (used by time counter) | 4342 | * e1000e_cyclecounter_read - read raw cycle counter (used by time counter) |
4307 | * @cc: cyclecounter structure | 4343 | * @cc: cyclecounter structure |
4308 | **/ | 4344 | **/ |
@@ -4312,7 +4348,7 @@ static cycle_t e1000e_cyclecounter_read(const struct cyclecounter *cc) | |||
4312 | cc); | 4348 | cc); |
4313 | struct e1000_hw *hw = &adapter->hw; | 4349 | struct e1000_hw *hw = &adapter->hw; |
4314 | u32 systimel, systimeh; | 4350 | u32 systimel, systimeh; |
4315 | cycle_t systim, systim_next; | 4351 | cycle_t systim; |
4316 | /* SYSTIMH latching upon SYSTIML read does not work well. | 4352 | /* SYSTIMH latching upon SYSTIML read does not work well. |
4317 | * This means that if SYSTIML overflows after we read it but before | 4353 | * This means that if SYSTIML overflows after we read it but before |
4318 | * we read SYSTIMH, the value of SYSTIMH has been incremented and we | 4354 | * we read SYSTIMH, the value of SYSTIMH has been incremented and we |
@@ -4335,33 +4371,9 @@ static cycle_t e1000e_cyclecounter_read(const struct cyclecounter *cc) | |||
4335 | systim = (cycle_t)systimel; | 4371 | systim = (cycle_t)systimel; |
4336 | systim |= (cycle_t)systimeh << 32; | 4372 | systim |= (cycle_t)systimeh << 32; |
4337 | 4373 | ||
4338 | if ((hw->mac.type == e1000_82574) || (hw->mac.type == e1000_82583)) { | 4374 | if (adapter->flags2 & FLAG2_CHECK_SYSTIM_OVERFLOW) |
4339 | u64 time_delta, rem, temp; | 4375 | systim = e1000e_sanitize_systim(hw, systim); |
4340 | u32 incvalue; | ||
4341 | int i; | ||
4342 | |||
4343 | /* errata for 82574/82583 possible bad bits read from SYSTIMH/L | ||
4344 | * check to see that the time is incrementing at a reasonable | ||
4345 | * rate and is a multiple of incvalue | ||
4346 | */ | ||
4347 | incvalue = er32(TIMINCA) & E1000_TIMINCA_INCVALUE_MASK; | ||
4348 | for (i = 0; i < E1000_MAX_82574_SYSTIM_REREADS; i++) { | ||
4349 | /* latch SYSTIMH on read of SYSTIML */ | ||
4350 | systim_next = (cycle_t)er32(SYSTIML); | ||
4351 | systim_next |= (cycle_t)er32(SYSTIMH) << 32; | ||
4352 | |||
4353 | time_delta = systim_next - systim; | ||
4354 | temp = time_delta; | ||
4355 | /* VMWare users have seen incvalue of zero, don't div / 0 */ | ||
4356 | rem = incvalue ? do_div(temp, incvalue) : (time_delta != 0); | ||
4357 | |||
4358 | systim = systim_next; | ||
4359 | 4376 | ||
4360 | if ((time_delta < E1000_82574_SYSTIM_EPSILON) && | ||
4361 | (rem == 0)) | ||
4362 | break; | ||
4363 | } | ||
4364 | } | ||
4365 | return systim; | 4377 | return systim; |
4366 | } | 4378 | } |
4367 | 4379 | ||