diff options
author | Jesse Brandeburg <jesse.brandeburg@intel.com> | 2009-07-06 06:44:20 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2009-07-06 21:07:47 -0400 |
commit | 94c9e5a89349a1f1ebabe0876c059dc387b8b2a0 (patch) | |
tree | 77ca6e744fdcdbe129e2b8ec06132c1f36f5aa27 /drivers/net/e1000 | |
parent | f77139c07a0e1dd164e039320ada50111f899223 (diff) |
e1000: allow ethtool coalesece to adjust interrupts per second
This patch allows on-the-fly adjustment of the interrupts per second generated
by e1000 devices 82545/82546 (hardware support of ITR register is a
requirement)
adjust using this command:
ethtool -C eth0 rx-usecs 10
where 10 is 10 microseconds per interrupt interval, so 10 = 100,000 interrupts
per second, and 125 = 8000 interrupts per second.
changes should be immediate.
1,3 are special values and indicate the automatic tuning mode to the driver,
where 1 is 4000-90000 interrupts per second and 3 is 4000-20000 interrupts
per second and is the driver default.
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@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/e1000')
-rw-r--r-- | drivers/net/e1000/e1000.h | 3 | ||||
-rw-r--r-- | drivers/net/e1000/e1000_ethtool.c | 51 |
2 files changed, 53 insertions, 1 deletions
diff --git a/drivers/net/e1000/e1000.h b/drivers/net/e1000/e1000.h index e9a416f40162..c87f2cbdbae3 100644 --- a/drivers/net/e1000/e1000.h +++ b/drivers/net/e1000/e1000.h | |||
@@ -111,6 +111,9 @@ do { \ | |||
111 | #define E1000_MIN_RXD 80 | 111 | #define E1000_MIN_RXD 80 |
112 | #define E1000_MAX_82544_RXD 4096 | 112 | #define E1000_MAX_82544_RXD 4096 |
113 | 113 | ||
114 | #define E1000_MIN_ITR_USECS 10 /* 100000 irq/sec */ | ||
115 | #define E1000_MAX_ITR_USECS 10000 /* 100 irq/sec */ | ||
116 | |||
114 | /* this is the size past which hardware will drop packets when setting LPE=0 */ | 117 | /* this is the size past which hardware will drop packets when setting LPE=0 */ |
115 | #define MAXIMUM_ETHERNET_VLAN_SIZE 1522 | 118 | #define MAXIMUM_ETHERNET_VLAN_SIZE 1522 |
116 | 119 | ||
diff --git a/drivers/net/e1000/e1000_ethtool.c b/drivers/net/e1000/e1000_ethtool.c index c854c96f5ab3..27f996a2010f 100644 --- a/drivers/net/e1000/e1000_ethtool.c +++ b/drivers/net/e1000/e1000_ethtool.c | |||
@@ -1904,6 +1904,53 @@ static int e1000_phys_id(struct net_device *netdev, u32 data) | |||
1904 | return 0; | 1904 | return 0; |
1905 | } | 1905 | } |
1906 | 1906 | ||
1907 | static int e1000_get_coalesce(struct net_device *netdev, | ||
1908 | struct ethtool_coalesce *ec) | ||
1909 | { | ||
1910 | struct e1000_adapter *adapter = netdev_priv(netdev); | ||
1911 | |||
1912 | if (adapter->hw.mac_type < e1000_82545) | ||
1913 | return -EOPNOTSUPP; | ||
1914 | |||
1915 | if (adapter->itr_setting <= 3) | ||
1916 | ec->rx_coalesce_usecs = adapter->itr_setting; | ||
1917 | else | ||
1918 | ec->rx_coalesce_usecs = 1000000 / adapter->itr_setting; | ||
1919 | |||
1920 | return 0; | ||
1921 | } | ||
1922 | |||
1923 | static int e1000_set_coalesce(struct net_device *netdev, | ||
1924 | struct ethtool_coalesce *ec) | ||
1925 | { | ||
1926 | struct e1000_adapter *adapter = netdev_priv(netdev); | ||
1927 | struct e1000_hw *hw = &adapter->hw; | ||
1928 | |||
1929 | if (hw->mac_type < e1000_82545) | ||
1930 | return -EOPNOTSUPP; | ||
1931 | |||
1932 | if ((ec->rx_coalesce_usecs > E1000_MAX_ITR_USECS) || | ||
1933 | ((ec->rx_coalesce_usecs > 3) && | ||
1934 | (ec->rx_coalesce_usecs < E1000_MIN_ITR_USECS)) || | ||
1935 | (ec->rx_coalesce_usecs == 2)) | ||
1936 | return -EINVAL; | ||
1937 | |||
1938 | if (ec->rx_coalesce_usecs <= 3) { | ||
1939 | adapter->itr = 20000; | ||
1940 | adapter->itr_setting = ec->rx_coalesce_usecs; | ||
1941 | } else { | ||
1942 | adapter->itr = (1000000 / ec->rx_coalesce_usecs); | ||
1943 | adapter->itr_setting = adapter->itr & ~3; | ||
1944 | } | ||
1945 | |||
1946 | if (adapter->itr_setting != 0) | ||
1947 | ew32(ITR, 1000000000 / (adapter->itr * 256)); | ||
1948 | else | ||
1949 | ew32(ITR, 0); | ||
1950 | |||
1951 | return 0; | ||
1952 | } | ||
1953 | |||
1907 | static int e1000_nway_reset(struct net_device *netdev) | 1954 | static int e1000_nway_reset(struct net_device *netdev) |
1908 | { | 1955 | { |
1909 | struct e1000_adapter *adapter = netdev_priv(netdev); | 1956 | struct e1000_adapter *adapter = netdev_priv(netdev); |
@@ -1978,7 +2025,9 @@ static const struct ethtool_ops e1000_ethtool_ops = { | |||
1978 | .get_strings = e1000_get_strings, | 2025 | .get_strings = e1000_get_strings, |
1979 | .phys_id = e1000_phys_id, | 2026 | .phys_id = e1000_phys_id, |
1980 | .get_ethtool_stats = e1000_get_ethtool_stats, | 2027 | .get_ethtool_stats = e1000_get_ethtool_stats, |
1981 | .get_sset_count = e1000_get_sset_count, | 2028 | .get_sset_count = e1000_get_sset_count, |
2029 | .get_coalesce = e1000_get_coalesce, | ||
2030 | .set_coalesce = e1000_set_coalesce, | ||
1982 | }; | 2031 | }; |
1983 | 2032 | ||
1984 | void e1000_set_ethtool_ops(struct net_device *netdev) | 2033 | void e1000_set_ethtool_ops(struct net_device *netdev) |