1// Copyright 2014 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "net/quic/quic_sustained_bandwidth_recorder.h"
6
7#include "net/quic/quic_bandwidth.h"
8#include "net/quic/quic_time.h"
9#include "testing/gtest/include/gtest/gtest.h"
10
11namespace net {
12namespace test {
13namespace {
14
15TEST(QuicSustainedBandwidthRecorderTest, BandwidthEstimates) {
16  QuicSustainedBandwidthRecorder recorder;
17  EXPECT_FALSE(recorder.HasEstimate());
18
19  QuicTime estimate_time = QuicTime::Zero();
20  QuicWallTime wall_time = QuicWallTime::Zero();
21  QuicTime::Delta srtt = QuicTime::Delta::FromMilliseconds(150);
22  const int kBandwidthBitsPerSecond = 12345678;
23  QuicBandwidth bandwidth =
24      QuicBandwidth::FromBitsPerSecond(kBandwidthBitsPerSecond);
25
26  bool in_recovery = false;
27  bool in_slow_start = false;
28
29  // This triggers recording, but should not yield a valid estimate yet.
30  recorder.RecordEstimate(in_recovery, in_slow_start, bandwidth, estimate_time,
31                          wall_time, srtt);
32  EXPECT_FALSE(recorder.HasEstimate());
33
34  // Send a second reading, again this should not result in a valid estimate,
35  // as not enough time has passed.
36  estimate_time = estimate_time.Add(srtt);
37  recorder.RecordEstimate(in_recovery, in_slow_start, bandwidth, estimate_time,
38                          wall_time, srtt);
39  EXPECT_FALSE(recorder.HasEstimate());
40
41  // Now 3 * kSRTT has elapsed since first recording, expect a valid estimate.
42  estimate_time = estimate_time.Add(srtt);
43  estimate_time = estimate_time.Add(srtt);
44  recorder.RecordEstimate(in_recovery, in_slow_start, bandwidth, estimate_time,
45                          wall_time, srtt);
46  EXPECT_TRUE(recorder.HasEstimate());
47  EXPECT_EQ(recorder.BandwidthEstimate(), bandwidth);
48  EXPECT_EQ(recorder.BandwidthEstimate(), recorder.MaxBandwidthEstimate());
49
50  // Resetting, and sending a different estimate will only change output after
51  // a further 3 * kSRTT has passed.
52  QuicBandwidth second_bandwidth =
53      QuicBandwidth::FromBitsPerSecond(2 * kBandwidthBitsPerSecond);
54  // Reset the recorder by passing in a measurement while in recovery.
55  in_recovery = true;
56  recorder.RecordEstimate(in_recovery, in_slow_start, bandwidth, estimate_time,
57                          wall_time, srtt);
58  in_recovery = false;
59  recorder.RecordEstimate(in_recovery, in_slow_start, bandwidth, estimate_time,
60                          wall_time, srtt);
61  EXPECT_EQ(recorder.BandwidthEstimate(), bandwidth);
62
63  estimate_time = estimate_time.Add(srtt.Multiply(3));
64  const int64 kSeconds = 556677;
65  QuicWallTime second_bandwidth_wall_time =
66      QuicWallTime::FromUNIXSeconds(kSeconds);
67  recorder.RecordEstimate(in_recovery, in_slow_start, second_bandwidth,
68                          estimate_time, second_bandwidth_wall_time, srtt);
69  EXPECT_EQ(recorder.BandwidthEstimate(), second_bandwidth);
70  EXPECT_EQ(recorder.BandwidthEstimate(), recorder.MaxBandwidthEstimate());
71  EXPECT_EQ(recorder.MaxBandwidthTimestamp(), kSeconds);
72
73  // Reset again, this time recording a lower bandwidth than before.
74  QuicBandwidth third_bandwidth =
75      QuicBandwidth::FromBitsPerSecond(0.5 * kBandwidthBitsPerSecond);
76  // Reset the recorder by passing in an unreliable measurement.
77  recorder.RecordEstimate(in_recovery, in_slow_start, third_bandwidth,
78                          estimate_time, wall_time, srtt);
79  recorder.RecordEstimate(in_recovery, in_slow_start, third_bandwidth,
80                          estimate_time, wall_time, srtt);
81  EXPECT_EQ(recorder.BandwidthEstimate(), third_bandwidth);
82
83  estimate_time = estimate_time.Add(srtt.Multiply(3));
84  recorder.RecordEstimate(in_recovery, in_slow_start, third_bandwidth,
85                          estimate_time, wall_time, srtt);
86  EXPECT_EQ(recorder.BandwidthEstimate(), third_bandwidth);
87
88  // Max bandwidth should not have changed.
89  EXPECT_LT(third_bandwidth, second_bandwidth);
90  EXPECT_EQ(recorder.MaxBandwidthEstimate(), second_bandwidth);
91  EXPECT_EQ(recorder.MaxBandwidthTimestamp(), kSeconds);
92}
93
94TEST(QuicSustainedBandwidthRecorderTest, SlowStart) {
95  // Verify that slow start status is correctly recorded.
96  QuicSustainedBandwidthRecorder recorder;
97  EXPECT_FALSE(recorder.HasEstimate());
98
99  QuicTime estimate_time = QuicTime::Zero();
100  QuicWallTime wall_time = QuicWallTime::Zero();
101  QuicTime::Delta srtt = QuicTime::Delta::FromMilliseconds(150);
102  const int kBandwidthBitsPerSecond = 12345678;
103  QuicBandwidth bandwidth =
104      QuicBandwidth::FromBitsPerSecond(kBandwidthBitsPerSecond);
105
106  bool in_recovery = false;
107  bool in_slow_start = true;
108
109  // This triggers recording, but should not yield a valid estimate yet.
110  recorder.RecordEstimate(in_recovery, in_slow_start, bandwidth, estimate_time,
111                          wall_time, srtt);
112
113  // Now 3 * kSRTT has elapsed since first recording, expect a valid estimate.
114  estimate_time = estimate_time.Add(srtt.Multiply(3));
115  recorder.RecordEstimate(in_recovery, in_slow_start, bandwidth, estimate_time,
116                          wall_time, srtt);
117  EXPECT_TRUE(recorder.HasEstimate());
118  EXPECT_TRUE(recorder.EstimateRecordedDuringSlowStart());
119
120  // Now send another estimate, this time not in slow start.
121  estimate_time = estimate_time.Add(srtt.Multiply(3));
122  in_slow_start = false;
123  recorder.RecordEstimate(in_recovery, in_slow_start, bandwidth, estimate_time,
124                          wall_time, srtt);
125  EXPECT_TRUE(recorder.HasEstimate());
126  EXPECT_FALSE(recorder.EstimateRecordedDuringSlowStart());
127}
128
129}  // namespace
130}  // namespace test
131}  // namespace net
132