Chromium Code Reviews| Index: content/renderer/scheduler/renderer_scheduler_impl_unittest.cc |
| diff --git a/content/renderer/scheduler/renderer_scheduler_impl_unittest.cc b/content/renderer/scheduler/renderer_scheduler_impl_unittest.cc |
| index 4a97a0454749f11708d1fdb98d7f81e2202a5354..5dff1fefe3033252b2d48ad740ca2e320771c2d4 100644 |
| --- a/content/renderer/scheduler/renderer_scheduler_impl_unittest.cc |
| +++ b/content/renderer/scheduler/renderer_scheduler_impl_unittest.cc |
| @@ -56,7 +56,14 @@ class RendererSchedulerImplTest : public testing::Test { |
| } |
| ~RendererSchedulerImplTest() override {} |
| - void RunUntilIdle() { mock_task_runner_->RunUntilIdle(); } |
| + void TearDown() override { |
| + // Check that all tests stop posting tasks. |
| + mock_task_runner_->SetAutoAdvanceNowToPendingTasks(true); |
| + while (RunUntilIdle()) |
| + ; |
|
rmcilroy
2015/03/12 22:09:34
nit - this would be clearer as an empty '{ }' rath
alex clarke (OOO till 29th)
2015/03/13 09:53:03
Done.
|
| + } |
| + |
| + bool RunUntilIdle() { return mock_task_runner_->RunUntilIdle(); } |
| void DoMainFrame() { |
| scheduler_->WillBeginFrame(cc::BeginFrameArgs::Create( |
| @@ -69,6 +76,16 @@ class RendererSchedulerImplTest : public testing::Test { |
| Policy CurrentPolicy() { return scheduler_->current_policy_; } |
| + void EnsureUrgentPolicyUpdatePostedOnMainThread() { |
| + base::AutoLock lock(scheduler_->incoming_signals_lock_); |
| + scheduler_->EnsureUrgentPolicyUpdatePostedOnMainThread(FROM_HERE); |
| + } |
| + |
| + void ScheduleDelayedPolicyUpdate(base::TimeDelta delay) { |
| + scheduler_->delayed_update_policy_runner_.SetDeadline(FROM_HERE, delay, |
| + clock_->Now()); |
| + } |
| + |
| // Helper for posting several tasks of specific types. |task_descriptor| is a |
| // string with space delimited task identifiers. The first letter of each |
| // task identifier specifies the task type: |
| @@ -847,4 +864,132 @@ TEST_F(RendererSchedulerImplTest, InputArrivesAfterBeginFrame) { |
| EXPECT_EQ(Policy::NORMAL, CurrentPolicy()); |
| } |
| +class MockRendererSchedulerImpl : public RendererSchedulerImpl { |
|
rmcilroy
2015/03/12 22:09:34
naming nit - this isn't really a mock, RenderSched
alex clarke (OOO till 29th)
2015/03/13 09:53:03
Done.
|
| + public: |
| + MockRendererSchedulerImpl( |
| + scoped_refptr<base::SingleThreadTaskRunner> main_task_runner) |
| + : RendererSchedulerImpl(main_task_runner), update_policy_count_(0) {} |
| + |
| + void UpdatePolicyLocked() override { |
| + update_policy_count_++; |
| + RendererSchedulerImpl::UpdatePolicyLocked(); |
| + } |
| + |
| + int update_policy_count_; |
| +}; |
| + |
| +TEST_F(RendererSchedulerImplTest, OnlyOnePendingUrgentPolicyUpdatey) { |
| + MockRendererSchedulerImpl* mock_scheduler = |
| + new MockRendererSchedulerImpl(mock_task_runner_); |
| + scheduler_.reset(mock_scheduler); |
| + |
| + EnsureUrgentPolicyUpdatePostedOnMainThread(); |
| + EnsureUrgentPolicyUpdatePostedOnMainThread(); |
| + EnsureUrgentPolicyUpdatePostedOnMainThread(); |
| + EnsureUrgentPolicyUpdatePostedOnMainThread(); |
| + |
| + RunUntilIdle(); |
| + |
| + EXPECT_EQ(1, mock_scheduler->update_policy_count_); |
| +} |
| + |
| +TEST_F(RendererSchedulerImplTest, OnePendingDelayedAndOneUrgentUpdatePolicy) { |
| + MockRendererSchedulerImpl* mock_scheduler = |
| + new MockRendererSchedulerImpl(mock_task_runner_); |
| + scheduler_.reset(mock_scheduler); |
| + scheduler_->SetTimeSourceForTesting(clock_); |
| + mock_task_runner_->SetAutoAdvanceNowToPendingTasks(true); |
| + |
| + ScheduleDelayedPolicyUpdate(base::TimeDelta::FromMilliseconds(1)); |
| + EnsureUrgentPolicyUpdatePostedOnMainThread(); |
| + |
| + RunUntilIdle(); |
| + |
| + // We expect both the urgent and the delayed updates to run. |
| + EXPECT_EQ(2, mock_scheduler->update_policy_count_); |
| +} |
| + |
| +TEST_F(RendererSchedulerImplTest, OneUrgentAndOnePendingDelayedUpdatePolicy) { |
| + MockRendererSchedulerImpl* mock_scheduler = |
| + new MockRendererSchedulerImpl(mock_task_runner_); |
| + scheduler_.reset(mock_scheduler); |
| + scheduler_->SetTimeSourceForTesting(clock_); |
| + mock_task_runner_->SetAutoAdvanceNowToPendingTasks(true); |
| + |
| + EnsureUrgentPolicyUpdatePostedOnMainThread(); |
| + ScheduleDelayedPolicyUpdate(base::TimeDelta::FromMilliseconds(1)); |
| + |
| + RunUntilIdle(); |
| + |
| + // We expect both the urgent and the delayed updates to run. |
| + EXPECT_EQ(2, mock_scheduler->update_policy_count_); |
| +} |
| + |
| +TEST_F(RendererSchedulerImplTest, UpdatePolicyCountTriggeredByOneInputEvent) { |
| + MockRendererSchedulerImpl* mock_scheduler = |
| + new MockRendererSchedulerImpl(mock_task_runner_); |
| + scheduler_.reset(mock_scheduler); |
| + scheduler_->SetTimeSourceForTesting(clock_); |
| + mock_task_runner_->SetAutoAdvanceNowToPendingTasks(true); |
| + |
| + scheduler_->DidReceiveInputEventOnCompositorThread( |
| + FakeInputEvent(blink::WebInputEvent::TouchStart)); |
| + |
| + RunUntilIdle(); |
| + |
| + EXPECT_EQ(2, mock_scheduler->update_policy_count_); |
| +} |
| + |
| +TEST_F(RendererSchedulerImplTest, UpdatePolicyCountTriggeredByTwoInputEvents) { |
| + MockRendererSchedulerImpl* mock_scheduler = |
| + new MockRendererSchedulerImpl(mock_task_runner_); |
| + scheduler_.reset(mock_scheduler); |
| + scheduler_->SetTimeSourceForTesting(clock_); |
| + mock_task_runner_->SetAutoAdvanceNowToPendingTasks(true); |
| + |
| + scheduler_->DidReceiveInputEventOnCompositorThread( |
| + FakeInputEvent(blink::WebInputEvent::TouchStart)); |
| + scheduler_->DidReceiveInputEventOnCompositorThread( |
| + FakeInputEvent(blink::WebInputEvent::TouchMove)); |
| + |
| + RunUntilIdle(); |
| + |
| + EXPECT_EQ(2, mock_scheduler->update_policy_count_); |
| +} |
| + |
| +TEST_F(RendererSchedulerImplTest, EnsureUpdatePolicyNotTriggeredTooOften) { |
| + MockRendererSchedulerImpl* mock_scheduler = |
| + new MockRendererSchedulerImpl(mock_task_runner_); |
| + scheduler_.reset(mock_scheduler); |
| + scheduler_->SetTimeSourceForTesting(clock_); |
| + mock_task_runner_->SetAutoAdvanceNowToPendingTasks(true); |
| + |
| + scheduler_->DidReceiveInputEventOnCompositorThread( |
| + FakeInputEvent(blink::WebInputEvent::TouchStart)); |
| + scheduler_->DidReceiveInputEventOnCompositorThread( |
| + FakeInputEvent(blink::WebInputEvent::TouchMove)); |
| + |
| + // We expect the first call to IsHighPriorityWorkAnticipated to be called |
| + // after recieving an input event (but before the UpdateTask was processed) to |
| + // call UpdatePolicy. |
| + EXPECT_EQ(0, mock_scheduler->update_policy_count_); |
| + scheduler_->IsHighPriorityWorkAnticipated(); |
| + EXPECT_EQ(1, mock_scheduler->update_policy_count_); |
| + // Subsequent calls should not call UpdatePolicy. |
| + scheduler_->IsHighPriorityWorkAnticipated(); |
| + scheduler_->IsHighPriorityWorkAnticipated(); |
| + scheduler_->IsHighPriorityWorkAnticipated(); |
| + scheduler_->ShouldYieldForHighPriorityWork(); |
| + scheduler_->ShouldYieldForHighPriorityWork(); |
| + scheduler_->ShouldYieldForHighPriorityWork(); |
| + scheduler_->ShouldYieldForHighPriorityWork(); |
| + |
| + EXPECT_EQ(1, mock_scheduler->update_policy_count_); |
| + |
| + RunUntilIdle(); |
| + // We expect both the urgent and the delayed updates to run in addition to the |
| + // earlier updated cause by IsHighPriorityWorkAnticipated. |
| + EXPECT_EQ(3, mock_scheduler->update_policy_count_); |
| +} |
|
rmcilroy
2015/03/12 22:09:34
Nice tests, thanks!
alex clarke (OOO till 29th)
2015/03/13 09:53:03
Acknowledged.
|
| + |
| } // namespace content |