tcp_bbr: fix bbr pacing rate for internal pacing
authorEric Dumazet <edumazet@google.com>
Wed, 20 Jun 2018 20:07:35 +0000 (16:07 -0400)
committerDavid S. Miller <davem@davemloft.net>
Fri, 22 Jun 2018 04:59:22 +0000 (13:59 +0900)
This commit makes BBR use only the MSS (without any headers) to
calculate pacing rates when internal TCP-layer pacing is used.

This is necessary to achieve the correct pacing behavior in this case,
since tcp_internal_pacing() uses only the payload length to calculate
pacing delays.

Signed-off-by: Kevin Yang <yyd@google.com>
Signed-off-by: Eric Dumazet <edumazet@google.com>
Reviewed-by: Neal Cardwell <ncardwell@google.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
include/net/tcp.h
net/ipv4/tcp_bbr.c
net/ipv4/tcp_output.c

index 0448e7c5d2b4062f8ceecb5b38882385a1be7ead..822ee49ed0f962f0531e2cab786899ca6f16536a 100644 (file)
@@ -1184,6 +1184,17 @@ static inline bool tcp_is_cwnd_limited(const struct sock *sk)
        return tp->is_cwnd_limited;
 }
 
+/* BBR congestion control needs pacing.
+ * Same remark for SO_MAX_PACING_RATE.
+ * sch_fq packet scheduler is efficiently handling pacing,
+ * but is not always installed/used.
+ * Return true if TCP stack should pace packets itself.
+ */
+static inline bool tcp_needs_internal_pacing(const struct sock *sk)
+{
+       return smp_load_acquire(&sk->sk_pacing_status) == SK_PACING_NEEDED;
+}
+
 /* Something is really bad, we could not queue an additional packet,
  * because qdisc is full or receiver sent a 0 window.
  * We do not want to add fuel to the fire, or abort too early,
index 58e2f479ffb4d523b4ccfbb859bdd186a55ab83d..3b5f45b9e81eb14ef39311a1e71fb01eb0622980 100644 (file)
@@ -205,7 +205,11 @@ static u32 bbr_bw(const struct sock *sk)
  */
 static u64 bbr_rate_bytes_per_sec(struct sock *sk, u64 rate, int gain)
 {
-       rate *= tcp_mss_to_mtu(sk, tcp_sk(sk)->mss_cache);
+       unsigned int mss = tcp_sk(sk)->mss_cache;
+
+       if (!tcp_needs_internal_pacing(sk))
+               mss = tcp_mss_to_mtu(sk, mss);
+       rate *= mss;
        rate *= gain;
        rate >>= BBR_SCALE;
        rate *= USEC_PER_SEC;
index 8e08b409c71e1f8e69422f1756d48b5bc55411c3..f8f6129160ddbdcd0419b5953906499270fe7ff0 100644 (file)
@@ -973,17 +973,6 @@ enum hrtimer_restart tcp_pace_kick(struct hrtimer *timer)
        return HRTIMER_NORESTART;
 }
 
-/* BBR congestion control needs pacing.
- * Same remark for SO_MAX_PACING_RATE.
- * sch_fq packet scheduler is efficiently handling pacing,
- * but is not always installed/used.
- * Return true if TCP stack should pace packets itself.
- */
-static bool tcp_needs_internal_pacing(const struct sock *sk)
-{
-       return smp_load_acquire(&sk->sk_pacing_status) == SK_PACING_NEEDED;
-}
-
 static void tcp_internal_pacing(struct sock *sk, const struct sk_buff *skb)
 {
        u64 len_ns;
@@ -995,9 +984,6 @@ static void tcp_internal_pacing(struct sock *sk, const struct sk_buff *skb)
        if (!rate || rate == ~0U)
                return;
 
-       /* Should account for header sizes as sch_fq does,
-        * but lets make things simple.
-        */
        len_ns = (u64)skb->len * NSEC_PER_SEC;
        do_div(len_ns, rate);
        hrtimer_start(&tcp_sk(sk)->pacing_timer,