diff options
author | Bruce Allan <bruce.w.allan@intel.com> | 2013-03-06 04:02:36 -0500 |
---|---|---|
committer | Jeff Kirsher <jeffrey.t.kirsher@intel.com> | 2013-03-28 02:25:36 -0400 |
commit | 772d05c51c4f4896c120ad418b1e91144a2ac813 (patch) | |
tree | 0c67bd6877d7c121030d34d1de86832c807d2d53 /drivers/net/ethernet/intel/e1000e | |
parent | bb034512da74dce901f738f7c7cea332ff971608 (diff) |
e1000e: slow performance between two 82579 connected via 10Mbit hub
Two 82579 LOMs connected via a 10Mb hub experience extraordinarily low
performance. This is because 82579 is excessively aggressive on transmit
at 10Mb half-duplex and will not provide sufficient time for the link
partner to transmit. When the link partner is also 82579, the result is a
lot of collisions (and corresponding re-transmits) that cause the poor
performance. To work-around this issue, significantly increase the IPG in
the MAC to allow enough gap for the link partner to transmit and reduce the
Rx latency in the analog PHY to 0 to reduce the number of collisions.
Signed-off-by: Bruce Allan <bruce.w.allan@intel.com>
Tested-by: Jeff Pieper <jeffrey.e.pieper@intel.com>
Signed-off-by: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
Diffstat (limited to 'drivers/net/ethernet/intel/e1000e')
-rw-r--r-- | drivers/net/ethernet/intel/e1000e/defines.h | 1 | ||||
-rw-r--r-- | drivers/net/ethernet/intel/e1000e/ich8lan.c | 28 | ||||
-rw-r--r-- | drivers/net/ethernet/intel/e1000e/ich8lan.h | 1 |
3 files changed, 30 insertions, 0 deletions
diff --git a/drivers/net/ethernet/intel/e1000e/defines.h b/drivers/net/ethernet/intel/e1000e/defines.h index a6aeb195390f..351c94a0cf74 100644 --- a/drivers/net/ethernet/intel/e1000e/defines.h +++ b/drivers/net/ethernet/intel/e1000e/defines.h | |||
@@ -236,6 +236,7 @@ | |||
236 | #define E1000_STATUS_FUNC_SHIFT 2 | 236 | #define E1000_STATUS_FUNC_SHIFT 2 |
237 | #define E1000_STATUS_FUNC_1 0x00000004 /* Function 1 */ | 237 | #define E1000_STATUS_FUNC_1 0x00000004 /* Function 1 */ |
238 | #define E1000_STATUS_TXOFF 0x00000010 /* transmission paused */ | 238 | #define E1000_STATUS_TXOFF 0x00000010 /* transmission paused */ |
239 | #define E1000_STATUS_SPEED_MASK 0x000000C0 | ||
239 | #define E1000_STATUS_SPEED_10 0x00000000 /* Speed 10Mb/s */ | 240 | #define E1000_STATUS_SPEED_10 0x00000000 /* Speed 10Mb/s */ |
240 | #define E1000_STATUS_SPEED_100 0x00000040 /* Speed 100Mb/s */ | 241 | #define E1000_STATUS_SPEED_100 0x00000040 /* Speed 100Mb/s */ |
241 | #define E1000_STATUS_SPEED_1000 0x00000080 /* Speed 1000Mb/s */ | 242 | #define E1000_STATUS_SPEED_1000 0x00000080 /* Speed 1000Mb/s */ |
diff --git a/drivers/net/ethernet/intel/e1000e/ich8lan.c b/drivers/net/ethernet/intel/e1000e/ich8lan.c index 1cdec5fd2129..4f2f0f69a48e 100644 --- a/drivers/net/ethernet/intel/e1000e/ich8lan.c +++ b/drivers/net/ethernet/intel/e1000e/ich8lan.c | |||
@@ -871,6 +871,34 @@ static s32 e1000_check_for_copper_link_ich8lan(struct e1000_hw *hw) | |||
871 | return ret_val; | 871 | return ret_val; |
872 | } | 872 | } |
873 | 873 | ||
874 | /* When connected at 10Mbps half-duplex, 82579 parts are excessively | ||
875 | * aggressive resulting in many collisions. To avoid this, increase | ||
876 | * the IPG and reduce Rx latency in the PHY. | ||
877 | */ | ||
878 | if ((hw->mac.type == e1000_pch2lan) && link) { | ||
879 | u32 reg; | ||
880 | reg = er32(STATUS); | ||
881 | if (!(reg & (E1000_STATUS_FD | E1000_STATUS_SPEED_MASK))) { | ||
882 | reg = er32(TIPG); | ||
883 | reg &= ~E1000_TIPG_IPGT_MASK; | ||
884 | reg |= 0xFF; | ||
885 | ew32(TIPG, reg); | ||
886 | |||
887 | /* Reduce Rx latency in analog PHY */ | ||
888 | ret_val = hw->phy.ops.acquire(hw); | ||
889 | if (ret_val) | ||
890 | return ret_val; | ||
891 | |||
892 | ret_val = | ||
893 | e1000_write_emi_reg_locked(hw, I82579_RX_CONFIG, 0); | ||
894 | |||
895 | hw->phy.ops.release(hw); | ||
896 | |||
897 | if (ret_val) | ||
898 | return ret_val; | ||
899 | } | ||
900 | } | ||
901 | |||
874 | /* Work-around I218 hang issue */ | 902 | /* Work-around I218 hang issue */ |
875 | if ((hw->adapter->pdev->device == E1000_DEV_ID_PCH_LPTLP_I218_LM) || | 903 | if ((hw->adapter->pdev->device == E1000_DEV_ID_PCH_LPTLP_I218_LM) || |
876 | (hw->adapter->pdev->device == E1000_DEV_ID_PCH_LPTLP_I218_V)) { | 904 | (hw->adapter->pdev->device == E1000_DEV_ID_PCH_LPTLP_I218_V)) { |
diff --git a/drivers/net/ethernet/intel/e1000e/ich8lan.h b/drivers/net/ethernet/intel/e1000e/ich8lan.h index 8bf4655c2e17..00ba6c912cc8 100644 --- a/drivers/net/ethernet/intel/e1000e/ich8lan.h +++ b/drivers/net/ethernet/intel/e1000e/ich8lan.h | |||
@@ -211,6 +211,7 @@ | |||
211 | #define I82579_MSE_THRESHOLD 0x084F /* 82579 Mean Square Error Threshold */ | 211 | #define I82579_MSE_THRESHOLD 0x084F /* 82579 Mean Square Error Threshold */ |
212 | #define I82577_MSE_THRESHOLD 0x0887 /* 82577 Mean Square Error Threshold */ | 212 | #define I82577_MSE_THRESHOLD 0x0887 /* 82577 Mean Square Error Threshold */ |
213 | #define I82579_MSE_LINK_DOWN 0x2411 /* MSE count before dropping link */ | 213 | #define I82579_MSE_LINK_DOWN 0x2411 /* MSE count before dropping link */ |
214 | #define I82579_RX_CONFIG 0x3412 /* Receive configuration */ | ||
214 | #define I82579_EEE_PCS_STATUS 0x182D /* IEEE MMD Register 3.1 >> 8 */ | 215 | #define I82579_EEE_PCS_STATUS 0x182D /* IEEE MMD Register 3.1 >> 8 */ |
215 | #define I82579_EEE_CAPABILITY 0x0410 /* IEEE MMD Register 3.20 */ | 216 | #define I82579_EEE_CAPABILITY 0x0410 /* IEEE MMD Register 3.20 */ |
216 | #define I82579_EEE_ADVERTISEMENT 0x040E /* IEEE MMD Register 7.60 */ | 217 | #define I82579_EEE_ADVERTISEMENT 0x040E /* IEEE MMD Register 7.60 */ |