diff options
Diffstat (limited to 'net/ipv4/tcp_output.c')
| -rw-r--r-- | net/ipv4/tcp_output.c | 17 | 
1 files changed, 11 insertions, 6 deletions
diff --git a/net/ipv4/tcp_output.c b/net/ipv4/tcp_output.c index 7c83cb8bf13..e6bb8256e59 100644 --- a/net/ipv4/tcp_output.c +++ b/net/ipv4/tcp_output.c @@ -895,8 +895,7 @@ static int tcp_transmit_skb(struct sock *sk, struct sk_buff *skb, int clone_it,  	skb_orphan(skb);  	skb->sk = sk; -	skb->destructor = (sysctl_tcp_limit_output_bytes > 0) ? -			  tcp_wfree : sock_wfree; +	skb->destructor = tcp_wfree;  	atomic_add(skb->truesize, &sk->sk_wmem_alloc);  	/* Build TCP header and checksum it. */ @@ -1840,7 +1839,6 @@ static bool tcp_write_xmit(struct sock *sk, unsigned int mss_now, int nonagle,  	while ((skb = tcp_send_head(sk))) {  		unsigned int limit; -  		tso_segs = tcp_init_tso_segs(sk, skb, mss_now);  		BUG_ON(!tso_segs); @@ -1869,13 +1867,20 @@ static bool tcp_write_xmit(struct sock *sk, unsigned int mss_now, int nonagle,  				break;  		} -		/* TSQ : sk_wmem_alloc accounts skb truesize, -		 * including skb overhead. But thats OK. +		/* TCP Small Queues : +		 * Control number of packets in qdisc/devices to two packets / or ~1 ms. +		 * This allows for : +		 *  - better RTT estimation and ACK scheduling +		 *  - faster recovery +		 *  - high rates  		 */ -		if (atomic_read(&sk->sk_wmem_alloc) >= sysctl_tcp_limit_output_bytes) { +		limit = max(skb->truesize, sk->sk_pacing_rate >> 10); + +		if (atomic_read(&sk->sk_wmem_alloc) > limit) {  			set_bit(TSQ_THROTTLED, &tp->tsq_flags);  			break;  		} +  		limit = mss_now;  		if (tso_segs > 1 && !tcp_urg_mode(tp))  			limit = tcp_mss_split_point(sk, skb, mss_now,  | 
