1 // Copyright (c) 2014 The Chromium OS 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 <gtest/gtest.h>
6
7 extern "C" {
8 #include "rate_estimator.h"
9 }
10
11 static struct timespec window = {
12 .tv_sec = 0,
13 .tv_nsec = 10000000
14 };
15
TEST(RateEstimatorTest,EstimateOutputLinear)16 TEST(RateEstimatorTest, EstimateOutputLinear) {
17 struct rate_estimator *re;
18 struct timespec t = {
19 .tv_sec = 1,
20 .tv_nsec = 0
21 };
22 int i, rc, level, tmp;
23
24 re = rate_estimator_create(10000, &window, 0.0f);
25 level = 240;
26 for (i = 0; i < 20; i++) {
27 rc = rate_estimator_check(re, level, &t);
28 EXPECT_EQ(0, rc);
29
30 /* Test that output device consumes 5 frames. */
31 tmp = rand() % 10;
32 rate_estimator_add_frames(re, 5 + tmp);
33 level += tmp;
34 t.tv_nsec += 500000;
35 }
36 t.tv_nsec += 1;
37 rc = rate_estimator_check(re, level, &t);
38 EXPECT_EQ(1, rc);
39 EXPECT_GT(10000, rate_estimator_get_rate(re));
40 EXPECT_LT(9999, rate_estimator_get_rate(re));
41
42 rate_estimator_destroy(re);
43 }
44
TEST(RateEstimatorTest,EstimateOutputLinear2)45 TEST(RateEstimatorTest, EstimateOutputLinear2) {
46 struct rate_estimator *re;
47 struct timespec t = {
48 .tv_sec = 1,
49 .tv_nsec = 0
50 };
51 int level = 240;
52 int i, rc, tmp;
53
54 int interval_nsec[5] = {1000000, 1500000, 2000000, 2500000, 3000000};
55 int frames_written[5] = {30, 25, 20, 15, 10};
56
57 re = rate_estimator_create(7470, &window, 0.0f);
58 for (i = 0; i < 5; i++) {
59 rc = rate_estimator_check(re, level, &t);
60 EXPECT_EQ(0, rc);
61
62 tmp = rand() % 10;
63 rate_estimator_add_frames(re, frames_written[i] + tmp);
64 level += tmp;
65 t.tv_nsec += interval_nsec[i];
66 }
67 t.tv_nsec += 1;
68 rc = rate_estimator_check(re, level, &t);
69 EXPECT_EQ(1, rc);
70 /* Calculated rate is 7475.72 */
71 EXPECT_GT(7476, rate_estimator_get_rate(re));
72 EXPECT_LT(7475, rate_estimator_get_rate(re));
73
74 rate_estimator_destroy(re);
75 }
76
TEST(RateEstimatorTest,EstimateRateSkewTooLarge)77 TEST(RateEstimatorTest, EstimateRateSkewTooLarge) {
78 struct rate_estimator *re;
79 struct timespec t = {
80 .tv_sec = 1,
81 .tv_nsec = 0
82 };
83 int level = 240;
84 int i, rc, tmp;
85
86 int interval_nsec[5] = {1000000, 1500000, 2000000, 2500000, 3000000};
87 int frames_written[5] = {30, 25, 20, 15, 10};
88
89 re = rate_estimator_create(10000, &window, 0.0f);
90 for (i = 0; i < 5; i++) {
91 rc = rate_estimator_check(re, level, &t);
92 EXPECT_EQ(0, rc);
93
94 tmp = rand() % 10;
95 rate_estimator_add_frames(re, frames_written[i] + tmp);
96 level += tmp;
97 t.tv_nsec += interval_nsec[i];
98 }
99 t.tv_nsec += 1;
100 rc = rate_estimator_check(re, level, &t);
101 EXPECT_EQ(1, rc);
102 /* Estimated rate too far from allowed max rate skew */
103 EXPECT_EQ(10000, rate_estimator_get_rate(re));
104
105 rate_estimator_destroy(re);
106 }
107
TEST(RateEstimatorTest,EstimateOutputSmooth)108 TEST(RateEstimatorTest, EstimateOutputSmooth) {
109 struct rate_estimator *re;
110 struct timespec t;
111 int rc;
112
113 re = rate_estimator_create(10010, &window, 0.9f);
114 t.tv_sec = 1;
115 rc = rate_estimator_check(re, 240, &t);
116 EXPECT_EQ(0, rc);
117
118 /* Test that output device consumes 100 frames in
119 * 10ms. */
120 rate_estimator_add_frames(re, 55);
121 t.tv_nsec += 5000000;
122 rc = rate_estimator_check(re, 245, &t);
123 EXPECT_EQ(0, rc);
124
125 rate_estimator_add_frames(re, 55);
126 t.tv_nsec += 5000001;
127 rc = rate_estimator_check(re, 250, &t);
128 EXPECT_EQ(1, rc);
129
130 /* Assert the rate is smoothed 10010 * 0.9 + 10000 * 0.1 */
131 EXPECT_LT(10008, rate_estimator_get_rate(re));
132 EXPECT_GT(10009, rate_estimator_get_rate(re));
133
134 rate_estimator_destroy(re);
135 }
136
TEST(RateEstimatorTest,EstimateInputLinear)137 TEST(RateEstimatorTest, EstimateInputLinear) {
138 struct rate_estimator *re;
139 struct timespec t;
140 int i, rc, level, tmp;
141
142 re = rate_estimator_create(10000, &window, 0.0f);
143 t.tv_sec = 1;
144 level = 1200;
145 for (i = 0; i < 20; i++) {
146 rc = rate_estimator_check(re, level, &t);
147 EXPECT_EQ(0, rc);
148
149 /* Test that stream consumes 5 frames. */
150 tmp = rand() % 10;
151 rate_estimator_add_frames(re, -(5 + tmp));
152 level -= tmp;
153 t.tv_nsec += 500000;
154 }
155 t.tv_nsec += 1;
156 rc = rate_estimator_check(re, level, &t);
157 EXPECT_EQ(1, rc);
158 EXPECT_GT(10000, rate_estimator_get_rate(re));
159 EXPECT_LT(9999, rate_estimator_get_rate(re));
160
161 rate_estimator_destroy(re);
162 }
163
TEST(RateEstimatorTest,EstimateInputLinear2)164 TEST(RateEstimatorTest, EstimateInputLinear2) {
165 struct rate_estimator *re;
166 struct timespec t;
167 int rc;
168 static struct timespec this_window = {
169 .tv_sec = 0,
170 .tv_nsec = 100000000
171 };
172
173 re = rate_estimator_create(10000, &this_window, 0.0f);
174 t.tv_sec = 1;
175 t.tv_nsec = 0;
176 rc = rate_estimator_check(re, 200, &t);
177 EXPECT_EQ(0, rc);
178
179 t.tv_nsec += 50000000;
180 rc = rate_estimator_check(re, 700, &t);
181 EXPECT_EQ(0, rc);
182
183 rate_estimator_add_frames(re, -100);
184
185 t.tv_nsec += 50000000;
186 rc = rate_estimator_check(re, 1100, &t);
187 t.tv_nsec += 1;
188 rc = rate_estimator_check(re, 1100, &t);
189 EXPECT_EQ(1, rc);
190 EXPECT_GT(10000, rate_estimator_get_rate(re));
191 EXPECT_LT(9999, rate_estimator_get_rate(re));
192
193 rate_estimator_destroy(re);
194 }
195
main(int argc,char ** argv)196 int main(int argc, char **argv) {
197 ::testing::InitGoogleTest(&argc, argv);
198 return RUN_ALL_TESTS();
199 }
200