aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJesse Brandeburg <jesse.brandeburg@intel.com>2014-05-10 00:49:12 -0400
committerJeff Kirsher <jeffrey.t.kirsher@intel.com>2014-06-08 05:01:55 -0400
commit980093ebf777f95459eabcf0ca7a29db7e9a10f7 (patch)
tree05ba527177f7d8dd0a15c04b3c12c6827486ddb1
parent63158f916f21b986743d0cb6f9e273d54a01ce7e (diff)
i40e/i40evf: fix TSO accounting
The TSO logic in the transmit path had some assumptions that have been broken now that the kernel can send as much as 32kB in a single skb->frag[.] entry, even on a system with 4kB pages. This fixes the assumptions and allows the kernel to operate as efficiently as possible with both SENDFILE and SEND. In addition, the hardware limit of data contained in a descriptor is changed to the next power of two below where it currently is in order to align to a power of two value, preventing a single byte of data in a descriptor. Change-ID: I6af1f0b87c1458e10644dbd47541591075a52651 Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com> Signed-off-by: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
-rw-r--r--drivers/net/ethernet/intel/i40e/i40e_txrx.c7
-rw-r--r--drivers/net/ethernet/intel/i40e/i40e_txrx.h4
-rw-r--r--drivers/net/ethernet/intel/i40evf/i40e_txrx.c7
-rw-r--r--drivers/net/ethernet/intel/i40evf/i40e_txrx.h4
4 files changed, 6 insertions, 16 deletions
diff --git a/drivers/net/ethernet/intel/i40e/i40e_txrx.c b/drivers/net/ethernet/intel/i40e/i40e_txrx.c
index 1fe28ca18296..d1a9a0512b93 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_txrx.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_txrx.c
@@ -2170,9 +2170,7 @@ static int i40e_maybe_stop_tx(struct i40e_ring *tx_ring, int size)
2170static int i40e_xmit_descriptor_count(struct sk_buff *skb, 2170static int i40e_xmit_descriptor_count(struct sk_buff *skb,
2171 struct i40e_ring *tx_ring) 2171 struct i40e_ring *tx_ring)
2172{ 2172{
2173#if PAGE_SIZE > I40E_MAX_DATA_PER_TXD
2174 unsigned int f; 2173 unsigned int f;
2175#endif
2176 int count = 0; 2174 int count = 0;
2177 2175
2178 /* need: 1 descriptor per page * PAGE_SIZE/I40E_MAX_DATA_PER_TXD, 2176 /* need: 1 descriptor per page * PAGE_SIZE/I40E_MAX_DATA_PER_TXD,
@@ -2181,12 +2179,9 @@ static int i40e_xmit_descriptor_count(struct sk_buff *skb,
2181 * + 1 desc for context descriptor, 2179 * + 1 desc for context descriptor,
2182 * otherwise try next time 2180 * otherwise try next time
2183 */ 2181 */
2184#if PAGE_SIZE > I40E_MAX_DATA_PER_TXD
2185 for (f = 0; f < skb_shinfo(skb)->nr_frags; f++) 2182 for (f = 0; f < skb_shinfo(skb)->nr_frags; f++)
2186 count += TXD_USE_COUNT(skb_shinfo(skb)->frags[f].size); 2183 count += TXD_USE_COUNT(skb_shinfo(skb)->frags[f].size);
2187#else 2184
2188 count += skb_shinfo(skb)->nr_frags;
2189#endif
2190 count += TXD_USE_COUNT(skb_headlen(skb)); 2185 count += TXD_USE_COUNT(skb_headlen(skb));
2191 if (i40e_maybe_stop_tx(tx_ring, count + 4 + 1)) { 2186 if (i40e_maybe_stop_tx(tx_ring, count + 4 + 1)) {
2192 tx_ring->tx_stats.tx_busy++; 2187 tx_ring->tx_stats.tx_busy++;
diff --git a/drivers/net/ethernet/intel/i40e/i40e_txrx.h b/drivers/net/ethernet/intel/i40e/i40e_txrx.h
index 30e5fe35fa3d..0277894fe1c4 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_txrx.h
+++ b/drivers/net/ethernet/intel/i40e/i40e_txrx.h
@@ -117,11 +117,11 @@ enum i40e_dyn_idx_t {
117#define i40e_rx_desc i40e_32byte_rx_desc 117#define i40e_rx_desc i40e_32byte_rx_desc
118 118
119#define I40E_MIN_TX_LEN 17 119#define I40E_MIN_TX_LEN 17
120#define I40E_MAX_DATA_PER_TXD 16383 /* aka 16kB - 1 */ 120#define I40E_MAX_DATA_PER_TXD 8192
121 121
122/* Tx Descriptors needed, worst case */ 122/* Tx Descriptors needed, worst case */
123#define TXD_USE_COUNT(S) DIV_ROUND_UP((S), I40E_MAX_DATA_PER_TXD) 123#define TXD_USE_COUNT(S) DIV_ROUND_UP((S), I40E_MAX_DATA_PER_TXD)
124#define DESC_NEEDED ((MAX_SKB_FRAGS * TXD_USE_COUNT(PAGE_SIZE)) + 4) 124#define DESC_NEEDED (MAX_SKB_FRAGS + 4)
125 125
126#define I40E_TX_FLAGS_CSUM (u32)(1) 126#define I40E_TX_FLAGS_CSUM (u32)(1)
127#define I40E_TX_FLAGS_HW_VLAN (u32)(1 << 1) 127#define I40E_TX_FLAGS_HW_VLAN (u32)(1 << 1)
diff --git a/drivers/net/ethernet/intel/i40evf/i40e_txrx.c b/drivers/net/ethernet/intel/i40evf/i40e_txrx.c
index 82d6844245b5..ae089df7df19 100644
--- a/drivers/net/ethernet/intel/i40evf/i40e_txrx.c
+++ b/drivers/net/ethernet/intel/i40evf/i40e_txrx.c
@@ -1511,9 +1511,7 @@ static int i40e_maybe_stop_tx(struct i40e_ring *tx_ring, int size)
1511static int i40e_xmit_descriptor_count(struct sk_buff *skb, 1511static int i40e_xmit_descriptor_count(struct sk_buff *skb,
1512 struct i40e_ring *tx_ring) 1512 struct i40e_ring *tx_ring)
1513{ 1513{
1514#if PAGE_SIZE > I40E_MAX_DATA_PER_TXD
1515 unsigned int f; 1514 unsigned int f;
1516#endif
1517 int count = 0; 1515 int count = 0;
1518 1516
1519 /* need: 1 descriptor per page * PAGE_SIZE/I40E_MAX_DATA_PER_TXD, 1517 /* need: 1 descriptor per page * PAGE_SIZE/I40E_MAX_DATA_PER_TXD,
@@ -1522,12 +1520,9 @@ static int i40e_xmit_descriptor_count(struct sk_buff *skb,
1522 * + 1 desc for context descriptor, 1520 * + 1 desc for context descriptor,
1523 * otherwise try next time 1521 * otherwise try next time
1524 */ 1522 */
1525#if PAGE_SIZE > I40E_MAX_DATA_PER_TXD
1526 for (f = 0; f < skb_shinfo(skb)->nr_frags; f++) 1523 for (f = 0; f < skb_shinfo(skb)->nr_frags; f++)
1527 count += TXD_USE_COUNT(skb_shinfo(skb)->frags[f].size); 1524 count += TXD_USE_COUNT(skb_shinfo(skb)->frags[f].size);
1528#else 1525
1529 count += skb_shinfo(skb)->nr_frags;
1530#endif
1531 count += TXD_USE_COUNT(skb_headlen(skb)); 1526 count += TXD_USE_COUNT(skb_headlen(skb));
1532 if (i40e_maybe_stop_tx(tx_ring, count + 4 + 1)) { 1527 if (i40e_maybe_stop_tx(tx_ring, count + 4 + 1)) {
1533 tx_ring->tx_stats.tx_busy++; 1528 tx_ring->tx_stats.tx_busy++;
diff --git a/drivers/net/ethernet/intel/i40evf/i40e_txrx.h b/drivers/net/ethernet/intel/i40evf/i40e_txrx.h
index e297a3aba0f2..30d248bc5d19 100644
--- a/drivers/net/ethernet/intel/i40evf/i40e_txrx.h
+++ b/drivers/net/ethernet/intel/i40evf/i40e_txrx.h
@@ -117,11 +117,11 @@ enum i40e_dyn_idx_t {
117#define i40e_rx_desc i40e_32byte_rx_desc 117#define i40e_rx_desc i40e_32byte_rx_desc
118 118
119#define I40E_MIN_TX_LEN 17 119#define I40E_MIN_TX_LEN 17
120#define I40E_MAX_DATA_PER_TXD 16383 /* aka 16kB - 1 */ 120#define I40E_MAX_DATA_PER_TXD 8192
121 121
122/* Tx Descriptors needed, worst case */ 122/* Tx Descriptors needed, worst case */
123#define TXD_USE_COUNT(S) DIV_ROUND_UP((S), I40E_MAX_DATA_PER_TXD) 123#define TXD_USE_COUNT(S) DIV_ROUND_UP((S), I40E_MAX_DATA_PER_TXD)
124#define DESC_NEEDED ((MAX_SKB_FRAGS * TXD_USE_COUNT(PAGE_SIZE)) + 4) 124#define DESC_NEEDED (MAX_SKB_FRAGS + 4)
125 125
126#define I40E_TX_FLAGS_CSUM (u32)(1) 126#define I40E_TX_FLAGS_CSUM (u32)(1)
127#define I40E_TX_FLAGS_HW_VLAN (u32)(1 << 1) 127#define I40E_TX_FLAGS_HW_VLAN (u32)(1 << 1)