aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/linux/skbuff.h3
-rw-r--r--net/core/dev.c18
-rw-r--r--net/ipv4/tcp_output.c5
3 files changed, 17 insertions, 9 deletions
diff --git a/include/linux/skbuff.h b/include/linux/skbuff.h
index e6ba898de61c..19f37a6ee6c4 100644
--- a/include/linux/skbuff.h
+++ b/include/linux/skbuff.h
@@ -386,9 +386,10 @@ struct sk_buff {
386#else 386#else
387 __u8 deliver_no_wcard:1; 387 __u8 deliver_no_wcard:1;
388#endif 388#endif
389 __u8 ooo_okay:1;
389 kmemcheck_bitfield_end(flags2); 390 kmemcheck_bitfield_end(flags2);
390 391
391 /* 0/14 bit hole */ 392 /* 0/13 bit hole */
392 393
393#ifdef CONFIG_NET_DMA 394#ifdef CONFIG_NET_DMA
394 dma_cookie_t dma_cookie; 395 dma_cookie_t dma_cookie;
diff --git a/net/core/dev.c b/net/core/dev.c
index 381b8e280162..7b17674a29ec 100644
--- a/net/core/dev.c
+++ b/net/core/dev.c
@@ -2148,20 +2148,24 @@ static struct netdev_queue *dev_pick_tx(struct net_device *dev,
2148 int queue_index; 2148 int queue_index;
2149 const struct net_device_ops *ops = dev->netdev_ops; 2149 const struct net_device_ops *ops = dev->netdev_ops;
2150 2150
2151 if (ops->ndo_select_queue) { 2151 if (dev->real_num_tx_queues == 1)
2152 queue_index = 0;
2153 else if (ops->ndo_select_queue) {
2152 queue_index = ops->ndo_select_queue(dev, skb); 2154 queue_index = ops->ndo_select_queue(dev, skb);
2153 queue_index = dev_cap_txqueue(dev, queue_index); 2155 queue_index = dev_cap_txqueue(dev, queue_index);
2154 } else { 2156 } else {
2155 struct sock *sk = skb->sk; 2157 struct sock *sk = skb->sk;
2156 queue_index = sk_tx_queue_get(sk); 2158 queue_index = sk_tx_queue_get(sk);
2157 if (queue_index < 0 || queue_index >= dev->real_num_tx_queues) {
2158 2159
2159 queue_index = 0; 2160 if (queue_index < 0 || skb->ooo_okay ||
2160 if (dev->real_num_tx_queues > 1) 2161 queue_index >= dev->real_num_tx_queues) {
2161 queue_index = skb_tx_hash(dev, skb); 2162 int old_index = queue_index;
2162 2163
2163 if (sk) { 2164 queue_index = skb_tx_hash(dev, skb);
2164 struct dst_entry *dst = rcu_dereference_check(sk->sk_dst_cache, 1); 2165
2166 if (queue_index != old_index && sk) {
2167 struct dst_entry *dst =
2168 rcu_dereference_check(sk->sk_dst_cache, 1);
2165 2169
2166 if (dst && skb_dst(skb) == dst) 2170 if (dst && skb_dst(skb) == dst)
2167 sk_tx_queue_set(sk, queue_index); 2171 sk_tx_queue_set(sk, queue_index);
diff --git a/net/ipv4/tcp_output.c b/net/ipv4/tcp_output.c
index bb8f547fc7d2..5f29b2e20e23 100644
--- a/net/ipv4/tcp_output.c
+++ b/net/ipv4/tcp_output.c
@@ -822,8 +822,11 @@ static int tcp_transmit_skb(struct sock *sk, struct sk_buff *skb, int clone_it,
822 &md5); 822 &md5);
823 tcp_header_size = tcp_options_size + sizeof(struct tcphdr); 823 tcp_header_size = tcp_options_size + sizeof(struct tcphdr);
824 824
825 if (tcp_packets_in_flight(tp) == 0) 825 if (tcp_packets_in_flight(tp) == 0) {
826 tcp_ca_event(sk, CA_EVENT_TX_START); 826 tcp_ca_event(sk, CA_EVENT_TX_START);
827 skb->ooo_okay = 1;
828 } else
829 skb->ooo_okay = 0;
827 830
828 skb_push(skb, tcp_header_size); 831 skb_push(skb, tcp_header_size);
829 skb_reset_transport_header(skb); 832 skb_reset_transport_header(skb);