Chromium Code Reviews| Index: third_party/WebKit/Source/platform/scheduler/base/queueing_time_estimator_unittest.cc |
| diff --git a/third_party/WebKit/Source/platform/scheduler/base/queueing_time_estimator_unittest.cc b/third_party/WebKit/Source/platform/scheduler/base/queueing_time_estimator_unittest.cc |
| index 2baaa9d2f167c5ddae805de35c3317cfa0295db6..5629160ea82f3df29adfabcda828f0c378679eb4 100644 |
| --- a/third_party/WebKit/Source/platform/scheduler/base/queueing_time_estimator_unittest.cc |
| +++ b/third_party/WebKit/Source/platform/scheduler/base/queueing_time_estimator_unittest.cc |
| @@ -3,6 +3,7 @@ |
| // found in the LICENSE file. |
| #include "platform/scheduler/base/queueing_time_estimator.h" |
| +#include "base/logging.h" |
| #include "platform/scheduler/base/test_time_source.h" |
| #include "testing/gmock/include/gmock/gmock.h" |
| #include "testing/gtest/include/gtest/gtest.h" |
| @@ -15,7 +16,8 @@ using QueueingTimeEstimatorTest = testing::Test; |
| class TestQueueingTimeEstimatorClient : public QueueingTimeEstimator::Client { |
| public: |
| void OnQueueingTimeForWindowEstimated( |
| - base::TimeDelta queueing_time) override { |
| + base::TimeDelta queueing_time, |
| + base::TimeTicks window_start_time) override { |
| expected_queueing_times_.push_back(queueing_time); |
| } |
| const std::vector<base::TimeDelta>& expected_queueing_times() { |
| @@ -29,8 +31,11 @@ class TestQueueingTimeEstimatorClient : public QueueingTimeEstimator::Client { |
| class QueueingTimeEstimatorForTest : public QueueingTimeEstimator { |
| public: |
| QueueingTimeEstimatorForTest(TestQueueingTimeEstimatorClient* client, |
| - base::TimeDelta window_duration) |
| - : QueueingTimeEstimator(client, window_duration) {} |
| + base::TimeDelta window_duration, |
| + uint window_duration_step_ratio) |
| + : QueueingTimeEstimator(client, |
| + window_duration, |
| + window_duration_step_ratio) {} |
| }; |
| // Three tasks of one second each, all within a 5 second window. Expected |
| @@ -41,7 +46,7 @@ TEST_F(QueueingTimeEstimatorTest, AllTasksWithinWindow) { |
| base::TimeTicks time; |
| TestQueueingTimeEstimatorClient client; |
| QueueingTimeEstimatorForTest estimator(&client, |
| - base::TimeDelta::FromSeconds(5)); |
| + base::TimeDelta::FromSeconds(5), 1); |
| for (int i = 0; i < 3; ++i) { |
| estimator.OnTopLevelTaskStarted(time); |
| time += base::TimeDelta::FromMilliseconds(1000); |
| @@ -68,7 +73,7 @@ TEST_F(QueueingTimeEstimatorTest, AllTasksWithinWindow) { |
| TEST_F(QueueingTimeEstimatorTest, MultiWindowTask) { |
| TestQueueingTimeEstimatorClient client; |
| QueueingTimeEstimatorForTest estimator(&client, |
| - base::TimeDelta::FromSeconds(5)); |
| + base::TimeDelta::FromSeconds(5), 1); |
| base::TimeTicks time; |
| time += base::TimeDelta::FromMilliseconds(5000); |
| estimator.OnTopLevelTaskStarted(time); |
| @@ -103,7 +108,7 @@ TEST_F(QueueingTimeEstimatorTest, |
| EstimateQueueingTimeDuringSingleLongTaskIncompleteWindow) { |
| TestQueueingTimeEstimatorClient client; |
| QueueingTimeEstimatorForTest estimator(&client, |
| - base::TimeDelta::FromSeconds(5)); |
| + base::TimeDelta::FromSeconds(5), 1); |
| base::TimeTicks time; |
| time += base::TimeDelta::FromMilliseconds(5000); |
| estimator.OnTopLevelTaskStarted(time); |
| @@ -128,7 +133,7 @@ TEST_F(QueueingTimeEstimatorTest, |
| EstimateQueueingTimeDuringSingleLongTaskExceedingWindow) { |
| TestQueueingTimeEstimatorClient client; |
| QueueingTimeEstimatorForTest estimator(&client, |
| - base::TimeDelta::FromSeconds(5)); |
| + base::TimeDelta::FromSeconds(5), 1); |
| base::TimeTicks time; |
| time += base::TimeDelta::FromMilliseconds(5000); |
| estimator.OnTopLevelTaskStarted(time); |
| @@ -144,13 +149,79 @@ TEST_F(QueueingTimeEstimatorTest, |
| EXPECT_EQ(base::TimeDelta::FromMilliseconds(5500), estimated_queueing_time); |
| } |
| +// Estimate |
| +// | |
| +// v |
| +// Task|------------------------------... |
| +// Time|---o---o---o---o---o---o--------> |
| +// 0 1 2 3 4 5 6 |
| +// | s | s | s | s | s | |
| +// |--------win1-------| |
| +// |--------win2-------| |
| +// |
| +// s: step window |
| +// win1: The last full window. |
| +// win2: The partial window. |
| +TEST_F(QueueingTimeEstimatorTest, |
| + SlidingWindowEstimateQueueingTimeFullWindowLargerThanPartial) { |
| + TestQueueingTimeEstimatorClient client; |
| + QueueingTimeEstimatorForTest estimator(&client, |
| + base::TimeDelta::FromSeconds(5), 5); |
| + base::TimeTicks time; |
| + time += base::TimeDelta::FromMilliseconds(5000); |
| + estimator.OnTopLevelTaskStarted(time); |
| + estimator.OnTopLevelTaskCompleted(time); |
| + |
| + base::TimeTicks start_time = time; |
| + estimator.OnTopLevelTaskStarted(start_time); |
| + |
| + time += base::TimeDelta::FromMilliseconds(5500); |
| + |
| + base::TimeDelta estimated_queueing_time = |
| + estimator.EstimateQueueingTimeIncludingCurrentTask(time); |
| + |
| + EXPECT_EQ(base::TimeDelta::FromMilliseconds(3000), estimated_queueing_time); |
|
tdresser
2017/05/11 13:52:45
Can you add a comment explaining where this 3000 n
Liquan (Max) Gu
2017/05/11 15:14:13
Done.
|
| +} |
| +// Estimate |
| +// | |
| +// v |
| +// Task |----------... |
| +// Time|---o---o---o---o---o---o--------> |
| +// 0 1 2 3 4 5 6 |
| +// | s | s | s | s | s | |
| +// |--------win1-------| |
| +// |--------win2-------| |
| +// |
| +// s: step window |
| +// win1: The last full window. |
| +// win2: The partial window. |
| +TEST_F(QueueingTimeEstimatorTest, |
| + SlidingWindowEstimateQueueingTimePartialWindowLargerThanFull) { |
| + TestQueueingTimeEstimatorClient client; |
| + QueueingTimeEstimatorForTest estimator(&client, |
| + base::TimeDelta::FromSeconds(5), 5); |
| + base::TimeTicks time; |
| + time += base::TimeDelta::FromMilliseconds(5000); |
| + estimator.OnTopLevelTaskStarted(time); |
| + estimator.OnTopLevelTaskCompleted(time); |
| + |
| + time += base::TimeDelta::FromMilliseconds(5000); |
| + base::TimeTicks start_time = time; |
| + estimator.OnTopLevelTaskStarted(start_time); |
| + time += base::TimeDelta::FromMilliseconds(500); |
| + |
| + base::TimeDelta estimated_queueing_time = |
| + estimator.EstimateQueueingTimeIncludingCurrentTask(time); |
| + |
| + EXPECT_EQ(base::TimeDelta::FromMilliseconds(25), estimated_queueing_time); |
|
tdresser
2017/05/11 13:52:44
Can you add a comment explaining where this 25 cam
Liquan (Max) Gu
2017/05/11 15:14:13
Done.
|
| +} |
| // Tasks containing nested message loops may be extremely long without |
| // negatively impacting user experience. Ignore such tasks. |
| TEST_F(QueueingTimeEstimatorTest, IgnoresTasksWithNestedMessageLoops) { |
| TestQueueingTimeEstimatorClient client; |
| QueueingTimeEstimatorForTest estimator(&client, |
| - base::TimeDelta::FromSeconds(5)); |
| + base::TimeDelta::FromSeconds(5), 1); |
| base::TimeTicks time; |
| time += base::TimeDelta::FromMilliseconds(5000); |
| estimator.OnTopLevelTaskStarted(time); |
| @@ -189,7 +260,7 @@ TEST_F(QueueingTimeEstimatorTest, IgnoresTasksWithNestedMessageLoops) { |
| TEST_F(QueueingTimeEstimatorTest, IgnoreExtremelyLongTasks) { |
| TestQueueingTimeEstimatorClient client; |
| QueueingTimeEstimatorForTest estimator(&client, |
| - base::TimeDelta::FromSeconds(5)); |
| + base::TimeDelta::FromSeconds(5), 1); |
| // Start with a 1 second task. |
| base::TimeTicks time; |
| estimator.OnTopLevelTaskStarted(time); |
| @@ -223,5 +294,143 @@ TEST_F(QueueingTimeEstimatorTest, IgnoreExtremelyLongTasks) { |
| base::TimeDelta::FromMilliseconds(100))); |
| } |
| +// ^ Instantaneous queuing time |
| +// | |
| +// | |
| +// | |\ |
| +// | | \ |
| +// | | \ |
| +// | | \ |
| +// | | \ | |
| +// ------------------------------------------------> Time |
| +// |s|s|s|s|s| |
| +// |---win---| |
| +// |---win---| |
| +// |---win---| |
| +TEST_F(QueueingTimeEstimatorTest, SlidingWindowOverOneTask) { |
| + TestQueueingTimeEstimatorClient client; |
| + QueueingTimeEstimatorForTest estimator(&client, |
| + base::TimeDelta::FromSeconds(5), 5); |
| + base::TimeTicks time; |
| + time += base::TimeDelta::FromMilliseconds(1000); |
| + |
| + estimator.OnTopLevelTaskStarted(time); |
| + time += base::TimeDelta::FromMilliseconds(5000); |
| + estimator.OnTopLevelTaskCompleted(time); |
|
tdresser
2017/05/11 13:52:44
I think a newline after the task completion calls
Liquan (Max) Gu
2017/05/11 15:14:13
Done.
|
| + time += base::TimeDelta::FromMilliseconds(6000); |
| + estimator.OnTopLevelTaskStarted(time); |
| + estimator.OnTopLevelTaskCompleted(time); |
| + |
| + EXPECT_THAT(client.expected_queueing_times(), |
| + testing::ElementsAre(base::TimeDelta::FromMilliseconds(900), |
| + base::TimeDelta::FromMilliseconds(1600), |
| + base::TimeDelta::FromMilliseconds(2100), |
| + base::TimeDelta::FromMilliseconds(2400), |
| + base::TimeDelta::FromMilliseconds(2500), |
| + base::TimeDelta::FromMilliseconds(1600), |
| + base::TimeDelta::FromMilliseconds(900), |
| + base::TimeDelta::FromMilliseconds(400), |
| + base::TimeDelta::FromMilliseconds(100), |
| + base::TimeDelta::FromMilliseconds(0))); |
| +} |
| + |
| +// ^ Instantaneous queuing time |
| +// | |
| +// | |
| +// | |\ |
| +// | | \ |
| +// | | \ |
| +// | | \ |\ |
| +// | | \ | \ | |
| +// ------------------------------------------------> Time |
| +// |s|s|s|s|s| |
| +// |---win---| |
| +// |---win---| |
| +// |---win---| |
| +TEST_F(QueueingTimeEstimatorTest, SlidingWindowOverTwoTasksWithinFirstWindow) { |
| + TestQueueingTimeEstimatorClient client; |
| + QueueingTimeEstimatorForTest estimator(&client, |
| + base::TimeDelta::FromSeconds(5), 5); |
| + base::TimeTicks time; |
| + time += base::TimeDelta::FromMilliseconds(1000); |
| + |
| + estimator.OnTopLevelTaskStarted(time); |
| + time += base::TimeDelta::FromMilliseconds(2500); |
| + estimator.OnTopLevelTaskCompleted(time); |
| + time += base::TimeDelta::FromMilliseconds(500); |
| + estimator.OnTopLevelTaskStarted(time); |
| + time += base::TimeDelta::FromMilliseconds(1000); |
| + estimator.OnTopLevelTaskCompleted(time); |
| + time += base::TimeDelta::FromMilliseconds(6000); |
| + estimator.OnTopLevelTaskStarted(time); |
| + estimator.OnTopLevelTaskCompleted(time); |
| + std::vector<long> expected_milliseconds = {400, 600, 625, 725, 725, |
| + 325, 125, 100, 0}; |
| + std::vector<base::TimeDelta> expected_durations = { |
| + base::TimeDelta::FromMilliseconds(400), |
| + base::TimeDelta::FromMilliseconds(600), |
| + base::TimeDelta::FromMilliseconds(625), |
| + base::TimeDelta::FromMilliseconds(725), |
| + base::TimeDelta::FromMilliseconds(725), |
| + base::TimeDelta::FromMilliseconds(325), |
| + base::TimeDelta::FromMilliseconds(125), |
| + base::TimeDelta::FromMilliseconds(100), |
| + base::TimeDelta::FromMilliseconds(0)}; |
| + EXPECT_THAT(client.expected_queueing_times(), |
| + testing::ElementsAreArray(expected_durations)); |
| +} |
| + |
| +// ^ Instantaneous queuing time |
| +// | |
| +// | |
| +// | |\ |
| +// | | \ |
| +// | | \ |
| +// | | \ |\ |
| +// | | \| \ | |
| +// ------------------------------------------------> Time |
| +// |s|s|s|s|s| |
| +// |---win---| |
| +// |---win---| |
| +// |---win---| |
| +TEST_F(QueueingTimeEstimatorTest, |
| + SlidingWindowOverTwoTasksStridingFirstWindow) { |
|
tdresser
2017/05/11 13:52:45
I'm not sure what "Striding First Window".
Liquan (Max) Gu
2017/05/11 15:14:13
Spanning several windows sound better?
tdresser
2017/05/11 15:55:11
Yup!
|
| + TestQueueingTimeEstimatorClient client; |
| + QueueingTimeEstimatorForTest estimator(&client, |
| + base::TimeDelta::FromSeconds(5), 5); |
| + base::TimeTicks time; |
| + time += base::TimeDelta::FromMilliseconds(1000); |
| + estimator.OnTopLevelTaskStarted(time); |
| + estimator.OnTopLevelTaskCompleted(time); |
| + time += base::TimeDelta::FromMilliseconds(4000); |
| + estimator.OnTopLevelTaskStarted(time); |
| + time += base::TimeDelta::FromMilliseconds(2500); |
| + estimator.OnTopLevelTaskCompleted(time); |
| + estimator.OnTopLevelTaskStarted(time); |
| + time += base::TimeDelta::FromMilliseconds(1000); |
| + estimator.OnTopLevelTaskCompleted(time); |
| + time += base::TimeDelta::FromMilliseconds(6000); |
| + estimator.OnTopLevelTaskStarted(time); |
| + estimator.OnTopLevelTaskCompleted(time); |
| + |
| + std::vector<base::TimeDelta> expected_durations = { |
| + base::TimeDelta::FromMilliseconds(0), |
| + base::TimeDelta::FromMilliseconds(0), |
| + base::TimeDelta::FromMilliseconds(0), |
| + base::TimeDelta::FromMilliseconds(0), |
| + base::TimeDelta::FromMilliseconds(400), |
| + base::TimeDelta::FromMilliseconds(600), |
| + base::TimeDelta::FromMilliseconds(700), |
| + base::TimeDelta::FromMilliseconds(725), |
| + base::TimeDelta::FromMilliseconds(725), |
| + base::TimeDelta::FromMilliseconds(325), |
| + base::TimeDelta::FromMilliseconds(125), |
| + base::TimeDelta::FromMilliseconds(25), |
| + base::TimeDelta::FromMilliseconds(0)}; |
| + |
| + EXPECT_THAT(client.expected_queueing_times(), |
| + testing::ElementsAreArray(expected_durations)); |
| +} |
| + |
| } // namespace scheduler |
| } // namespace blink |