OLD | NEW |
| (Empty) |
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 "content/renderer/scheduler/renderer_scheduler_impl.h" | |
6 | |
7 #include "base/callback.h" | |
8 #include "cc/output/begin_frame_args.h" | |
9 #include "cc/test/ordered_simple_task_runner.h" | |
10 #include "cc/test/test_now_source.h" | |
11 #include "content/child/scheduler/nestable_task_runner_for_test.h" | |
12 #include "content/child/scheduler/scheduler_message_loop_delegate.h" | |
13 #include "content/test/test_time_source.h" | |
14 #include "testing/gmock/include/gmock/gmock.h" | |
15 #include "testing/gtest/include/gtest/gtest.h" | |
16 | |
17 namespace content { | |
18 | |
19 namespace { | |
20 class FakeInputEvent : public blink::WebInputEvent { | |
21 public: | |
22 explicit FakeInputEvent(blink::WebInputEvent::Type event_type) | |
23 : WebInputEvent(sizeof(FakeInputEvent)) { | |
24 type = event_type; | |
25 } | |
26 | |
27 FakeInputEvent(blink::WebInputEvent::Type event_type, int event_modifiers) | |
28 : WebInputEvent(sizeof(FakeInputEvent)) { | |
29 type = event_type; | |
30 modifiers = event_modifiers; | |
31 } | |
32 }; | |
33 | |
34 void AppendToVectorTestTask(std::vector<std::string>* vector, | |
35 std::string value) { | |
36 vector->push_back(value); | |
37 } | |
38 | |
39 void AppendToVectorIdleTestTask(std::vector<std::string>* vector, | |
40 std::string value, | |
41 base::TimeTicks deadline) { | |
42 AppendToVectorTestTask(vector, value); | |
43 } | |
44 | |
45 void NullTask() { | |
46 } | |
47 | |
48 void AppendToVectorReentrantTask( | |
49 base::SingleThreadTaskRunner* task_runner, | |
50 std::vector<int>* vector, | |
51 int* reentrant_count, | |
52 int max_reentrant_count) { | |
53 vector->push_back((*reentrant_count)++); | |
54 if (*reentrant_count < max_reentrant_count) { | |
55 task_runner->PostTask( | |
56 FROM_HERE, base::Bind(AppendToVectorReentrantTask, | |
57 base::Unretained(task_runner), vector, | |
58 reentrant_count, max_reentrant_count)); | |
59 } | |
60 } | |
61 | |
62 void IdleTestTask(int* run_count, | |
63 base::TimeTicks* deadline_out, | |
64 base::TimeTicks deadline) { | |
65 (*run_count)++; | |
66 *deadline_out = deadline; | |
67 } | |
68 | |
69 int max_idle_task_reposts = 2; | |
70 | |
71 void RepostingIdleTestTask( | |
72 SingleThreadIdleTaskRunner* idle_task_runner, | |
73 int* run_count, | |
74 base::TimeTicks deadline) { | |
75 if ((*run_count + 1) < max_idle_task_reposts) { | |
76 idle_task_runner->PostIdleTask( | |
77 FROM_HERE, | |
78 base::Bind(&RepostingIdleTestTask, base::Unretained(idle_task_runner), | |
79 run_count)); | |
80 } | |
81 (*run_count)++; | |
82 } | |
83 | |
84 void UpdateClockToDeadlineIdleTestTask( | |
85 cc::TestNowSource* clock, | |
86 base::SingleThreadTaskRunner* task_runner, | |
87 int* run_count, | |
88 base::TimeTicks deadline) { | |
89 clock->SetNow(deadline); | |
90 // Due to the way in which OrderedSimpleTestRunner orders tasks and the fact | |
91 // that we updated the time within a task, the delayed pending task to call | |
92 // EndIdlePeriod will not happen until after a TaskQueueManager DoWork, so | |
93 // post a normal task here to ensure it runs before the next idle task. | |
94 task_runner->PostTask(FROM_HERE, base::Bind(NullTask)); | |
95 (*run_count)++; | |
96 } | |
97 | |
98 void PostingYieldingTestTask( | |
99 RendererSchedulerImpl* scheduler, | |
100 base::SingleThreadTaskRunner* task_runner, | |
101 bool simulate_input, | |
102 bool* should_yield_before, | |
103 bool* should_yield_after) { | |
104 *should_yield_before = scheduler->ShouldYieldForHighPriorityWork(); | |
105 task_runner->PostTask(FROM_HERE, base::Bind(NullTask)); | |
106 if (simulate_input) { | |
107 scheduler->DidReceiveInputEventOnCompositorThread( | |
108 FakeInputEvent(blink::WebInputEvent::GestureFlingStart)); | |
109 } | |
110 *should_yield_after = scheduler->ShouldYieldForHighPriorityWork(); | |
111 } | |
112 | |
113 void AnticipationTestTask(RendererSchedulerImpl* scheduler, | |
114 bool simulate_input, | |
115 bool* is_anticipated_before, | |
116 bool* is_anticipated_after) { | |
117 *is_anticipated_before = scheduler->IsHighPriorityWorkAnticipated(); | |
118 if (simulate_input) { | |
119 scheduler->DidReceiveInputEventOnCompositorThread( | |
120 FakeInputEvent(blink::WebInputEvent::GestureFlingStart)); | |
121 } | |
122 *is_anticipated_after = scheduler->IsHighPriorityWorkAnticipated(); | |
123 } | |
124 }; // namespace | |
125 | |
126 class RendererSchedulerImplTest : public testing::Test { | |
127 public: | |
128 using Policy = RendererSchedulerImpl::Policy; | |
129 | |
130 RendererSchedulerImplTest() | |
131 : clock_(cc::TestNowSource::Create(5000)), | |
132 mock_task_runner_(new cc::OrderedSimpleTaskRunner(clock_, false)), | |
133 nestable_task_runner_( | |
134 NestableTaskRunnerForTest::Create(mock_task_runner_)), | |
135 scheduler_(new RendererSchedulerImpl(nestable_task_runner_)), | |
136 default_task_runner_(scheduler_->DefaultTaskRunner()), | |
137 compositor_task_runner_(scheduler_->CompositorTaskRunner()), | |
138 loading_task_runner_(scheduler_->LoadingTaskRunner()), | |
139 idle_task_runner_(scheduler_->IdleTaskRunner()), | |
140 timer_task_runner_(scheduler_->TimerTaskRunner()) { | |
141 scheduler_->GetSchedulerHelperForTesting()->SetTimeSourceForTesting( | |
142 make_scoped_ptr(new TestTimeSource(clock_))); | |
143 scheduler_->GetSchedulerHelperForTesting() | |
144 ->GetTaskQueueManagerForTesting() | |
145 ->SetTimeSourceForTesting(make_scoped_ptr(new TestTimeSource(clock_))); | |
146 } | |
147 | |
148 RendererSchedulerImplTest(base::MessageLoop* message_loop) | |
149 : clock_(cc::TestNowSource::Create(5000)), | |
150 message_loop_(message_loop), | |
151 nestable_task_runner_( | |
152 SchedulerMessageLoopDelegate::Create(message_loop)), | |
153 scheduler_(new RendererSchedulerImpl(nestable_task_runner_)), | |
154 default_task_runner_(scheduler_->DefaultTaskRunner()), | |
155 compositor_task_runner_(scheduler_->CompositorTaskRunner()), | |
156 loading_task_runner_(scheduler_->LoadingTaskRunner()), | |
157 idle_task_runner_(scheduler_->IdleTaskRunner()), | |
158 timer_task_runner_(scheduler_->TimerTaskRunner()) { | |
159 scheduler_->GetSchedulerHelperForTesting()->SetTimeSourceForTesting( | |
160 make_scoped_ptr(new TestTimeSource(clock_))); | |
161 scheduler_->GetSchedulerHelperForTesting() | |
162 ->GetTaskQueueManagerForTesting() | |
163 ->SetTimeSourceForTesting(make_scoped_ptr(new TestTimeSource(clock_))); | |
164 } | |
165 ~RendererSchedulerImplTest() override {} | |
166 | |
167 void TearDown() override { | |
168 DCHECK(!mock_task_runner_.get() || !message_loop_.get()); | |
169 if (mock_task_runner_.get()) { | |
170 // Check that all tests stop posting tasks. | |
171 mock_task_runner_->SetAutoAdvanceNowToPendingTasks(true); | |
172 while (mock_task_runner_->RunUntilIdle()) { | |
173 } | |
174 } else { | |
175 message_loop_->RunUntilIdle(); | |
176 } | |
177 } | |
178 | |
179 void RunUntilIdle() { | |
180 // Only one of mock_task_runner_ or message_loop_ should be set. | |
181 DCHECK(!mock_task_runner_.get() || !message_loop_.get()); | |
182 if (mock_task_runner_.get()) | |
183 mock_task_runner_->RunUntilIdle(); | |
184 else | |
185 message_loop_->RunUntilIdle(); | |
186 } | |
187 | |
188 void DoMainFrame() { | |
189 scheduler_->WillBeginFrame(cc::BeginFrameArgs::Create( | |
190 BEGINFRAME_FROM_HERE, clock_->Now(), base::TimeTicks(), | |
191 base::TimeDelta::FromMilliseconds(1000), cc::BeginFrameArgs::NORMAL)); | |
192 scheduler_->DidCommitFrameToCompositor(); | |
193 } | |
194 | |
195 void EnableIdleTasks() { DoMainFrame(); } | |
196 | |
197 Policy CurrentPolicy() { return scheduler_->current_policy_; } | |
198 | |
199 void EnsureUrgentPolicyUpdatePostedOnMainThread() { | |
200 base::AutoLock lock(scheduler_->incoming_signals_lock_); | |
201 scheduler_->EnsureUrgentPolicyUpdatePostedOnMainThread(FROM_HERE); | |
202 } | |
203 | |
204 void ScheduleDelayedPolicyUpdate(base::TimeDelta delay) { | |
205 scheduler_->delayed_update_policy_runner_.SetDeadline(FROM_HERE, delay, | |
206 clock_->Now()); | |
207 } | |
208 | |
209 // Helper for posting several tasks of specific types. |task_descriptor| is a | |
210 // string with space delimited task identifiers. The first letter of each | |
211 // task identifier specifies the task type: | |
212 // - 'D': Default task | |
213 // - 'C': Compositor task | |
214 // - 'L': Loading task | |
215 // - 'I': Idle task | |
216 // - 'T': Timer task | |
217 void PostTestTasks(std::vector<std::string>* run_order, | |
218 const std::string& task_descriptor) { | |
219 std::istringstream stream(task_descriptor); | |
220 while (!stream.eof()) { | |
221 std::string task; | |
222 stream >> task; | |
223 switch (task[0]) { | |
224 case 'D': | |
225 default_task_runner_->PostTask( | |
226 FROM_HERE, base::Bind(&AppendToVectorTestTask, run_order, task)); | |
227 break; | |
228 case 'C': | |
229 compositor_task_runner_->PostTask( | |
230 FROM_HERE, base::Bind(&AppendToVectorTestTask, run_order, task)); | |
231 break; | |
232 case 'L': | |
233 loading_task_runner_->PostTask( | |
234 FROM_HERE, base::Bind(&AppendToVectorTestTask, run_order, task)); | |
235 break; | |
236 case 'I': | |
237 idle_task_runner_->PostIdleTask( | |
238 FROM_HERE, | |
239 base::Bind(&AppendToVectorIdleTestTask, run_order, task)); | |
240 break; | |
241 case 'T': | |
242 timer_task_runner_->PostTask( | |
243 FROM_HERE, base::Bind(&AppendToVectorTestTask, run_order, task)); | |
244 break; | |
245 default: | |
246 NOTREACHED(); | |
247 } | |
248 } | |
249 } | |
250 | |
251 protected: | |
252 static base::TimeDelta priority_escalation_after_input_duration() { | |
253 return base::TimeDelta::FromMilliseconds( | |
254 RendererSchedulerImpl::kPriorityEscalationAfterInputMillis); | |
255 } | |
256 | |
257 static base::TimeDelta maximum_idle_period_duration() { | |
258 return base::TimeDelta::FromMilliseconds( | |
259 SchedulerHelper::kMaximumIdlePeriodMillis); | |
260 } | |
261 | |
262 static base::TimeDelta end_idle_when_hidden_delay() { | |
263 return base::TimeDelta::FromMilliseconds( | |
264 RendererSchedulerImpl::kEndIdleWhenHiddenDelayMillis); | |
265 } | |
266 | |
267 scoped_refptr<cc::TestNowSource> clock_; | |
268 // Only one of mock_task_runner_ or message_loop_ will be set. | |
269 scoped_refptr<cc::OrderedSimpleTaskRunner> mock_task_runner_; | |
270 scoped_ptr<base::MessageLoop> message_loop_; | |
271 | |
272 scoped_refptr<NestableSingleThreadTaskRunner> nestable_task_runner_; | |
273 scoped_ptr<RendererSchedulerImpl> scheduler_; | |
274 scoped_refptr<base::SingleThreadTaskRunner> default_task_runner_; | |
275 scoped_refptr<base::SingleThreadTaskRunner> compositor_task_runner_; | |
276 scoped_refptr<base::SingleThreadTaskRunner> loading_task_runner_; | |
277 scoped_refptr<SingleThreadIdleTaskRunner> idle_task_runner_; | |
278 scoped_refptr<base::SingleThreadTaskRunner> timer_task_runner_; | |
279 | |
280 DISALLOW_COPY_AND_ASSIGN(RendererSchedulerImplTest); | |
281 }; | |
282 | |
283 TEST_F(RendererSchedulerImplTest, TestPostDefaultTask) { | |
284 std::vector<std::string> run_order; | |
285 PostTestTasks(&run_order, "D1 D2 D3 D4"); | |
286 | |
287 RunUntilIdle(); | |
288 EXPECT_THAT(run_order, | |
289 testing::ElementsAre(std::string("D1"), std::string("D2"), | |
290 std::string("D3"), std::string("D4"))); | |
291 } | |
292 | |
293 TEST_F(RendererSchedulerImplTest, TestPostDefaultAndCompositor) { | |
294 std::vector<std::string> run_order; | |
295 PostTestTasks(&run_order, "D1 C1"); | |
296 RunUntilIdle(); | |
297 EXPECT_THAT(run_order, testing::Contains("D1")); | |
298 EXPECT_THAT(run_order, testing::Contains("C1")); | |
299 } | |
300 | |
301 TEST_F(RendererSchedulerImplTest, TestRentrantTask) { | |
302 int count = 0; | |
303 std::vector<int> run_order; | |
304 default_task_runner_->PostTask( | |
305 FROM_HERE, base::Bind(AppendToVectorReentrantTask, default_task_runner_, | |
306 &run_order, &count, 5)); | |
307 RunUntilIdle(); | |
308 | |
309 EXPECT_THAT(run_order, testing::ElementsAre(0, 1, 2, 3, 4)); | |
310 } | |
311 | |
312 TEST_F(RendererSchedulerImplTest, TestPostIdleTask) { | |
313 int run_count = 0; | |
314 base::TimeTicks expected_deadline = | |
315 clock_->Now() + base::TimeDelta::FromMilliseconds(2300); | |
316 base::TimeTicks deadline_in_task; | |
317 | |
318 clock_->AdvanceNow(base::TimeDelta::FromMilliseconds(100)); | |
319 idle_task_runner_->PostIdleTask( | |
320 FROM_HERE, base::Bind(&IdleTestTask, &run_count, &deadline_in_task)); | |
321 | |
322 RunUntilIdle(); | |
323 EXPECT_EQ(0, run_count); // Shouldn't run yet as no WillBeginFrame. | |
324 | |
325 scheduler_->WillBeginFrame(cc::BeginFrameArgs::Create( | |
326 BEGINFRAME_FROM_HERE, clock_->Now(), base::TimeTicks(), | |
327 base::TimeDelta::FromMilliseconds(1000), cc::BeginFrameArgs::NORMAL)); | |
328 RunUntilIdle(); | |
329 EXPECT_EQ(0, run_count); // Shouldn't run as no DidCommitFrameToCompositor. | |
330 | |
331 clock_->AdvanceNow(base::TimeDelta::FromMilliseconds(1200)); | |
332 scheduler_->DidCommitFrameToCompositor(); | |
333 RunUntilIdle(); | |
334 EXPECT_EQ(0, run_count); // We missed the deadline. | |
335 | |
336 scheduler_->WillBeginFrame(cc::BeginFrameArgs::Create( | |
337 BEGINFRAME_FROM_HERE, clock_->Now(), base::TimeTicks(), | |
338 base::TimeDelta::FromMilliseconds(1000), cc::BeginFrameArgs::NORMAL)); | |
339 clock_->AdvanceNow(base::TimeDelta::FromMilliseconds(800)); | |
340 scheduler_->DidCommitFrameToCompositor(); | |
341 RunUntilIdle(); | |
342 EXPECT_EQ(1, run_count); | |
343 EXPECT_EQ(expected_deadline, deadline_in_task); | |
344 } | |
345 | |
346 TEST_F(RendererSchedulerImplTest, TestRepostingIdleTask) { | |
347 int run_count = 0; | |
348 | |
349 max_idle_task_reposts = 2; | |
350 idle_task_runner_->PostIdleTask( | |
351 FROM_HERE, | |
352 base::Bind(&RepostingIdleTestTask, idle_task_runner_, &run_count)); | |
353 EnableIdleTasks(); | |
354 RunUntilIdle(); | |
355 EXPECT_EQ(1, run_count); | |
356 | |
357 // Reposted tasks shouldn't run until next idle period. | |
358 RunUntilIdle(); | |
359 EXPECT_EQ(1, run_count); | |
360 | |
361 EnableIdleTasks(); | |
362 RunUntilIdle(); | |
363 EXPECT_EQ(2, run_count); | |
364 } | |
365 | |
366 TEST_F(RendererSchedulerImplTest, TestIdleTaskExceedsDeadline) { | |
367 mock_task_runner_->SetAutoAdvanceNowToPendingTasks(true); | |
368 int run_count = 0; | |
369 | |
370 // Post two UpdateClockToDeadlineIdleTestTask tasks. | |
371 idle_task_runner_->PostIdleTask( | |
372 FROM_HERE, base::Bind(&UpdateClockToDeadlineIdleTestTask, clock_, | |
373 default_task_runner_, &run_count)); | |
374 idle_task_runner_->PostIdleTask( | |
375 FROM_HERE, base::Bind(&UpdateClockToDeadlineIdleTestTask, clock_, | |
376 default_task_runner_, &run_count)); | |
377 | |
378 EnableIdleTasks(); | |
379 RunUntilIdle(); | |
380 // Only the first idle task should execute since it's used up the deadline. | |
381 EXPECT_EQ(1, run_count); | |
382 | |
383 EnableIdleTasks(); | |
384 RunUntilIdle(); | |
385 // Second task should be run on the next idle period. | |
386 EXPECT_EQ(2, run_count); | |
387 } | |
388 | |
389 TEST_F(RendererSchedulerImplTest, TestPostIdleTaskAfterWakeup) { | |
390 base::TimeTicks deadline_in_task; | |
391 int run_count = 0; | |
392 | |
393 idle_task_runner_->PostIdleTaskAfterWakeup( | |
394 FROM_HERE, base::Bind(&IdleTestTask, &run_count, &deadline_in_task)); | |
395 | |
396 EnableIdleTasks(); | |
397 RunUntilIdle(); | |
398 // Shouldn't run yet as no other task woke up the scheduler. | |
399 EXPECT_EQ(0, run_count); | |
400 | |
401 idle_task_runner_->PostIdleTaskAfterWakeup( | |
402 FROM_HERE, base::Bind(&IdleTestTask, &run_count, &deadline_in_task)); | |
403 | |
404 EnableIdleTasks(); | |
405 RunUntilIdle(); | |
406 // Another after wakeup idle task shouldn't wake the scheduler. | |
407 EXPECT_EQ(0, run_count); | |
408 | |
409 default_task_runner_->PostTask(FROM_HERE, base::Bind(&NullTask)); | |
410 | |
411 RunUntilIdle(); | |
412 EnableIdleTasks(); // Must start a new idle period before idle task runs. | |
413 RunUntilIdle(); | |
414 // Execution of default task queue task should trigger execution of idle task. | |
415 EXPECT_EQ(2, run_count); | |
416 } | |
417 | |
418 TEST_F(RendererSchedulerImplTest, TestPostIdleTaskAfterWakeupWhileAwake) { | |
419 base::TimeTicks deadline_in_task; | |
420 int run_count = 0; | |
421 | |
422 idle_task_runner_->PostIdleTaskAfterWakeup( | |
423 FROM_HERE, base::Bind(&IdleTestTask, &run_count, &deadline_in_task)); | |
424 default_task_runner_->PostTask(FROM_HERE, base::Bind(&NullTask)); | |
425 | |
426 RunUntilIdle(); | |
427 EnableIdleTasks(); // Must start a new idle period before idle task runs. | |
428 RunUntilIdle(); | |
429 // Should run as the scheduler was already awakened by the normal task. | |
430 EXPECT_EQ(1, run_count); | |
431 } | |
432 | |
433 TEST_F(RendererSchedulerImplTest, TestPostIdleTaskWakesAfterWakeupIdleTask) { | |
434 base::TimeTicks deadline_in_task; | |
435 int run_count = 0; | |
436 | |
437 idle_task_runner_->PostIdleTaskAfterWakeup( | |
438 FROM_HERE, base::Bind(&IdleTestTask, &run_count, &deadline_in_task)); | |
439 idle_task_runner_->PostIdleTask( | |
440 FROM_HERE, base::Bind(&IdleTestTask, &run_count, &deadline_in_task)); | |
441 | |
442 EnableIdleTasks(); | |
443 RunUntilIdle(); | |
444 // Must start a new idle period before after-wakeup idle task runs. | |
445 EnableIdleTasks(); | |
446 RunUntilIdle(); | |
447 // Normal idle task should wake up after-wakeup idle task. | |
448 EXPECT_EQ(2, run_count); | |
449 } | |
450 | |
451 TEST_F(RendererSchedulerImplTest, TestDelayedEndIdlePeriodCanceled) { | |
452 int run_count = 0; | |
453 | |
454 base::TimeTicks deadline_in_task; | |
455 idle_task_runner_->PostIdleTask( | |
456 FROM_HERE, base::Bind(&IdleTestTask, &run_count, &deadline_in_task)); | |
457 | |
458 // Trigger the beginning of an idle period for 1000ms. | |
459 scheduler_->WillBeginFrame(cc::BeginFrameArgs::Create( | |
460 BEGINFRAME_FROM_HERE, clock_->Now(), base::TimeTicks(), | |
461 base::TimeDelta::FromMilliseconds(1000), cc::BeginFrameArgs::NORMAL)); | |
462 DoMainFrame(); | |
463 | |
464 // End the idle period early (after 500ms), and send a WillBeginFrame which | |
465 // specifies that the next idle period should end 1000ms from now. | |
466 clock_->AdvanceNow(base::TimeDelta::FromMilliseconds(500)); | |
467 scheduler_->WillBeginFrame(cc::BeginFrameArgs::Create( | |
468 BEGINFRAME_FROM_HERE, clock_->Now(), base::TimeTicks(), | |
469 base::TimeDelta::FromMilliseconds(1000), cc::BeginFrameArgs::NORMAL)); | |
470 | |
471 RunUntilIdle(); | |
472 EXPECT_EQ(0, run_count); // Not currently in an idle period. | |
473 | |
474 // Trigger the start of the idle period before the task to end the previous | |
475 // idle period has been triggered. | |
476 clock_->AdvanceNow(base::TimeDelta::FromMilliseconds(400)); | |
477 scheduler_->DidCommitFrameToCompositor(); | |
478 | |
479 // Post a task which simulates running until after the previous end idle | |
480 // period delayed task was scheduled for | |
481 scheduler_->DefaultTaskRunner()->PostTask(FROM_HERE, base::Bind(NullTask)); | |
482 clock_->AdvanceNow(base::TimeDelta::FromMilliseconds(300)); | |
483 | |
484 RunUntilIdle(); | |
485 EXPECT_EQ(1, run_count); // We should still be in the new idle period. | |
486 } | |
487 | |
488 TEST_F(RendererSchedulerImplTest, TestDefaultPolicy) { | |
489 std::vector<std::string> run_order; | |
490 PostTestTasks(&run_order, "L1 I1 D1 C1 D2 C2"); | |
491 | |
492 EnableIdleTasks(); | |
493 RunUntilIdle(); | |
494 EXPECT_THAT(run_order, | |
495 testing::ElementsAre(std::string("L1"), std::string("D1"), | |
496 std::string("C1"), std::string("D2"), | |
497 std::string("C2"), std::string("I1"))); | |
498 } | |
499 | |
500 TEST_F(RendererSchedulerImplTest, TestCompositorPolicy) { | |
501 std::vector<std::string> run_order; | |
502 PostTestTasks(&run_order, "L1 I1 D1 C1 D2 C2"); | |
503 | |
504 scheduler_->DidReceiveInputEventOnCompositorThread( | |
505 FakeInputEvent(blink::WebInputEvent::GestureFlingStart)); | |
506 EnableIdleTasks(); | |
507 RunUntilIdle(); | |
508 EXPECT_THAT(run_order, | |
509 testing::ElementsAre(std::string("C1"), std::string("C2"), | |
510 std::string("D1"), std::string("D2"), | |
511 std::string("L1"), std::string("I1"))); | |
512 } | |
513 | |
514 TEST_F(RendererSchedulerImplTest, TestCompositorPolicy_DidAnimateForInput) { | |
515 std::vector<std::string> run_order; | |
516 PostTestTasks(&run_order, "I1 D1 C1 D2 C2"); | |
517 | |
518 scheduler_->DidAnimateForInputOnCompositorThread(); | |
519 EnableIdleTasks(); | |
520 RunUntilIdle(); | |
521 EXPECT_THAT(run_order, | |
522 testing::ElementsAre(std::string("C1"), std::string("C2"), | |
523 std::string("D1"), std::string("D2"), | |
524 std::string("I1"))); | |
525 } | |
526 | |
527 TEST_F(RendererSchedulerImplTest, TestTouchstartPolicy) { | |
528 std::vector<std::string> run_order; | |
529 PostTestTasks(&run_order, "L1 D1 C1 D2 C2 T1 T2"); | |
530 | |
531 // Observation of touchstart should defer execution of idle and loading tasks. | |
532 scheduler_->DidReceiveInputEventOnCompositorThread( | |
533 FakeInputEvent(blink::WebInputEvent::TouchStart)); | |
534 RunUntilIdle(); | |
535 EXPECT_THAT(run_order, | |
536 testing::ElementsAre(std::string("C1"), std::string("C2"), | |
537 std::string("D1"), std::string("D2"), | |
538 std::string("T1"), std::string("T2"))); | |
539 | |
540 // Meta events like TapDown/FlingCancel shouldn't affect the priority. | |
541 run_order.clear(); | |
542 scheduler_->DidReceiveInputEventOnCompositorThread( | |
543 FakeInputEvent(blink::WebInputEvent::GestureFlingCancel)); | |
544 scheduler_->DidReceiveInputEventOnCompositorThread( | |
545 FakeInputEvent(blink::WebInputEvent::GestureTapDown)); | |
546 RunUntilIdle(); | |
547 EXPECT_TRUE(run_order.empty()); | |
548 | |
549 // Action events like ScrollBegin will kick us back into compositor priority, | |
550 // allowing service of the timer, loading and idle queues. | |
551 run_order.clear(); | |
552 scheduler_->DidReceiveInputEventOnCompositorThread( | |
553 FakeInputEvent(blink::WebInputEvent::GestureScrollBegin)); | |
554 RunUntilIdle(); | |
555 | |
556 EXPECT_THAT(run_order, | |
557 testing::ElementsAre(std::string("L1"))); | |
558 } | |
559 | |
560 TEST_F(RendererSchedulerImplTest, | |
561 DidReceiveInputEventOnCompositorThread_IgnoresMouseMove_WhenMouseUp) { | |
562 std::vector<std::string> run_order; | |
563 PostTestTasks(&run_order, "I1 D1 C1 D2 C2"); | |
564 | |
565 scheduler_->DidReceiveInputEventOnCompositorThread( | |
566 FakeInputEvent(blink::WebInputEvent::MouseMove)); | |
567 EnableIdleTasks(); | |
568 RunUntilIdle(); | |
569 // Note compositor tasks are not prioritized. | |
570 EXPECT_THAT(run_order, | |
571 testing::ElementsAre(std::string("D1"), std::string("C1"), | |
572 std::string("D2"), std::string("C2"), | |
573 std::string("I1"))); | |
574 } | |
575 | |
576 TEST_F(RendererSchedulerImplTest, | |
577 DidReceiveInputEventOnCompositorThread_MouseMove_WhenMouseDown) { | |
578 std::vector<std::string> run_order; | |
579 PostTestTasks(&run_order, "I1 D1 C1 D2 C2"); | |
580 | |
581 scheduler_->DidReceiveInputEventOnCompositorThread(FakeInputEvent( | |
582 blink::WebInputEvent::MouseMove, blink::WebInputEvent::LeftButtonDown)); | |
583 EnableIdleTasks(); | |
584 RunUntilIdle(); | |
585 // Note compositor tasks are prioritized. | |
586 EXPECT_THAT(run_order, | |
587 testing::ElementsAre(std::string("C1"), std::string("C2"), | |
588 std::string("D1"), std::string("D2"), | |
589 std::string("I1"))); | |
590 } | |
591 | |
592 TEST_F(RendererSchedulerImplTest, | |
593 DidReceiveInputEventOnCompositorThread_MouseWheel) { | |
594 std::vector<std::string> run_order; | |
595 PostTestTasks(&run_order, "I1 D1 C1 D2 C2"); | |
596 | |
597 scheduler_->DidReceiveInputEventOnCompositorThread( | |
598 FakeInputEvent(blink::WebInputEvent::MouseWheel)); | |
599 EnableIdleTasks(); | |
600 RunUntilIdle(); | |
601 // Note compositor tasks are prioritized. | |
602 EXPECT_THAT(run_order, | |
603 testing::ElementsAre(std::string("C1"), std::string("C2"), | |
604 std::string("D1"), std::string("D2"), | |
605 std::string("I1"))); | |
606 } | |
607 | |
608 TEST_F(RendererSchedulerImplTest, | |
609 DidReceiveInputEventOnCompositorThread_IgnoresKeyboardEvents) { | |
610 std::vector<std::string> run_order; | |
611 PostTestTasks(&run_order, "I1 D1 C1 D2 C2"); | |
612 | |
613 scheduler_->DidReceiveInputEventOnCompositorThread( | |
614 FakeInputEvent(blink::WebInputEvent::KeyDown)); | |
615 EnableIdleTasks(); | |
616 RunUntilIdle(); | |
617 // Note compositor tasks are not prioritized. | |
618 EXPECT_THAT(run_order, | |
619 testing::ElementsAre(std::string("D1"), std::string("C1"), | |
620 std::string("D2"), std::string("C2"), | |
621 std::string("I1"))); | |
622 } | |
623 | |
624 TEST_F(RendererSchedulerImplTest, | |
625 TestCompositorPolicyDoesNotStarveDefaultTasks) { | |
626 std::vector<std::string> run_order; | |
627 PostTestTasks(&run_order, "D1 C1"); | |
628 | |
629 for (int i = 0; i < 20; i++) { | |
630 compositor_task_runner_->PostTask(FROM_HERE, base::Bind(&NullTask)); | |
631 } | |
632 PostTestTasks(&run_order, "C2"); | |
633 | |
634 scheduler_->DidReceiveInputEventOnCompositorThread( | |
635 FakeInputEvent(blink::WebInputEvent::GestureFlingStart)); | |
636 RunUntilIdle(); | |
637 // Ensure that the default D1 task gets to run at some point before the final | |
638 // C2 compositor task. | |
639 EXPECT_THAT(run_order, | |
640 testing::ElementsAre(std::string("C1"), std::string("D1"), | |
641 std::string("C2"))); | |
642 } | |
643 | |
644 TEST_F(RendererSchedulerImplTest, TestCompositorPolicyEnds) { | |
645 std::vector<std::string> run_order; | |
646 PostTestTasks(&run_order, "D1 C1 D2 C2"); | |
647 | |
648 scheduler_->DidReceiveInputEventOnCompositorThread( | |
649 FakeInputEvent(blink::WebInputEvent::GestureFlingStart)); | |
650 DoMainFrame(); | |
651 RunUntilIdle(); | |
652 EXPECT_THAT(run_order, | |
653 testing::ElementsAre(std::string("C1"), std::string("C2"), | |
654 std::string("D1"), std::string("D2"))); | |
655 | |
656 run_order.clear(); | |
657 clock_->AdvanceNow(base::TimeDelta::FromMilliseconds(1000)); | |
658 PostTestTasks(&run_order, "D1 C1 D2 C2"); | |
659 | |
660 // Compositor policy mode should have ended now that the clock has advanced. | |
661 RunUntilIdle(); | |
662 EXPECT_THAT(run_order, | |
663 testing::ElementsAre(std::string("D1"), std::string("C1"), | |
664 std::string("D2"), std::string("C2"))); | |
665 } | |
666 | |
667 TEST_F(RendererSchedulerImplTest, TestTouchstartPolicyEndsAfterTimeout) { | |
668 std::vector<std::string> run_order; | |
669 PostTestTasks(&run_order, "L1 D1 C1 D2 C2"); | |
670 | |
671 scheduler_->DidReceiveInputEventOnCompositorThread( | |
672 FakeInputEvent(blink::WebInputEvent::TouchStart)); | |
673 RunUntilIdle(); | |
674 EXPECT_THAT(run_order, | |
675 testing::ElementsAre(std::string("C1"), std::string("C2"), | |
676 std::string("D1"), std::string("D2"))); | |
677 | |
678 run_order.clear(); | |
679 clock_->AdvanceNow(base::TimeDelta::FromMilliseconds(1000)); | |
680 | |
681 // Don't post any compositor tasks to simulate a very long running event | |
682 // handler. | |
683 PostTestTasks(&run_order, "D1 D2"); | |
684 | |
685 // Touchstart policy mode should have ended now that the clock has advanced. | |
686 RunUntilIdle(); | |
687 EXPECT_THAT(run_order, | |
688 testing::ElementsAre(std::string("L1"), std::string("D1"), | |
689 std::string("D2"))); | |
690 } | |
691 | |
692 TEST_F(RendererSchedulerImplTest, | |
693 TestTouchstartPolicyEndsAfterConsecutiveTouchmoves) { | |
694 std::vector<std::string> run_order; | |
695 PostTestTasks(&run_order, "L1 D1 C1 D2 C2"); | |
696 | |
697 // Observation of touchstart should defer execution of idle and loading tasks. | |
698 scheduler_->DidReceiveInputEventOnCompositorThread( | |
699 FakeInputEvent(blink::WebInputEvent::TouchStart)); | |
700 DoMainFrame(); | |
701 RunUntilIdle(); | |
702 EXPECT_THAT(run_order, | |
703 testing::ElementsAre(std::string("C1"), std::string("C2"), | |
704 std::string("D1"), std::string("D2"))); | |
705 | |
706 // Receiving the first touchmove will not affect scheduler priority. | |
707 run_order.clear(); | |
708 scheduler_->DidReceiveInputEventOnCompositorThread( | |
709 FakeInputEvent(blink::WebInputEvent::TouchMove)); | |
710 DoMainFrame(); | |
711 RunUntilIdle(); | |
712 EXPECT_TRUE(run_order.empty()); | |
713 | |
714 // Receiving the second touchmove will kick us back into compositor priority. | |
715 run_order.clear(); | |
716 scheduler_->DidReceiveInputEventOnCompositorThread( | |
717 FakeInputEvent(blink::WebInputEvent::TouchMove)); | |
718 RunUntilIdle(); | |
719 EXPECT_THAT(run_order, testing::ElementsAre(std::string("L1"))); | |
720 } | |
721 | |
722 TEST_F(RendererSchedulerImplTest, TestIsHighPriorityWorkAnticipated) { | |
723 bool is_anticipated_before = false; | |
724 bool is_anticipated_after = false; | |
725 | |
726 bool simulate_input = false; | |
727 default_task_runner_->PostTask( | |
728 FROM_HERE, | |
729 base::Bind(&AnticipationTestTask, scheduler_.get(), simulate_input, | |
730 &is_anticipated_before, &is_anticipated_after)); | |
731 RunUntilIdle(); | |
732 // In its default state, without input receipt, the scheduler should indicate | |
733 // that no high-priority is anticipated. | |
734 EXPECT_FALSE(is_anticipated_before); | |
735 EXPECT_FALSE(is_anticipated_after); | |
736 | |
737 simulate_input = true; | |
738 default_task_runner_->PostTask( | |
739 FROM_HERE, | |
740 base::Bind(&AnticipationTestTask, scheduler_.get(), simulate_input, | |
741 &is_anticipated_before, &is_anticipated_after)); | |
742 RunUntilIdle(); | |
743 // When input is received, the scheduler should indicate that high-priority | |
744 // work is anticipated. | |
745 EXPECT_FALSE(is_anticipated_before); | |
746 EXPECT_TRUE(is_anticipated_after); | |
747 | |
748 clock_->AdvanceNow(priority_escalation_after_input_duration() * 2); | |
749 simulate_input = false; | |
750 default_task_runner_->PostTask( | |
751 FROM_HERE, | |
752 base::Bind(&AnticipationTestTask, scheduler_.get(), simulate_input, | |
753 &is_anticipated_before, &is_anticipated_after)); | |
754 RunUntilIdle(); | |
755 // Without additional input, the scheduler should indicate that high-priority | |
756 // work is no longer anticipated. | |
757 EXPECT_FALSE(is_anticipated_before); | |
758 EXPECT_FALSE(is_anticipated_after); | |
759 } | |
760 | |
761 TEST_F(RendererSchedulerImplTest, TestShouldYield) { | |
762 bool should_yield_before = false; | |
763 bool should_yield_after = false; | |
764 | |
765 default_task_runner_->PostTask( | |
766 FROM_HERE, base::Bind(&PostingYieldingTestTask, scheduler_.get(), | |
767 default_task_runner_, false, &should_yield_before, | |
768 &should_yield_after)); | |
769 RunUntilIdle(); | |
770 // Posting to default runner shouldn't cause yielding. | |
771 EXPECT_FALSE(should_yield_before); | |
772 EXPECT_FALSE(should_yield_after); | |
773 | |
774 default_task_runner_->PostTask( | |
775 FROM_HERE, base::Bind(&PostingYieldingTestTask, scheduler_.get(), | |
776 compositor_task_runner_, false, | |
777 &should_yield_before, &should_yield_after)); | |
778 RunUntilIdle(); | |
779 // Posting while not in compositor priority shouldn't cause yielding. | |
780 EXPECT_FALSE(should_yield_before); | |
781 EXPECT_FALSE(should_yield_after); | |
782 | |
783 default_task_runner_->PostTask( | |
784 FROM_HERE, base::Bind(&PostingYieldingTestTask, scheduler_.get(), | |
785 compositor_task_runner_, true, &should_yield_before, | |
786 &should_yield_after)); | |
787 RunUntilIdle(); | |
788 // We should be able to switch to compositor priority mid-task. | |
789 EXPECT_FALSE(should_yield_before); | |
790 EXPECT_TRUE(should_yield_after); | |
791 | |
792 // Receiving a touchstart should immediately trigger yielding, even if | |
793 // there's no immediately pending work in the compositor queue. | |
794 EXPECT_FALSE(scheduler_->ShouldYieldForHighPriorityWork()); | |
795 scheduler_->DidReceiveInputEventOnCompositorThread( | |
796 FakeInputEvent(blink::WebInputEvent::TouchStart)); | |
797 EXPECT_TRUE(scheduler_->ShouldYieldForHighPriorityWork()); | |
798 RunUntilIdle(); | |
799 } | |
800 | |
801 TEST_F(RendererSchedulerImplTest, SlowInputEvent) { | |
802 EXPECT_EQ(Policy::NORMAL, CurrentPolicy()); | |
803 | |
804 // An input event should bump us into input priority. | |
805 scheduler_->DidReceiveInputEventOnCompositorThread( | |
806 FakeInputEvent(blink::WebInputEvent::GestureFlingStart)); | |
807 RunUntilIdle(); | |
808 EXPECT_EQ(Policy::COMPOSITOR_PRIORITY, CurrentPolicy()); | |
809 | |
810 // Simulate the input event being queued for a very long time. The compositor | |
811 // task we post here represents the enqueued input task. | |
812 clock_->AdvanceNow(priority_escalation_after_input_duration() * 2); | |
813 compositor_task_runner_->PostTask(FROM_HERE, base::Bind(&NullTask)); | |
814 RunUntilIdle(); | |
815 | |
816 // Even though we exceeded the input priority escalation period, we should | |
817 // still be in compositor priority since the input remains queued. | |
818 EXPECT_EQ(Policy::COMPOSITOR_PRIORITY, CurrentPolicy()); | |
819 | |
820 // Simulate the input event triggering a composition. This should start the | |
821 // countdown for going back into normal policy. | |
822 DoMainFrame(); | |
823 RunUntilIdle(); | |
824 EXPECT_EQ(Policy::COMPOSITOR_PRIORITY, CurrentPolicy()); | |
825 | |
826 // After the escalation period ends we should go back into normal mode. | |
827 clock_->AdvanceNow(priority_escalation_after_input_duration() * 2); | |
828 RunUntilIdle(); | |
829 EXPECT_EQ(Policy::NORMAL, CurrentPolicy()); | |
830 } | |
831 | |
832 TEST_F(RendererSchedulerImplTest, SlowNoOpInputEvent) { | |
833 EXPECT_EQ(Policy::NORMAL, CurrentPolicy()); | |
834 | |
835 // An input event should bump us into input priority. | |
836 scheduler_->DidReceiveInputEventOnCompositorThread( | |
837 FakeInputEvent(blink::WebInputEvent::GestureFlingStart)); | |
838 RunUntilIdle(); | |
839 EXPECT_EQ(Policy::COMPOSITOR_PRIORITY, CurrentPolicy()); | |
840 | |
841 // Simulate the input event being queued for a very long time. The compositor | |
842 // task we post here represents the enqueued input task. | |
843 clock_->AdvanceNow(priority_escalation_after_input_duration() * 2); | |
844 compositor_task_runner_->PostTask(FROM_HERE, base::Bind(&NullTask)); | |
845 RunUntilIdle(); | |
846 | |
847 // Even though we exceeded the input priority escalation period, we should | |
848 // still be in compositor priority since the input remains queued. | |
849 EXPECT_EQ(Policy::COMPOSITOR_PRIORITY, CurrentPolicy()); | |
850 | |
851 // If we let the compositor queue drain, we should fall out of input | |
852 // priority. | |
853 clock_->AdvanceNow(priority_escalation_after_input_duration() * 2); | |
854 RunUntilIdle(); | |
855 EXPECT_EQ(Policy::NORMAL, CurrentPolicy()); | |
856 } | |
857 | |
858 TEST_F(RendererSchedulerImplTest, NoOpInputEvent) { | |
859 EXPECT_EQ(Policy::NORMAL, CurrentPolicy()); | |
860 | |
861 // An input event should bump us into input priority. | |
862 scheduler_->DidReceiveInputEventOnCompositorThread( | |
863 FakeInputEvent(blink::WebInputEvent::GestureFlingStart)); | |
864 RunUntilIdle(); | |
865 EXPECT_EQ(Policy::COMPOSITOR_PRIORITY, CurrentPolicy()); | |
866 | |
867 // If nothing else happens after this, we should drop out of compositor | |
868 // priority after the escalation period ends and stop polling. | |
869 clock_->AdvanceNow(priority_escalation_after_input_duration() * 2); | |
870 RunUntilIdle(); | |
871 EXPECT_EQ(Policy::NORMAL, CurrentPolicy()); | |
872 EXPECT_FALSE(mock_task_runner_->HasPendingTasks()); | |
873 } | |
874 | |
875 TEST_F(RendererSchedulerImplTest, NoOpInputEventExtendsEscalationPeriod) { | |
876 EXPECT_EQ(Policy::NORMAL, CurrentPolicy()); | |
877 | |
878 // Simulate one handled input event. | |
879 scheduler_->DidReceiveInputEventOnCompositorThread( | |
880 FakeInputEvent(blink::WebInputEvent::GestureScrollBegin)); | |
881 RunUntilIdle(); | |
882 DoMainFrame(); | |
883 EXPECT_EQ(Policy::COMPOSITOR_PRIORITY, CurrentPolicy()); | |
884 | |
885 // Send a no-op input event in the middle of the escalation period. | |
886 clock_->AdvanceNow(priority_escalation_after_input_duration() / 2); | |
887 scheduler_->DidReceiveInputEventOnCompositorThread( | |
888 FakeInputEvent(blink::WebInputEvent::GestureScrollUpdate)); | |
889 RunUntilIdle(); | |
890 EXPECT_EQ(Policy::COMPOSITOR_PRIORITY, CurrentPolicy()); | |
891 | |
892 // The escalation period should have been extended by the new input event. | |
893 clock_->AdvanceNow(3 * priority_escalation_after_input_duration() / 4); | |
894 RunUntilIdle(); | |
895 EXPECT_EQ(Policy::COMPOSITOR_PRIORITY, CurrentPolicy()); | |
896 | |
897 clock_->AdvanceNow(priority_escalation_after_input_duration() / 2); | |
898 RunUntilIdle(); | |
899 EXPECT_EQ(Policy::NORMAL, CurrentPolicy()); | |
900 } | |
901 | |
902 TEST_F(RendererSchedulerImplTest, InputArrivesAfterBeginFrame) { | |
903 EXPECT_EQ(Policy::NORMAL, CurrentPolicy()); | |
904 | |
905 cc::BeginFrameArgs args = cc::BeginFrameArgs::Create( | |
906 BEGINFRAME_FROM_HERE, clock_->Now(), base::TimeTicks(), | |
907 base::TimeDelta::FromMilliseconds(1000), cc::BeginFrameArgs::NORMAL); | |
908 clock_->AdvanceNow(priority_escalation_after_input_duration() / 2); | |
909 | |
910 scheduler_->DidReceiveInputEventOnCompositorThread( | |
911 FakeInputEvent(blink::WebInputEvent::GestureScrollBegin)); | |
912 | |
913 // Simulate a BeginMainFrame task from the past. | |
914 clock_->AdvanceNow(2 * priority_escalation_after_input_duration()); | |
915 scheduler_->WillBeginFrame(args); | |
916 scheduler_->DidCommitFrameToCompositor(); | |
917 | |
918 // This task represents the queued-up input event. | |
919 compositor_task_runner_->PostTask(FROM_HERE, base::Bind(&NullTask)); | |
920 | |
921 // Should remain in input priority policy since the input event hasn't been | |
922 // processed yet. | |
923 clock_->AdvanceNow(2 * priority_escalation_after_input_duration()); | |
924 RunUntilIdle(); | |
925 EXPECT_EQ(Policy::COMPOSITOR_PRIORITY, CurrentPolicy()); | |
926 | |
927 // Process the input event with a new BeginMainFrame. | |
928 DoMainFrame(); | |
929 clock_->AdvanceNow(2 * priority_escalation_after_input_duration()); | |
930 RunUntilIdle(); | |
931 EXPECT_EQ(Policy::NORMAL, CurrentPolicy()); | |
932 } | |
933 | |
934 class RendererSchedulerImplForTest : public RendererSchedulerImpl { | |
935 public: | |
936 RendererSchedulerImplForTest( | |
937 scoped_refptr<NestableSingleThreadTaskRunner> main_task_runner) | |
938 : RendererSchedulerImpl(main_task_runner), update_policy_count_(0) {} | |
939 | |
940 void UpdatePolicyLocked(UpdateType update_type) override { | |
941 update_policy_count_++; | |
942 RendererSchedulerImpl::UpdatePolicyLocked(update_type); | |
943 } | |
944 | |
945 int update_policy_count_; | |
946 }; | |
947 | |
948 TEST_F(RendererSchedulerImplTest, OnlyOnePendingUrgentPolicyUpdatey) { | |
949 RendererSchedulerImplForTest* mock_scheduler = | |
950 new RendererSchedulerImplForTest(nestable_task_runner_); | |
951 scheduler_.reset(mock_scheduler); | |
952 | |
953 EnsureUrgentPolicyUpdatePostedOnMainThread(); | |
954 EnsureUrgentPolicyUpdatePostedOnMainThread(); | |
955 EnsureUrgentPolicyUpdatePostedOnMainThread(); | |
956 EnsureUrgentPolicyUpdatePostedOnMainThread(); | |
957 | |
958 RunUntilIdle(); | |
959 | |
960 EXPECT_EQ(1, mock_scheduler->update_policy_count_); | |
961 } | |
962 | |
963 TEST_F(RendererSchedulerImplTest, OnePendingDelayedAndOneUrgentUpdatePolicy) { | |
964 RendererSchedulerImplForTest* mock_scheduler = | |
965 new RendererSchedulerImplForTest(nestable_task_runner_); | |
966 scheduler_.reset(mock_scheduler); | |
967 scheduler_->GetSchedulerHelperForTesting()->SetTimeSourceForTesting( | |
968 make_scoped_ptr(new TestTimeSource(clock_))); | |
969 scheduler_->GetSchedulerHelperForTesting() | |
970 ->GetTaskQueueManagerForTesting() | |
971 ->SetTimeSourceForTesting(make_scoped_ptr(new TestTimeSource(clock_))); | |
972 mock_task_runner_->SetAutoAdvanceNowToPendingTasks(true); | |
973 | |
974 ScheduleDelayedPolicyUpdate(base::TimeDelta::FromMilliseconds(1)); | |
975 EnsureUrgentPolicyUpdatePostedOnMainThread(); | |
976 | |
977 RunUntilIdle(); | |
978 | |
979 // We expect both the urgent and the delayed updates to run. | |
980 EXPECT_EQ(2, mock_scheduler->update_policy_count_); | |
981 } | |
982 | |
983 TEST_F(RendererSchedulerImplTest, OneUrgentAndOnePendingDelayedUpdatePolicy) { | |
984 RendererSchedulerImplForTest* mock_scheduler = | |
985 new RendererSchedulerImplForTest(nestable_task_runner_); | |
986 scheduler_.reset(mock_scheduler); | |
987 scheduler_->GetSchedulerHelperForTesting()->SetTimeSourceForTesting( | |
988 make_scoped_ptr(new TestTimeSource(clock_))); | |
989 scheduler_->GetSchedulerHelperForTesting() | |
990 ->GetTaskQueueManagerForTesting() | |
991 ->SetTimeSourceForTesting(make_scoped_ptr(new TestTimeSource(clock_))); | |
992 mock_task_runner_->SetAutoAdvanceNowToPendingTasks(true); | |
993 | |
994 EnsureUrgentPolicyUpdatePostedOnMainThread(); | |
995 ScheduleDelayedPolicyUpdate(base::TimeDelta::FromMilliseconds(1)); | |
996 | |
997 RunUntilIdle(); | |
998 | |
999 // We expect both the urgent and the delayed updates to run. | |
1000 EXPECT_EQ(2, mock_scheduler->update_policy_count_); | |
1001 } | |
1002 | |
1003 TEST_F(RendererSchedulerImplTest, UpdatePolicyCountTriggeredByOneInputEvent) { | |
1004 RendererSchedulerImplForTest* mock_scheduler = | |
1005 new RendererSchedulerImplForTest(nestable_task_runner_); | |
1006 scheduler_.reset(mock_scheduler); | |
1007 scheduler_->GetSchedulerHelperForTesting()->SetTimeSourceForTesting( | |
1008 make_scoped_ptr(new TestTimeSource(clock_))); | |
1009 scheduler_->GetSchedulerHelperForTesting() | |
1010 ->GetTaskQueueManagerForTesting() | |
1011 ->SetTimeSourceForTesting(make_scoped_ptr(new TestTimeSource(clock_))); | |
1012 mock_task_runner_->SetAutoAdvanceNowToPendingTasks(true); | |
1013 | |
1014 scheduler_->DidReceiveInputEventOnCompositorThread( | |
1015 FakeInputEvent(blink::WebInputEvent::TouchStart)); | |
1016 | |
1017 RunUntilIdle(); | |
1018 | |
1019 // We expect an urgent policy update followed by a delayed one 100ms later. | |
1020 EXPECT_EQ(2, mock_scheduler->update_policy_count_); | |
1021 } | |
1022 | |
1023 TEST_F(RendererSchedulerImplTest, UpdatePolicyCountTriggeredByTwoInputEvents) { | |
1024 RendererSchedulerImplForTest* mock_scheduler = | |
1025 new RendererSchedulerImplForTest(nestable_task_runner_); | |
1026 scheduler_.reset(mock_scheduler); | |
1027 scheduler_->GetSchedulerHelperForTesting()->SetTimeSourceForTesting( | |
1028 make_scoped_ptr(new TestTimeSource(clock_))); | |
1029 scheduler_->GetSchedulerHelperForTesting() | |
1030 ->GetTaskQueueManagerForTesting() | |
1031 ->SetTimeSourceForTesting(make_scoped_ptr(new TestTimeSource(clock_))); | |
1032 mock_task_runner_->SetAutoAdvanceNowToPendingTasks(true); | |
1033 | |
1034 scheduler_->DidReceiveInputEventOnCompositorThread( | |
1035 FakeInputEvent(blink::WebInputEvent::TouchStart)); | |
1036 scheduler_->DidReceiveInputEventOnCompositorThread( | |
1037 FakeInputEvent(blink::WebInputEvent::TouchMove)); | |
1038 | |
1039 RunUntilIdle(); | |
1040 | |
1041 // We expect an urgent policy update followed by a delayed one 100ms later. | |
1042 EXPECT_EQ(2, mock_scheduler->update_policy_count_); | |
1043 } | |
1044 | |
1045 TEST_F(RendererSchedulerImplTest, EnsureUpdatePolicyNotTriggeredTooOften) { | |
1046 RendererSchedulerImplForTest* mock_scheduler = | |
1047 new RendererSchedulerImplForTest(nestable_task_runner_); | |
1048 scheduler_.reset(mock_scheduler); | |
1049 scheduler_->GetSchedulerHelperForTesting()->SetTimeSourceForTesting( | |
1050 make_scoped_ptr(new TestTimeSource(clock_))); | |
1051 scheduler_->GetSchedulerHelperForTesting() | |
1052 ->GetTaskQueueManagerForTesting() | |
1053 ->SetTimeSourceForTesting(make_scoped_ptr(new TestTimeSource(clock_))); | |
1054 mock_task_runner_->SetAutoAdvanceNowToPendingTasks(true); | |
1055 | |
1056 scheduler_->DidReceiveInputEventOnCompositorThread( | |
1057 FakeInputEvent(blink::WebInputEvent::TouchStart)); | |
1058 scheduler_->DidReceiveInputEventOnCompositorThread( | |
1059 FakeInputEvent(blink::WebInputEvent::TouchMove)); | |
1060 | |
1061 // We expect the first call to IsHighPriorityWorkAnticipated to be called | |
1062 // after recieving an input event (but before the UpdateTask was processed) to | |
1063 // call UpdatePolicy. | |
1064 EXPECT_EQ(0, mock_scheduler->update_policy_count_); | |
1065 scheduler_->IsHighPriorityWorkAnticipated(); | |
1066 EXPECT_EQ(1, mock_scheduler->update_policy_count_); | |
1067 // Subsequent calls should not call UpdatePolicy. | |
1068 scheduler_->IsHighPriorityWorkAnticipated(); | |
1069 scheduler_->IsHighPriorityWorkAnticipated(); | |
1070 scheduler_->IsHighPriorityWorkAnticipated(); | |
1071 scheduler_->ShouldYieldForHighPriorityWork(); | |
1072 scheduler_->ShouldYieldForHighPriorityWork(); | |
1073 scheduler_->ShouldYieldForHighPriorityWork(); | |
1074 scheduler_->ShouldYieldForHighPriorityWork(); | |
1075 | |
1076 EXPECT_EQ(1, mock_scheduler->update_policy_count_); | |
1077 | |
1078 RunUntilIdle(); | |
1079 // We expect both the urgent and the delayed updates to run in addition to the | |
1080 // earlier updated cause by IsHighPriorityWorkAnticipated. | |
1081 EXPECT_EQ(3, mock_scheduler->update_policy_count_); | |
1082 } | |
1083 | |
1084 class RendererSchedulerImplWithMessageLoopTest | |
1085 : public RendererSchedulerImplTest { | |
1086 public: | |
1087 RendererSchedulerImplWithMessageLoopTest() | |
1088 : RendererSchedulerImplTest(new base::MessageLoop()) {} | |
1089 ~RendererSchedulerImplWithMessageLoopTest() override {} | |
1090 | |
1091 void PostFromNestedRunloop(std::vector< | |
1092 std::pair<SingleThreadIdleTaskRunner::IdleTask, bool>>* tasks) { | |
1093 base::MessageLoop::ScopedNestableTaskAllower allow(message_loop_.get()); | |
1094 for (std::pair<SingleThreadIdleTaskRunner::IdleTask, bool>& pair : *tasks) { | |
1095 if (pair.second) { | |
1096 idle_task_runner_->PostIdleTask(FROM_HERE, pair.first); | |
1097 } else { | |
1098 idle_task_runner_->PostNonNestableIdleTask(FROM_HERE, pair.first); | |
1099 } | |
1100 } | |
1101 EnableIdleTasks(); | |
1102 message_loop_->RunUntilIdle(); | |
1103 } | |
1104 | |
1105 private: | |
1106 DISALLOW_COPY_AND_ASSIGN(RendererSchedulerImplWithMessageLoopTest); | |
1107 }; | |
1108 | |
1109 TEST_F(RendererSchedulerImplWithMessageLoopTest, | |
1110 NonNestableIdleTaskDoesntExecuteInNestedLoop) { | |
1111 std::vector<std::string> order; | |
1112 idle_task_runner_->PostIdleTask( | |
1113 FROM_HERE, | |
1114 base::Bind(&AppendToVectorIdleTestTask, &order, std::string("1"))); | |
1115 idle_task_runner_->PostIdleTask( | |
1116 FROM_HERE, | |
1117 base::Bind(&AppendToVectorIdleTestTask, &order, std::string("2"))); | |
1118 | |
1119 std::vector<std::pair<SingleThreadIdleTaskRunner::IdleTask, bool>> | |
1120 tasks_to_post_from_nested_loop; | |
1121 tasks_to_post_from_nested_loop.push_back(std::make_pair( | |
1122 base::Bind(&AppendToVectorIdleTestTask, &order, std::string("3")), | |
1123 false)); | |
1124 tasks_to_post_from_nested_loop.push_back(std::make_pair( | |
1125 base::Bind(&AppendToVectorIdleTestTask, &order, std::string("4")), true)); | |
1126 tasks_to_post_from_nested_loop.push_back(std::make_pair( | |
1127 base::Bind(&AppendToVectorIdleTestTask, &order, std::string("5")), true)); | |
1128 | |
1129 default_task_runner_->PostTask( | |
1130 FROM_HERE, | |
1131 base::Bind( | |
1132 &RendererSchedulerImplWithMessageLoopTest::PostFromNestedRunloop, | |
1133 base::Unretained(this), | |
1134 base::Unretained(&tasks_to_post_from_nested_loop))); | |
1135 | |
1136 EnableIdleTasks(); | |
1137 RunUntilIdle(); | |
1138 // Note we expect task 3 to run last because it's non-nestable. | |
1139 EXPECT_THAT(order, testing::ElementsAre(std::string("1"), std::string("2"), | |
1140 std::string("4"), std::string("5"), | |
1141 std::string("3"))); | |
1142 } | |
1143 | |
1144 TEST_F(RendererSchedulerImplTest, TestLongIdlePeriod) { | |
1145 base::TimeTicks expected_deadline = | |
1146 clock_->Now() + maximum_idle_period_duration(); | |
1147 base::TimeTicks deadline_in_task; | |
1148 int run_count = 0; | |
1149 | |
1150 idle_task_runner_->PostIdleTask( | |
1151 FROM_HERE, base::Bind(&IdleTestTask, &run_count, &deadline_in_task)); | |
1152 | |
1153 RunUntilIdle(); | |
1154 EXPECT_EQ(0, run_count); // Shouldn't run yet as no idle period. | |
1155 | |
1156 scheduler_->BeginFrameNotExpectedSoon(); | |
1157 RunUntilIdle(); | |
1158 EXPECT_EQ(1, run_count); // Should have run in a long idle time. | |
1159 EXPECT_EQ(expected_deadline, deadline_in_task); | |
1160 } | |
1161 | |
1162 TEST_F(RendererSchedulerImplTest, TestLongIdlePeriodWithPendingDelayedTask) { | |
1163 base::TimeDelta pending_task_delay = base::TimeDelta::FromMilliseconds(30); | |
1164 base::TimeTicks expected_deadline = clock_->Now() + pending_task_delay; | |
1165 base::TimeTicks deadline_in_task; | |
1166 int run_count = 0; | |
1167 | |
1168 idle_task_runner_->PostIdleTask( | |
1169 FROM_HERE, base::Bind(&IdleTestTask, &run_count, &deadline_in_task)); | |
1170 default_task_runner_->PostDelayedTask( | |
1171 FROM_HERE, base::Bind(&NullTask), pending_task_delay); | |
1172 | |
1173 scheduler_->BeginFrameNotExpectedSoon(); | |
1174 RunUntilIdle(); | |
1175 EXPECT_EQ(1, run_count); // Should have run in a long idle time. | |
1176 EXPECT_EQ(expected_deadline, deadline_in_task); | |
1177 } | |
1178 | |
1179 TEST_F(RendererSchedulerImplTest, | |
1180 TestLongIdlePeriodWithLatePendingDelayedTask) { | |
1181 base::TimeDelta pending_task_delay = base::TimeDelta::FromMilliseconds(10); | |
1182 base::TimeTicks deadline_in_task; | |
1183 int run_count = 0; | |
1184 | |
1185 default_task_runner_->PostDelayedTask( | |
1186 FROM_HERE, base::Bind(&NullTask), pending_task_delay); | |
1187 | |
1188 // Advance clock until after delayed task was meant to be run. | |
1189 clock_->AdvanceNow(base::TimeDelta::FromMilliseconds(20)); | |
1190 | |
1191 // Post an idle task and BeginFrameNotExpectedSoon to initiate a long idle | |
1192 // period. Since there is a late pending delayed task this shouldn't actually | |
1193 // start an idle period. | |
1194 idle_task_runner_->PostIdleTask( | |
1195 FROM_HERE, base::Bind(&IdleTestTask, &run_count, &deadline_in_task)); | |
1196 scheduler_->BeginFrameNotExpectedSoon(); | |
1197 RunUntilIdle(); | |
1198 EXPECT_EQ(0, run_count); | |
1199 | |
1200 // After the delayed task has been run we should trigger an idle period. | |
1201 clock_->AdvanceNow(maximum_idle_period_duration()); | |
1202 RunUntilIdle(); | |
1203 EXPECT_EQ(1, run_count); | |
1204 } | |
1205 | |
1206 TEST_F(RendererSchedulerImplTest, TestLongIdlePeriodRepeating) { | |
1207 int run_count = 0; | |
1208 | |
1209 max_idle_task_reposts = 3; | |
1210 idle_task_runner_->PostIdleTask( | |
1211 FROM_HERE, | |
1212 base::Bind(&RepostingIdleTestTask, idle_task_runner_, &run_count)); | |
1213 | |
1214 scheduler_->BeginFrameNotExpectedSoon(); | |
1215 RunUntilIdle(); | |
1216 EXPECT_EQ(1, run_count); // Should only run once per idle period. | |
1217 | |
1218 // Advance time to start of next long idle period and check task reposted task | |
1219 // gets run. | |
1220 clock_->AdvanceNow(maximum_idle_period_duration()); | |
1221 RunUntilIdle(); | |
1222 EXPECT_EQ(2, run_count); | |
1223 | |
1224 // Advance time to start of next long idle period then end idle period with a | |
1225 // new BeginMainFrame and check idle task doesn't run. | |
1226 clock_->AdvanceNow(maximum_idle_period_duration()); | |
1227 scheduler_->WillBeginFrame(cc::BeginFrameArgs::Create( | |
1228 BEGINFRAME_FROM_HERE, clock_->Now(), base::TimeTicks(), | |
1229 base::TimeDelta::FromMilliseconds(1000), cc::BeginFrameArgs::NORMAL)); | |
1230 RunUntilIdle(); | |
1231 EXPECT_EQ(2, run_count); | |
1232 } | |
1233 | |
1234 TEST_F(RendererSchedulerImplTest, TestLongIdlePeriodDoesNotWakeScheduler) { | |
1235 base::TimeTicks deadline_in_task; | |
1236 int run_count = 0; | |
1237 | |
1238 // Start a long idle period and get the time it should end. | |
1239 scheduler_->BeginFrameNotExpectedSoon(); | |
1240 // The scheduler should not run the initiate_next_long_idle_period task if | |
1241 // there are no idle tasks and no other task woke up the scheduler, thus | |
1242 // the idle period deadline shouldn't update at the end of the current long | |
1243 // idle period. | |
1244 base::TimeTicks idle_period_deadline = | |
1245 scheduler_->CurrentIdleTaskDeadlineForTesting(); | |
1246 clock_->AdvanceNow(maximum_idle_period_duration()); | |
1247 RunUntilIdle(); | |
1248 | |
1249 base::TimeTicks new_idle_period_deadline = | |
1250 scheduler_->CurrentIdleTaskDeadlineForTesting(); | |
1251 EXPECT_EQ(idle_period_deadline, new_idle_period_deadline); | |
1252 | |
1253 // Posting a after-wakeup idle task also shouldn't wake the scheduler or | |
1254 // initiate the next long idle period. | |
1255 idle_task_runner_->PostIdleTaskAfterWakeup( | |
1256 FROM_HERE, | |
1257 base::Bind(&IdleTestTask, &run_count, &deadline_in_task)); | |
1258 RunUntilIdle(); | |
1259 new_idle_period_deadline = scheduler_->CurrentIdleTaskDeadlineForTesting(); | |
1260 EXPECT_EQ(idle_period_deadline, new_idle_period_deadline); | |
1261 EXPECT_EQ(0, run_count); | |
1262 | |
1263 // Running a normal task should initiate a new long idle period though. | |
1264 default_task_runner_->PostTask(FROM_HERE, base::Bind(&NullTask)); | |
1265 RunUntilIdle(); | |
1266 new_idle_period_deadline = scheduler_->CurrentIdleTaskDeadlineForTesting(); | |
1267 EXPECT_EQ(idle_period_deadline + maximum_idle_period_duration(), | |
1268 new_idle_period_deadline); | |
1269 | |
1270 EXPECT_EQ(1, run_count); | |
1271 } | |
1272 | |
1273 TEST_F(RendererSchedulerImplTest, TestLongIdlePeriodInTouchStartPolicy) { | |
1274 base::TimeTicks deadline_in_task; | |
1275 int run_count = 0; | |
1276 | |
1277 idle_task_runner_->PostIdleTask( | |
1278 FROM_HERE, | |
1279 base::Bind(&IdleTestTask, &run_count, &deadline_in_task)); | |
1280 | |
1281 // Observation of touchstart should defer the start of the long idle period. | |
1282 scheduler_->DidReceiveInputEventOnCompositorThread( | |
1283 FakeInputEvent(blink::WebInputEvent::TouchStart)); | |
1284 scheduler_->BeginFrameNotExpectedSoon(); | |
1285 RunUntilIdle(); | |
1286 EXPECT_EQ(0, run_count); | |
1287 | |
1288 // The long idle period should start after the touchstart policy has finished. | |
1289 clock_->AdvanceNow(priority_escalation_after_input_duration()); | |
1290 RunUntilIdle(); | |
1291 EXPECT_EQ(1, run_count); | |
1292 } | |
1293 | |
1294 void TestCanExceedIdleDeadlineIfRequiredTask(RendererScheduler* scheduler, | |
1295 bool* can_exceed_idle_deadline_out, | |
1296 int* run_count, | |
1297 base::TimeTicks deadline) { | |
1298 *can_exceed_idle_deadline_out = scheduler->CanExceedIdleDeadlineIfRequired(); | |
1299 (*run_count)++; | |
1300 } | |
1301 | |
1302 TEST_F(RendererSchedulerImplTest, CanExceedIdleDeadlineIfRequired) { | |
1303 int run_count = 0; | |
1304 bool can_exceed_idle_deadline = false; | |
1305 | |
1306 // Should return false if not in an idle period. | |
1307 EXPECT_FALSE(scheduler_->CanExceedIdleDeadlineIfRequired()); | |
1308 | |
1309 // Should return false for short idle periods. | |
1310 idle_task_runner_->PostIdleTask( | |
1311 FROM_HERE, | |
1312 base::Bind(&TestCanExceedIdleDeadlineIfRequiredTask, scheduler_.get(), | |
1313 &can_exceed_idle_deadline, &run_count)); | |
1314 EnableIdleTasks(); | |
1315 RunUntilIdle(); | |
1316 EXPECT_EQ(1, run_count); | |
1317 EXPECT_FALSE(can_exceed_idle_deadline); | |
1318 | |
1319 // Should return false for a long idle period which is shortened due to a | |
1320 // pending delayed task. | |
1321 default_task_runner_->PostDelayedTask(FROM_HERE, base::Bind(&NullTask), | |
1322 base::TimeDelta::FromMilliseconds(10)); | |
1323 idle_task_runner_->PostIdleTask( | |
1324 FROM_HERE, | |
1325 base::Bind(&TestCanExceedIdleDeadlineIfRequiredTask, scheduler_.get(), | |
1326 &can_exceed_idle_deadline, &run_count)); | |
1327 scheduler_->BeginFrameNotExpectedSoon(); | |
1328 RunUntilIdle(); | |
1329 EXPECT_EQ(2, run_count); | |
1330 EXPECT_FALSE(can_exceed_idle_deadline); | |
1331 | |
1332 // Next long idle period will be for the maximum time, so | |
1333 // CanExceedIdleDeadlineIfRequired should return true. | |
1334 clock_->AdvanceNow(maximum_idle_period_duration()); | |
1335 idle_task_runner_->PostIdleTask( | |
1336 FROM_HERE, | |
1337 base::Bind(&TestCanExceedIdleDeadlineIfRequiredTask, scheduler_.get(), | |
1338 &can_exceed_idle_deadline, &run_count)); | |
1339 RunUntilIdle(); | |
1340 EXPECT_EQ(3, run_count); | |
1341 EXPECT_TRUE(can_exceed_idle_deadline); | |
1342 | |
1343 // Next long idle period will be for the maximum time, so | |
1344 // CanExceedIdleDeadlineIfRequired should return true. | |
1345 scheduler_->WillBeginFrame(cc::BeginFrameArgs::Create( | |
1346 BEGINFRAME_FROM_HERE, clock_->Now(), base::TimeTicks(), | |
1347 base::TimeDelta::FromMilliseconds(1000), cc::BeginFrameArgs::NORMAL)); | |
1348 EXPECT_FALSE(scheduler_->CanExceedIdleDeadlineIfRequired()); | |
1349 } | |
1350 | |
1351 TEST_F(RendererSchedulerImplTest, TestRendererHiddenIdlePeriod) { | |
1352 int run_count = 0; | |
1353 | |
1354 idle_task_runner_->PostIdleTask( | |
1355 FROM_HERE, | |
1356 base::Bind(&RepostingIdleTestTask, idle_task_runner_, &run_count)); | |
1357 | |
1358 // Renderer should start in visible state. | |
1359 RunUntilIdle(); | |
1360 EXPECT_EQ(0, run_count); | |
1361 | |
1362 // When we hide the renderer it should start an idle period. | |
1363 scheduler_->OnRendererHidden(); | |
1364 RunUntilIdle(); | |
1365 EXPECT_EQ(1, run_count); | |
1366 | |
1367 // Advance time to start of next long idle period and check task reposted task | |
1368 // gets run. | |
1369 clock_->AdvanceNow(maximum_idle_period_duration()); | |
1370 RunUntilIdle(); | |
1371 EXPECT_EQ(2, run_count); | |
1372 | |
1373 // Advance time by amount of time by the maximum amount of time we execute | |
1374 // idle tasks when hidden (plus some slack) - idle period should have ended. | |
1375 clock_->AdvanceNow(end_idle_when_hidden_delay() + | |
1376 base::TimeDelta::FromMilliseconds(10)); | |
1377 RunUntilIdle(); | |
1378 EXPECT_EQ(2, run_count); | |
1379 } | |
1380 | |
1381 TEST_F(RendererSchedulerImplTest, TimerQueueEnabledByDefault) { | |
1382 std::vector<std::string> run_order; | |
1383 PostTestTasks(&run_order, "T1 T2"); | |
1384 RunUntilIdle(); | |
1385 EXPECT_THAT(run_order, | |
1386 testing::ElementsAre(std::string("T1"), std::string("T2"))); | |
1387 } | |
1388 | |
1389 TEST_F(RendererSchedulerImplTest, SuspendAndResumeTimerQueue) { | |
1390 std::vector<std::string> run_order; | |
1391 PostTestTasks(&run_order, "T1 T2"); | |
1392 | |
1393 scheduler_->SuspendTimerQueue(); | |
1394 RunUntilIdle(); | |
1395 EXPECT_TRUE(run_order.empty()); | |
1396 | |
1397 scheduler_->ResumeTimerQueue(); | |
1398 RunUntilIdle(); | |
1399 EXPECT_THAT(run_order, | |
1400 testing::ElementsAre(std::string("T1"), std::string("T2"))); | |
1401 } | |
1402 | |
1403 TEST_F(RendererSchedulerImplTest, MultipleSuspendsNeedMultipleResumes) { | |
1404 std::vector<std::string> run_order; | |
1405 PostTestTasks(&run_order, "T1 T2"); | |
1406 | |
1407 scheduler_->SuspendTimerQueue(); | |
1408 scheduler_->SuspendTimerQueue(); | |
1409 scheduler_->SuspendTimerQueue(); | |
1410 RunUntilIdle(); | |
1411 EXPECT_TRUE(run_order.empty()); | |
1412 | |
1413 scheduler_->ResumeTimerQueue(); | |
1414 RunUntilIdle(); | |
1415 EXPECT_TRUE(run_order.empty()); | |
1416 | |
1417 scheduler_->ResumeTimerQueue(); | |
1418 RunUntilIdle(); | |
1419 EXPECT_TRUE(run_order.empty()); | |
1420 | |
1421 scheduler_->ResumeTimerQueue(); | |
1422 RunUntilIdle(); | |
1423 EXPECT_THAT(run_order, | |
1424 testing::ElementsAre(std::string("T1"), std::string("T2"))); | |
1425 } | |
1426 | |
1427 } // namespace content | |
OLD | NEW |