| 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 "components/scheduler/base/task_queue_manager.h" | |
| 6 | |
| 7 #include "base/location.h" | |
| 8 #include "base/run_loop.h" | |
| 9 #include "base/single_thread_task_runner.h" | |
| 10 #include "base/test/simple_test_tick_clock.h" | |
| 11 #include "base/threading/thread.h" | |
| 12 #include "cc/test/ordered_simple_task_runner.h" | |
| 13 #include "components/scheduler/base/nestable_task_runner_for_test.h" | |
| 14 #include "components/scheduler/base/task_queue_impl.h" | |
| 15 #include "components/scheduler/base/task_queue_selector.h" | |
| 16 #include "components/scheduler/base/task_queue_sets.h" | |
| 17 #include "components/scheduler/base/test_always_fail_time_source.h" | |
| 18 #include "components/scheduler/base/test_time_source.h" | |
| 19 #include "testing/gmock/include/gmock/gmock.h" | |
| 20 | |
| 21 using testing::ElementsAre; | |
| 22 using testing::_; | |
| 23 | |
| 24 namespace scheduler { | |
| 25 | |
| 26 class MessageLoopTaskRunner : public NestableTaskRunnerForTest { | |
| 27 public: | |
| 28 static scoped_refptr<MessageLoopTaskRunner> Create() { | |
| 29 return make_scoped_refptr(new MessageLoopTaskRunner()); | |
| 30 } | |
| 31 | |
| 32 // NestableTaskRunner implementation. | |
| 33 bool IsNested() const override { | |
| 34 return base::MessageLoop::current()->IsNested(); | |
| 35 } | |
| 36 | |
| 37 private: | |
| 38 MessageLoopTaskRunner() | |
| 39 : NestableTaskRunnerForTest(base::MessageLoop::current()->task_runner()) { | |
| 40 } | |
| 41 ~MessageLoopTaskRunner() override {} | |
| 42 }; | |
| 43 | |
| 44 class TaskQueueManagerTest : public testing::Test { | |
| 45 public: | |
| 46 void DeleteTaskQueueManager() { manager_.reset(); } | |
| 47 | |
| 48 protected: | |
| 49 void Initialize(size_t num_queues) { | |
| 50 now_src_.reset(new base::SimpleTestTickClock()); | |
| 51 now_src_->Advance(base::TimeDelta::FromMicroseconds(1000)); | |
| 52 test_task_runner_ = make_scoped_refptr( | |
| 53 new cc::OrderedSimpleTaskRunner(now_src_.get(), false)); | |
| 54 main_task_runner_ = | |
| 55 NestableTaskRunnerForTest::Create(test_task_runner_.get()); | |
| 56 manager_ = make_scoped_ptr(new TaskQueueManager( | |
| 57 main_task_runner_, "test.scheduler", "test.scheduler.debug")); | |
| 58 manager_->SetTimeSourceForTesting( | |
| 59 make_scoped_ptr(new TestTimeSource(now_src_.get()))); | |
| 60 | |
| 61 for (size_t i = 0; i < num_queues; i++) | |
| 62 runners_.push_back(manager_->NewTaskQueue(TaskQueue::Spec("test_queue"))); | |
| 63 } | |
| 64 | |
| 65 void InitializeWithRealMessageLoop(size_t num_queues) { | |
| 66 message_loop_.reset(new base::MessageLoop()); | |
| 67 manager_ = make_scoped_ptr( | |
| 68 new TaskQueueManager(MessageLoopTaskRunner::Create(), "test.scheduler", | |
| 69 "test.scheduler.debug")); | |
| 70 | |
| 71 for (size_t i = 0; i < num_queues; i++) | |
| 72 runners_.push_back(manager_->NewTaskQueue(TaskQueue::Spec("test_queue"))); | |
| 73 } | |
| 74 | |
| 75 scoped_ptr<base::MessageLoop> message_loop_; | |
| 76 scoped_ptr<base::SimpleTestTickClock> now_src_; | |
| 77 scoped_refptr<NestableTaskRunnerForTest> main_task_runner_; | |
| 78 scoped_refptr<cc::OrderedSimpleTaskRunner> test_task_runner_; | |
| 79 scoped_ptr<TaskQueueManager> manager_; | |
| 80 std::vector<scoped_refptr<internal::TaskQueueImpl>> runners_; | |
| 81 }; | |
| 82 | |
| 83 void PostFromNestedRunloop(base::MessageLoop* message_loop, | |
| 84 base::SingleThreadTaskRunner* runner, | |
| 85 std::vector<std::pair<base::Closure, bool>>* tasks) { | |
| 86 base::MessageLoop::ScopedNestableTaskAllower allow(message_loop); | |
| 87 for (std::pair<base::Closure, bool>& pair : *tasks) { | |
| 88 if (pair.second) { | |
| 89 runner->PostTask(FROM_HERE, pair.first); | |
| 90 } else { | |
| 91 runner->PostNonNestableTask(FROM_HERE, pair.first); | |
| 92 } | |
| 93 } | |
| 94 message_loop->RunUntilIdle(); | |
| 95 } | |
| 96 | |
| 97 void NullTask() {} | |
| 98 | |
| 99 void TestTask(int value, std::vector<int>* out_result) { | |
| 100 out_result->push_back(value); | |
| 101 } | |
| 102 | |
| 103 TEST_F(TaskQueueManagerTest, SingleQueuePosting) { | |
| 104 Initialize(1u); | |
| 105 | |
| 106 std::vector<int> run_order; | |
| 107 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 108 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 109 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order)); | |
| 110 | |
| 111 test_task_runner_->RunUntilIdle(); | |
| 112 EXPECT_THAT(run_order, ElementsAre(1, 2, 3)); | |
| 113 } | |
| 114 | |
| 115 TEST_F(TaskQueueManagerTest, MultiQueuePosting) { | |
| 116 Initialize(3u); | |
| 117 | |
| 118 std::vector<int> run_order; | |
| 119 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 120 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 121 runners_[1]->PostTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order)); | |
| 122 runners_[1]->PostTask(FROM_HERE, base::Bind(&TestTask, 4, &run_order)); | |
| 123 runners_[2]->PostTask(FROM_HERE, base::Bind(&TestTask, 5, &run_order)); | |
| 124 runners_[2]->PostTask(FROM_HERE, base::Bind(&TestTask, 6, &run_order)); | |
| 125 | |
| 126 test_task_runner_->RunUntilIdle(); | |
| 127 EXPECT_THAT(run_order, ElementsAre(1, 2, 3, 4, 5, 6)); | |
| 128 } | |
| 129 | |
| 130 void NopTask() {} | |
| 131 | |
| 132 TEST_F(TaskQueueManagerTest, NowNotCalledWhenThereAreNoDelayedTasks) { | |
| 133 Initialize(3u); | |
| 134 | |
| 135 manager_->SetTimeSourceForTesting( | |
| 136 make_scoped_ptr(new TestAlwaysFailTimeSource())); | |
| 137 | |
| 138 runners_[0]->PostTask(FROM_HERE, base::Bind(&NopTask)); | |
| 139 runners_[0]->PostTask(FROM_HERE, base::Bind(&NopTask)); | |
| 140 runners_[1]->PostTask(FROM_HERE, base::Bind(&NopTask)); | |
| 141 runners_[1]->PostTask(FROM_HERE, base::Bind(&NopTask)); | |
| 142 runners_[2]->PostTask(FROM_HERE, base::Bind(&NopTask)); | |
| 143 runners_[2]->PostTask(FROM_HERE, base::Bind(&NopTask)); | |
| 144 | |
| 145 test_task_runner_->RunUntilIdle(); | |
| 146 } | |
| 147 | |
| 148 TEST_F(TaskQueueManagerTest, NonNestableTaskPosting) { | |
| 149 InitializeWithRealMessageLoop(1u); | |
| 150 | |
| 151 std::vector<int> run_order; | |
| 152 runners_[0]->PostNonNestableTask(FROM_HERE, | |
| 153 base::Bind(&TestTask, 1, &run_order)); | |
| 154 | |
| 155 message_loop_->RunUntilIdle(); | |
| 156 EXPECT_THAT(run_order, ElementsAre(1)); | |
| 157 } | |
| 158 | |
| 159 TEST_F(TaskQueueManagerTest, NonNestableTaskExecutesInExpectedOrder) { | |
| 160 InitializeWithRealMessageLoop(1u); | |
| 161 | |
| 162 std::vector<int> run_order; | |
| 163 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 164 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 165 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order)); | |
| 166 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 4, &run_order)); | |
| 167 runners_[0]->PostNonNestableTask(FROM_HERE, | |
| 168 base::Bind(&TestTask, 5, &run_order)); | |
| 169 | |
| 170 message_loop_->RunUntilIdle(); | |
| 171 EXPECT_THAT(run_order, ElementsAre(1, 2, 3, 4, 5)); | |
| 172 } | |
| 173 | |
| 174 TEST_F(TaskQueueManagerTest, NonNestableTaskDoesntExecuteInNestedLoop) { | |
| 175 InitializeWithRealMessageLoop(1u); | |
| 176 | |
| 177 std::vector<int> run_order; | |
| 178 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 179 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 180 | |
| 181 std::vector<std::pair<base::Closure, bool>> tasks_to_post_from_nested_loop; | |
| 182 tasks_to_post_from_nested_loop.push_back( | |
| 183 std::make_pair(base::Bind(&TestTask, 3, &run_order), false)); | |
| 184 tasks_to_post_from_nested_loop.push_back( | |
| 185 std::make_pair(base::Bind(&TestTask, 4, &run_order), true)); | |
| 186 tasks_to_post_from_nested_loop.push_back( | |
| 187 std::make_pair(base::Bind(&TestTask, 5, &run_order), true)); | |
| 188 | |
| 189 runners_[0]->PostTask( | |
| 190 FROM_HERE, | |
| 191 base::Bind(&PostFromNestedRunloop, message_loop_.get(), runners_[0], | |
| 192 base::Unretained(&tasks_to_post_from_nested_loop))); | |
| 193 | |
| 194 message_loop_->RunUntilIdle(); | |
| 195 // Note we expect task 3 to run last because it's non-nestable. | |
| 196 EXPECT_THAT(run_order, ElementsAre(1, 2, 4, 5, 3)); | |
| 197 } | |
| 198 | |
| 199 TEST_F(TaskQueueManagerTest, QueuePolling) { | |
| 200 Initialize(1u); | |
| 201 | |
| 202 std::vector<int> run_order; | |
| 203 EXPECT_TRUE(runners_[0]->IsQueueEmpty()); | |
| 204 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 205 EXPECT_FALSE(runners_[0]->IsQueueEmpty()); | |
| 206 | |
| 207 test_task_runner_->RunUntilIdle(); | |
| 208 EXPECT_TRUE(runners_[0]->IsQueueEmpty()); | |
| 209 } | |
| 210 | |
| 211 TEST_F(TaskQueueManagerTest, DelayedTaskPosting) { | |
| 212 Initialize(1u); | |
| 213 | |
| 214 std::vector<int> run_order; | |
| 215 base::TimeDelta delay(base::TimeDelta::FromMilliseconds(10)); | |
| 216 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order), | |
| 217 delay); | |
| 218 EXPECT_EQ(delay, test_task_runner_->DelayToNextTaskTime()); | |
| 219 EXPECT_TRUE(runners_[0]->IsQueueEmpty()); | |
| 220 EXPECT_TRUE(run_order.empty()); | |
| 221 | |
| 222 // The task doesn't run before the delay has completed. | |
| 223 test_task_runner_->RunForPeriod(base::TimeDelta::FromMilliseconds(9)); | |
| 224 EXPECT_TRUE(run_order.empty()); | |
| 225 | |
| 226 // After the delay has completed, the task runs normally. | |
| 227 test_task_runner_->RunForPeriod(base::TimeDelta::FromMilliseconds(1)); | |
| 228 EXPECT_THAT(run_order, ElementsAre(1)); | |
| 229 } | |
| 230 | |
| 231 bool MessageLoopTaskCounter(size_t* count) { | |
| 232 *count = *count + 1; | |
| 233 return true; | |
| 234 } | |
| 235 | |
| 236 TEST_F(TaskQueueManagerTest, DelayedTaskExecutedInOneMessageLoopTask) { | |
| 237 Initialize(1u); | |
| 238 | |
| 239 base::TimeDelta delay(base::TimeDelta::FromMilliseconds(10)); | |
| 240 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&NopTask), delay); | |
| 241 | |
| 242 size_t task_count = 0; | |
| 243 test_task_runner_->RunTasksWhile( | |
| 244 base::Bind(&MessageLoopTaskCounter, &task_count)); | |
| 245 EXPECT_EQ(1u, task_count); | |
| 246 } | |
| 247 | |
| 248 TEST_F(TaskQueueManagerTest, DelayedTaskPosting_MultipleTasks_DecendingOrder) { | |
| 249 Initialize(1u); | |
| 250 | |
| 251 std::vector<int> run_order; | |
| 252 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order), | |
| 253 base::TimeDelta::FromMilliseconds(10)); | |
| 254 | |
| 255 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order), | |
| 256 base::TimeDelta::FromMilliseconds(8)); | |
| 257 | |
| 258 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order), | |
| 259 base::TimeDelta::FromMilliseconds(5)); | |
| 260 | |
| 261 EXPECT_EQ(base::TimeDelta::FromMilliseconds(5), | |
| 262 test_task_runner_->DelayToNextTaskTime()); | |
| 263 | |
| 264 test_task_runner_->RunForPeriod(base::TimeDelta::FromMilliseconds(5)); | |
| 265 EXPECT_THAT(run_order, ElementsAre(3)); | |
| 266 EXPECT_EQ(base::TimeDelta::FromMilliseconds(3), | |
| 267 test_task_runner_->DelayToNextTaskTime()); | |
| 268 | |
| 269 test_task_runner_->RunForPeriod(base::TimeDelta::FromMilliseconds(3)); | |
| 270 EXPECT_THAT(run_order, ElementsAre(3, 2)); | |
| 271 EXPECT_EQ(base::TimeDelta::FromMilliseconds(2), | |
| 272 test_task_runner_->DelayToNextTaskTime()); | |
| 273 | |
| 274 test_task_runner_->RunForPeriod(base::TimeDelta::FromMilliseconds(2)); | |
| 275 EXPECT_THAT(run_order, ElementsAre(3, 2, 1)); | |
| 276 } | |
| 277 | |
| 278 TEST_F(TaskQueueManagerTest, DelayedTaskPosting_MultipleTasks_AscendingOrder) { | |
| 279 Initialize(1u); | |
| 280 | |
| 281 std::vector<int> run_order; | |
| 282 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order), | |
| 283 base::TimeDelta::FromMilliseconds(1)); | |
| 284 | |
| 285 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order), | |
| 286 base::TimeDelta::FromMilliseconds(5)); | |
| 287 | |
| 288 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order), | |
| 289 base::TimeDelta::FromMilliseconds(10)); | |
| 290 | |
| 291 EXPECT_EQ(base::TimeDelta::FromMilliseconds(1), | |
| 292 test_task_runner_->DelayToNextTaskTime()); | |
| 293 | |
| 294 test_task_runner_->RunForPeriod(base::TimeDelta::FromMilliseconds(1)); | |
| 295 EXPECT_THAT(run_order, ElementsAre(1)); | |
| 296 EXPECT_EQ(base::TimeDelta::FromMilliseconds(4), | |
| 297 test_task_runner_->DelayToNextTaskTime()); | |
| 298 | |
| 299 test_task_runner_->RunForPeriod(base::TimeDelta::FromMilliseconds(4)); | |
| 300 EXPECT_THAT(run_order, ElementsAre(1, 2)); | |
| 301 EXPECT_EQ(base::TimeDelta::FromMilliseconds(5), | |
| 302 test_task_runner_->DelayToNextTaskTime()); | |
| 303 | |
| 304 test_task_runner_->RunForPeriod(base::TimeDelta::FromMilliseconds(5)); | |
| 305 EXPECT_THAT(run_order, ElementsAre(1, 2, 3)); | |
| 306 } | |
| 307 | |
| 308 TEST_F(TaskQueueManagerTest, PostDelayedTask_SharesUnderlyingDelayedTasks) { | |
| 309 Initialize(1u); | |
| 310 | |
| 311 std::vector<int> run_order; | |
| 312 base::TimeDelta delay(base::TimeDelta::FromMilliseconds(10)); | |
| 313 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order), | |
| 314 delay); | |
| 315 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order), | |
| 316 delay); | |
| 317 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order), | |
| 318 delay); | |
| 319 | |
| 320 EXPECT_EQ(1u, test_task_runner_->NumPendingTasks()); | |
| 321 } | |
| 322 | |
| 323 class TestObject { | |
| 324 public: | |
| 325 ~TestObject() { destructor_count_++; } | |
| 326 | |
| 327 void Run() { FAIL() << "TestObject::Run should not be called"; } | |
| 328 | |
| 329 static int destructor_count_; | |
| 330 }; | |
| 331 | |
| 332 int TestObject::destructor_count_ = 0; | |
| 333 | |
| 334 TEST_F(TaskQueueManagerTest, PendingDelayedTasksRemovedOnShutdown) { | |
| 335 Initialize(1u); | |
| 336 | |
| 337 TestObject::destructor_count_ = 0; | |
| 338 | |
| 339 base::TimeDelta delay(base::TimeDelta::FromMilliseconds(10)); | |
| 340 runners_[0]->PostDelayedTask( | |
| 341 FROM_HERE, base::Bind(&TestObject::Run, base::Owned(new TestObject())), | |
| 342 delay); | |
| 343 runners_[0]->PostTask( | |
| 344 FROM_HERE, base::Bind(&TestObject::Run, base::Owned(new TestObject()))); | |
| 345 | |
| 346 manager_.reset(); | |
| 347 | |
| 348 EXPECT_EQ(2, TestObject::destructor_count_); | |
| 349 } | |
| 350 | |
| 351 TEST_F(TaskQueueManagerTest, ManualPumping) { | |
| 352 Initialize(1u); | |
| 353 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::MANUAL); | |
| 354 | |
| 355 std::vector<int> run_order; | |
| 356 // Posting a task when pumping is disabled doesn't result in work getting | |
| 357 // posted. | |
| 358 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 359 EXPECT_FALSE(test_task_runner_->HasPendingTasks()); | |
| 360 | |
| 361 // However polling still works. | |
| 362 EXPECT_FALSE(runners_[0]->IsQueueEmpty()); | |
| 363 | |
| 364 // After pumping the task runs normally. | |
| 365 runners_[0]->PumpQueue(); | |
| 366 EXPECT_TRUE(test_task_runner_->HasPendingTasks()); | |
| 367 test_task_runner_->RunUntilIdle(); | |
| 368 EXPECT_THAT(run_order, ElementsAre(1)); | |
| 369 } | |
| 370 | |
| 371 TEST_F(TaskQueueManagerTest, ManualPumpingToggle) { | |
| 372 Initialize(1u); | |
| 373 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::MANUAL); | |
| 374 | |
| 375 std::vector<int> run_order; | |
| 376 // Posting a task when pumping is disabled doesn't result in work getting | |
| 377 // posted. | |
| 378 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 379 EXPECT_FALSE(test_task_runner_->HasPendingTasks()); | |
| 380 | |
| 381 // When pumping is enabled the task runs normally. | |
| 382 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::AUTO); | |
| 383 EXPECT_TRUE(test_task_runner_->HasPendingTasks()); | |
| 384 test_task_runner_->RunUntilIdle(); | |
| 385 EXPECT_THAT(run_order, ElementsAre(1)); | |
| 386 } | |
| 387 | |
| 388 TEST_F(TaskQueueManagerTest, DenyRunning_BeforePosting) { | |
| 389 Initialize(1u); | |
| 390 | |
| 391 std::vector<int> run_order; | |
| 392 runners_[0]->SetQueuePriority(TaskQueue::DISABLED_PRIORITY); | |
| 393 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 394 | |
| 395 test_task_runner_->RunUntilIdle(); | |
| 396 EXPECT_TRUE(run_order.empty()); | |
| 397 | |
| 398 runners_[0]->SetQueuePriority(TaskQueue::NORMAL_PRIORITY); | |
| 399 test_task_runner_->RunUntilIdle(); | |
| 400 EXPECT_THAT(run_order, ElementsAre(1)); | |
| 401 } | |
| 402 | |
| 403 TEST_F(TaskQueueManagerTest, DenyRunning_AfterPosting) { | |
| 404 Initialize(1u); | |
| 405 | |
| 406 std::vector<int> run_order; | |
| 407 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 408 runners_[0]->SetQueuePriority(TaskQueue::DISABLED_PRIORITY); | |
| 409 | |
| 410 test_task_runner_->RunUntilIdle(); | |
| 411 EXPECT_TRUE(run_order.empty()); | |
| 412 | |
| 413 runners_[0]->SetQueuePriority(TaskQueue::NORMAL_PRIORITY); | |
| 414 test_task_runner_->RunUntilIdle(); | |
| 415 EXPECT_THAT(run_order, ElementsAre(1)); | |
| 416 } | |
| 417 | |
| 418 TEST_F(TaskQueueManagerTest, DenyRunning_ManuallyPumpedTransitionsToAuto) { | |
| 419 Initialize(1u); | |
| 420 | |
| 421 std::vector<int> run_order; | |
| 422 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::MANUAL); | |
| 423 runners_[0]->SetQueuePriority(TaskQueue::DISABLED_PRIORITY); | |
| 424 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 425 | |
| 426 test_task_runner_->RunUntilIdle(); | |
| 427 EXPECT_TRUE(run_order.empty()); | |
| 428 | |
| 429 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::AUTO); | |
| 430 runners_[0]->SetQueuePriority(TaskQueue::NORMAL_PRIORITY); | |
| 431 test_task_runner_->RunUntilIdle(); | |
| 432 EXPECT_THAT(run_order, ElementsAre(1)); | |
| 433 } | |
| 434 | |
| 435 TEST_F(TaskQueueManagerTest, ManualPumpingWithDelayedTask) { | |
| 436 Initialize(1u); | |
| 437 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::MANUAL); | |
| 438 | |
| 439 std::vector<int> run_order; | |
| 440 // Posting a delayed task when pumping will apply the delay, but won't cause | |
| 441 // work to executed afterwards. | |
| 442 base::TimeDelta delay(base::TimeDelta::FromMilliseconds(10)); | |
| 443 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order), | |
| 444 delay); | |
| 445 | |
| 446 // After pumping but before the delay period has expired, task does not run. | |
| 447 runners_[0]->PumpQueue(); | |
| 448 test_task_runner_->RunForPeriod(base::TimeDelta::FromMilliseconds(5)); | |
| 449 EXPECT_TRUE(run_order.empty()); | |
| 450 | |
| 451 // Once the delay has expired, pumping causes the task to run. | |
| 452 now_src_->Advance(base::TimeDelta::FromMilliseconds(5)); | |
| 453 runners_[0]->PumpQueue(); | |
| 454 EXPECT_TRUE(test_task_runner_->HasPendingTasks()); | |
| 455 test_task_runner_->RunPendingTasks(); | |
| 456 EXPECT_THAT(run_order, ElementsAre(1)); | |
| 457 } | |
| 458 | |
| 459 TEST_F(TaskQueueManagerTest, ManualPumpingWithMultipleDelayedTasks) { | |
| 460 Initialize(1u); | |
| 461 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::MANUAL); | |
| 462 | |
| 463 std::vector<int> run_order; | |
| 464 // Posting a delayed task when pumping will apply the delay, but won't cause | |
| 465 // work to executed afterwards. | |
| 466 base::TimeDelta delay1(base::TimeDelta::FromMilliseconds(1)); | |
| 467 base::TimeDelta delay2(base::TimeDelta::FromMilliseconds(10)); | |
| 468 base::TimeDelta delay3(base::TimeDelta::FromMilliseconds(20)); | |
| 469 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order), | |
| 470 delay1); | |
| 471 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order), | |
| 472 delay2); | |
| 473 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order), | |
| 474 delay3); | |
| 475 | |
| 476 now_src_->Advance(base::TimeDelta::FromMilliseconds(15)); | |
| 477 test_task_runner_->RunUntilIdle(); | |
| 478 EXPECT_TRUE(run_order.empty()); | |
| 479 | |
| 480 // Once the delay has expired, pumping causes the task to run. | |
| 481 runners_[0]->PumpQueue(); | |
| 482 test_task_runner_->RunUntilIdle(); | |
| 483 EXPECT_THAT(run_order, ElementsAre(1, 2)); | |
| 484 } | |
| 485 | |
| 486 TEST_F(TaskQueueManagerTest, DelayedTasksDontAutoRunWithManualPumping) { | |
| 487 Initialize(1u); | |
| 488 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::MANUAL); | |
| 489 | |
| 490 std::vector<int> run_order; | |
| 491 base::TimeDelta delay(base::TimeDelta::FromMilliseconds(10)); | |
| 492 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order), | |
| 493 delay); | |
| 494 | |
| 495 test_task_runner_->RunForPeriod(base::TimeDelta::FromMilliseconds(10)); | |
| 496 EXPECT_TRUE(run_order.empty()); | |
| 497 } | |
| 498 | |
| 499 TEST_F(TaskQueueManagerTest, ManualPumpingWithNonEmptyWorkQueue) { | |
| 500 Initialize(1u); | |
| 501 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::MANUAL); | |
| 502 | |
| 503 std::vector<int> run_order; | |
| 504 // Posting two tasks and pumping twice should result in two tasks in the work | |
| 505 // queue. | |
| 506 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 507 runners_[0]->PumpQueue(); | |
| 508 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 509 runners_[0]->PumpQueue(); | |
| 510 | |
| 511 EXPECT_EQ(2u, runners_[0]->WorkQueueSizeForTest()); | |
| 512 } | |
| 513 | |
| 514 void ReentrantTestTask(scoped_refptr<base::SingleThreadTaskRunner> runner, | |
| 515 int countdown, | |
| 516 std::vector<int>* out_result) { | |
| 517 out_result->push_back(countdown); | |
| 518 if (--countdown) { | |
| 519 runner->PostTask(FROM_HERE, | |
| 520 Bind(&ReentrantTestTask, runner, countdown, out_result)); | |
| 521 } | |
| 522 } | |
| 523 | |
| 524 TEST_F(TaskQueueManagerTest, ReentrantPosting) { | |
| 525 Initialize(1u); | |
| 526 | |
| 527 std::vector<int> run_order; | |
| 528 runners_[0]->PostTask(FROM_HERE, | |
| 529 Bind(&ReentrantTestTask, runners_[0], 3, &run_order)); | |
| 530 | |
| 531 test_task_runner_->RunUntilIdle(); | |
| 532 EXPECT_THAT(run_order, ElementsAre(3, 2, 1)); | |
| 533 } | |
| 534 | |
| 535 TEST_F(TaskQueueManagerTest, NoTasksAfterShutdown) { | |
| 536 Initialize(1u); | |
| 537 | |
| 538 std::vector<int> run_order; | |
| 539 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 540 manager_.reset(); | |
| 541 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 542 | |
| 543 test_task_runner_->RunUntilIdle(); | |
| 544 EXPECT_TRUE(run_order.empty()); | |
| 545 } | |
| 546 | |
| 547 void PostTaskToRunner(scoped_refptr<base::SingleThreadTaskRunner> runner, | |
| 548 std::vector<int>* run_order) { | |
| 549 runner->PostTask(FROM_HERE, base::Bind(&TestTask, 1, run_order)); | |
| 550 } | |
| 551 | |
| 552 TEST_F(TaskQueueManagerTest, PostFromThread) { | |
| 553 InitializeWithRealMessageLoop(1u); | |
| 554 | |
| 555 std::vector<int> run_order; | |
| 556 base::Thread thread("TestThread"); | |
| 557 thread.Start(); | |
| 558 thread.task_runner()->PostTask( | |
| 559 FROM_HERE, base::Bind(&PostTaskToRunner, runners_[0], &run_order)); | |
| 560 thread.Stop(); | |
| 561 | |
| 562 message_loop_->RunUntilIdle(); | |
| 563 EXPECT_THAT(run_order, ElementsAre(1)); | |
| 564 } | |
| 565 | |
| 566 void RePostingTestTask(scoped_refptr<base::SingleThreadTaskRunner> runner, | |
| 567 int* run_count) { | |
| 568 (*run_count)++; | |
| 569 runner->PostTask(FROM_HERE, Bind(&RePostingTestTask, | |
| 570 base::Unretained(runner.get()), run_count)); | |
| 571 } | |
| 572 | |
| 573 TEST_F(TaskQueueManagerTest, DoWorkCantPostItselfMultipleTimes) { | |
| 574 Initialize(1u); | |
| 575 | |
| 576 int run_count = 0; | |
| 577 runners_[0]->PostTask( | |
| 578 FROM_HERE, base::Bind(&RePostingTestTask, runners_[0], &run_count)); | |
| 579 | |
| 580 test_task_runner_->RunPendingTasks(); | |
| 581 // NOTE without the executing_task_ check in MaybePostDoWorkOnMainRunner there | |
| 582 // will be two tasks here. | |
| 583 EXPECT_EQ(1u, test_task_runner_->NumPendingTasks()); | |
| 584 EXPECT_EQ(1, run_count); | |
| 585 } | |
| 586 | |
| 587 TEST_F(TaskQueueManagerTest, PostFromNestedRunloop) { | |
| 588 InitializeWithRealMessageLoop(1u); | |
| 589 | |
| 590 std::vector<int> run_order; | |
| 591 std::vector<std::pair<base::Closure, bool>> tasks_to_post_from_nested_loop; | |
| 592 tasks_to_post_from_nested_loop.push_back( | |
| 593 std::make_pair(base::Bind(&TestTask, 1, &run_order), true)); | |
| 594 | |
| 595 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 0, &run_order)); | |
| 596 runners_[0]->PostTask( | |
| 597 FROM_HERE, | |
| 598 base::Bind(&PostFromNestedRunloop, message_loop_.get(), runners_[0], | |
| 599 base::Unretained(&tasks_to_post_from_nested_loop))); | |
| 600 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 601 | |
| 602 message_loop_->RunUntilIdle(); | |
| 603 | |
| 604 EXPECT_THAT(run_order, ElementsAre(0, 2, 1)); | |
| 605 } | |
| 606 | |
| 607 TEST_F(TaskQueueManagerTest, WorkBatching) { | |
| 608 Initialize(1u); | |
| 609 | |
| 610 manager_->SetWorkBatchSize(2); | |
| 611 | |
| 612 std::vector<int> run_order; | |
| 613 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 614 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 615 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order)); | |
| 616 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 4, &run_order)); | |
| 617 | |
| 618 // Running one task in the host message loop should cause two posted tasks to | |
| 619 // get executed. | |
| 620 EXPECT_EQ(test_task_runner_->NumPendingTasks(), 1u); | |
| 621 test_task_runner_->RunPendingTasks(); | |
| 622 EXPECT_THAT(run_order, ElementsAre(1, 2)); | |
| 623 | |
| 624 // The second task runs the remaining two posted tasks. | |
| 625 EXPECT_EQ(test_task_runner_->NumPendingTasks(), 1u); | |
| 626 test_task_runner_->RunPendingTasks(); | |
| 627 EXPECT_THAT(run_order, ElementsAre(1, 2, 3, 4)); | |
| 628 } | |
| 629 | |
| 630 TEST_F(TaskQueueManagerTest, AutoPumpAfterWakeup) { | |
| 631 Initialize(2u); | |
| 632 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::AFTER_WAKEUP); | |
| 633 | |
| 634 std::vector<int> run_order; | |
| 635 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 636 test_task_runner_->RunUntilIdle(); | |
| 637 EXPECT_TRUE(run_order.empty()); // Shouldn't run - no other task to wake TQM. | |
| 638 | |
| 639 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 640 test_task_runner_->RunUntilIdle(); | |
| 641 EXPECT_TRUE(run_order.empty()); // Still shouldn't wake TQM. | |
| 642 | |
| 643 runners_[1]->PostTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order)); | |
| 644 test_task_runner_->RunUntilIdle(); | |
| 645 // Executing a task on an auto pumped queue should wake the TQM. | |
| 646 EXPECT_THAT(run_order, ElementsAre(3, 1, 2)); | |
| 647 } | |
| 648 | |
| 649 TEST_F(TaskQueueManagerTest, AutoPumpAfterWakeupWhenAlreadyAwake) { | |
| 650 Initialize(2u); | |
| 651 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::AFTER_WAKEUP); | |
| 652 | |
| 653 std::vector<int> run_order; | |
| 654 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 655 runners_[1]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 656 test_task_runner_->RunUntilIdle(); | |
| 657 EXPECT_THAT(run_order, ElementsAre(2, 1)); // TQM was already awake. | |
| 658 } | |
| 659 | |
| 660 TEST_F(TaskQueueManagerTest, | |
| 661 AutoPumpAfterWakeupTriggeredByManuallyPumpedQueue) { | |
| 662 Initialize(2u); | |
| 663 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::AFTER_WAKEUP); | |
| 664 runners_[1]->SetPumpPolicy(TaskQueue::PumpPolicy::MANUAL); | |
| 665 | |
| 666 std::vector<int> run_order; | |
| 667 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 668 test_task_runner_->RunUntilIdle(); | |
| 669 EXPECT_TRUE(run_order.empty()); // Shouldn't run - no other task to wake TQM. | |
| 670 | |
| 671 runners_[1]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 672 test_task_runner_->RunUntilIdle(); | |
| 673 // This still shouldn't wake TQM as manual queue was not pumped. | |
| 674 EXPECT_TRUE(run_order.empty()); | |
| 675 | |
| 676 runners_[1]->PumpQueue(); | |
| 677 test_task_runner_->RunUntilIdle(); | |
| 678 // Executing a task on an auto pumped queue should wake the TQM. | |
| 679 EXPECT_THAT(run_order, ElementsAre(2, 1)); | |
| 680 } | |
| 681 | |
| 682 void TestPostingTask(scoped_refptr<base::SingleThreadTaskRunner> task_runner, | |
| 683 base::Closure task) { | |
| 684 task_runner->PostTask(FROM_HERE, task); | |
| 685 } | |
| 686 | |
| 687 TEST_F(TaskQueueManagerTest, AutoPumpAfterWakeupFromTask) { | |
| 688 Initialize(2u); | |
| 689 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::AFTER_WAKEUP); | |
| 690 | |
| 691 std::vector<int> run_order; | |
| 692 // Check that a task which posts a task to an auto pump after wakeup queue | |
| 693 // doesn't cause the queue to wake up. | |
| 694 base::Closure after_wakeup_task = base::Bind(&TestTask, 1, &run_order); | |
| 695 runners_[1]->PostTask( | |
| 696 FROM_HERE, base::Bind(&TestPostingTask, runners_[0], after_wakeup_task)); | |
| 697 test_task_runner_->RunUntilIdle(); | |
| 698 EXPECT_TRUE(run_order.empty()); | |
| 699 | |
| 700 // Wake up the queue. | |
| 701 runners_[1]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 702 test_task_runner_->RunUntilIdle(); | |
| 703 EXPECT_THAT(run_order, ElementsAre(2, 1)); | |
| 704 } | |
| 705 | |
| 706 TEST_F(TaskQueueManagerTest, AutoPumpAfterWakeupFromMultipleTasks) { | |
| 707 Initialize(2u); | |
| 708 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::AFTER_WAKEUP); | |
| 709 | |
| 710 std::vector<int> run_order; | |
| 711 // Check that a task which posts a task to an auto pump after wakeup queue | |
| 712 // doesn't cause the queue to wake up. | |
| 713 base::Closure after_wakeup_task_1 = base::Bind(&TestTask, 1, &run_order); | |
| 714 base::Closure after_wakeup_task_2 = base::Bind(&TestTask, 2, &run_order); | |
| 715 runners_[1]->PostTask(FROM_HERE, base::Bind(&TestPostingTask, runners_[0], | |
| 716 after_wakeup_task_1)); | |
| 717 runners_[1]->PostTask(FROM_HERE, base::Bind(&TestPostingTask, runners_[0], | |
| 718 after_wakeup_task_2)); | |
| 719 test_task_runner_->RunUntilIdle(); | |
| 720 EXPECT_TRUE(run_order.empty()); | |
| 721 | |
| 722 // Wake up the queue. | |
| 723 runners_[1]->PostTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order)); | |
| 724 test_task_runner_->RunUntilIdle(); | |
| 725 EXPECT_THAT(run_order, ElementsAre(3, 1, 2)); | |
| 726 } | |
| 727 | |
| 728 TEST_F(TaskQueueManagerTest, AutoPumpAfterWakeupBecomesQuiescent) { | |
| 729 Initialize(2u); | |
| 730 runners_[0]->SetPumpPolicy(TaskQueue::PumpPolicy::AFTER_WAKEUP); | |
| 731 | |
| 732 int run_count = 0; | |
| 733 // Check that if multiple tasks reposts themselves onto a pump-after-wakeup | |
| 734 // queue they don't wake each other and will eventually stop when no other | |
| 735 // tasks execute. | |
| 736 runners_[0]->PostTask( | |
| 737 FROM_HERE, base::Bind(&RePostingTestTask, runners_[0], &run_count)); | |
| 738 runners_[0]->PostTask( | |
| 739 FROM_HERE, base::Bind(&RePostingTestTask, runners_[0], &run_count)); | |
| 740 runners_[1]->PostTask(FROM_HERE, base::Bind(&NopTask)); | |
| 741 test_task_runner_->RunUntilIdle(); | |
| 742 // The reposting tasks posted to the after wakeup queue shouldn't have woken | |
| 743 // each other up. | |
| 744 EXPECT_EQ(2, run_count); | |
| 745 } | |
| 746 | |
| 747 TEST_F(TaskQueueManagerTest, AutoPumpAfterWakeupWithDontWakeQueue) { | |
| 748 Initialize(1u); | |
| 749 | |
| 750 scoped_refptr<internal::TaskQueueImpl> queue0 = manager_->NewTaskQueue( | |
| 751 TaskQueue::Spec("test_queue 0") | |
| 752 .SetPumpPolicy(TaskQueue::PumpPolicy::AFTER_WAKEUP)); | |
| 753 scoped_refptr<internal::TaskQueueImpl> queue1 = manager_->NewTaskQueue( | |
| 754 TaskQueue::Spec("test_queue 0") | |
| 755 .SetWakeupPolicy(TaskQueue::WakeupPolicy::DONT_WAKE_OTHER_QUEUES)); | |
| 756 scoped_refptr<internal::TaskQueueImpl> queue2 = runners_[0]; | |
| 757 | |
| 758 std::vector<int> run_order; | |
| 759 queue0->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 760 queue1->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 761 test_task_runner_->RunUntilIdle(); | |
| 762 // Executing a DONT_WAKE_OTHER_QUEUES queue shouldn't wake the autopump after | |
| 763 // wakeup queue. | |
| 764 EXPECT_THAT(run_order, ElementsAre(2)); | |
| 765 | |
| 766 queue2->PostTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order)); | |
| 767 test_task_runner_->RunUntilIdle(); | |
| 768 // Executing a CAN_WAKE_OTHER_QUEUES queue should wake the autopump after | |
| 769 // wakeup queue. | |
| 770 EXPECT_THAT(run_order, ElementsAre(2, 3, 1)); | |
| 771 } | |
| 772 | |
| 773 class MockTaskObserver : public base::MessageLoop::TaskObserver { | |
| 774 public: | |
| 775 MOCK_METHOD1(DidProcessTask, void(const base::PendingTask& task)); | |
| 776 MOCK_METHOD1(WillProcessTask, void(const base::PendingTask& task)); | |
| 777 }; | |
| 778 | |
| 779 TEST_F(TaskQueueManagerTest, TaskObserverAdding) { | |
| 780 InitializeWithRealMessageLoop(1u); | |
| 781 MockTaskObserver observer; | |
| 782 | |
| 783 manager_->SetWorkBatchSize(2); | |
| 784 manager_->AddTaskObserver(&observer); | |
| 785 | |
| 786 std::vector<int> run_order; | |
| 787 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 788 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 789 | |
| 790 EXPECT_CALL(observer, WillProcessTask(_)).Times(2); | |
| 791 EXPECT_CALL(observer, DidProcessTask(_)).Times(2); | |
| 792 message_loop_->RunUntilIdle(); | |
| 793 } | |
| 794 | |
| 795 TEST_F(TaskQueueManagerTest, TaskObserverRemoving) { | |
| 796 InitializeWithRealMessageLoop(1u); | |
| 797 MockTaskObserver observer; | |
| 798 manager_->SetWorkBatchSize(2); | |
| 799 manager_->AddTaskObserver(&observer); | |
| 800 manager_->RemoveTaskObserver(&observer); | |
| 801 | |
| 802 std::vector<int> run_order; | |
| 803 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 804 | |
| 805 EXPECT_CALL(observer, WillProcessTask(_)).Times(0); | |
| 806 EXPECT_CALL(observer, DidProcessTask(_)).Times(0); | |
| 807 | |
| 808 message_loop_->RunUntilIdle(); | |
| 809 } | |
| 810 | |
| 811 void RemoveObserverTask(TaskQueueManager* manager, | |
| 812 base::MessageLoop::TaskObserver* observer) { | |
| 813 manager->RemoveTaskObserver(observer); | |
| 814 } | |
| 815 | |
| 816 TEST_F(TaskQueueManagerTest, TaskObserverRemovingInsideTask) { | |
| 817 InitializeWithRealMessageLoop(1u); | |
| 818 MockTaskObserver observer; | |
| 819 manager_->SetWorkBatchSize(3); | |
| 820 manager_->AddTaskObserver(&observer); | |
| 821 | |
| 822 runners_[0]->PostTask( | |
| 823 FROM_HERE, base::Bind(&RemoveObserverTask, manager_.get(), &observer)); | |
| 824 | |
| 825 EXPECT_CALL(observer, WillProcessTask(_)).Times(1); | |
| 826 EXPECT_CALL(observer, DidProcessTask(_)).Times(0); | |
| 827 message_loop_->RunUntilIdle(); | |
| 828 } | |
| 829 | |
| 830 TEST_F(TaskQueueManagerTest, QueueTaskObserverAdding) { | |
| 831 InitializeWithRealMessageLoop(2u); | |
| 832 MockTaskObserver observer; | |
| 833 | |
| 834 manager_->SetWorkBatchSize(2); | |
| 835 runners_[0]->AddTaskObserver(&observer); | |
| 836 | |
| 837 std::vector<int> run_order; | |
| 838 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 839 runners_[1]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 840 | |
| 841 EXPECT_CALL(observer, WillProcessTask(_)).Times(1); | |
| 842 EXPECT_CALL(observer, DidProcessTask(_)).Times(1); | |
| 843 message_loop_->RunUntilIdle(); | |
| 844 } | |
| 845 | |
| 846 TEST_F(TaskQueueManagerTest, QueueTaskObserverRemoving) { | |
| 847 InitializeWithRealMessageLoop(1u); | |
| 848 MockTaskObserver observer; | |
| 849 manager_->SetWorkBatchSize(2); | |
| 850 runners_[0]->AddTaskObserver(&observer); | |
| 851 runners_[0]->RemoveTaskObserver(&observer); | |
| 852 | |
| 853 std::vector<int> run_order; | |
| 854 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 855 | |
| 856 EXPECT_CALL(observer, WillProcessTask(_)).Times(0); | |
| 857 EXPECT_CALL(observer, DidProcessTask(_)).Times(0); | |
| 858 | |
| 859 message_loop_->RunUntilIdle(); | |
| 860 } | |
| 861 | |
| 862 void RemoveQueueObserverTask(scoped_refptr<TaskQueue> queue, | |
| 863 base::MessageLoop::TaskObserver* observer) { | |
| 864 queue->RemoveTaskObserver(observer); | |
| 865 } | |
| 866 | |
| 867 TEST_F(TaskQueueManagerTest, QueueTaskObserverRemovingInsideTask) { | |
| 868 InitializeWithRealMessageLoop(1u); | |
| 869 MockTaskObserver observer; | |
| 870 runners_[0]->AddTaskObserver(&observer); | |
| 871 | |
| 872 runners_[0]->PostTask( | |
| 873 FROM_HERE, base::Bind(&RemoveQueueObserverTask, runners_[0], &observer)); | |
| 874 | |
| 875 EXPECT_CALL(observer, WillProcessTask(_)).Times(1); | |
| 876 EXPECT_CALL(observer, DidProcessTask(_)).Times(0); | |
| 877 message_loop_->RunUntilIdle(); | |
| 878 } | |
| 879 | |
| 880 TEST_F(TaskQueueManagerTest, ThreadCheckAfterTermination) { | |
| 881 Initialize(1u); | |
| 882 EXPECT_TRUE(runners_[0]->RunsTasksOnCurrentThread()); | |
| 883 manager_.reset(); | |
| 884 EXPECT_TRUE(runners_[0]->RunsTasksOnCurrentThread()); | |
| 885 } | |
| 886 | |
| 887 TEST_F(TaskQueueManagerTest, NextPendingDelayedTaskRunTime) { | |
| 888 scoped_ptr<base::SimpleTestTickClock> clock(new base::SimpleTestTickClock()); | |
| 889 clock->Advance(base::TimeDelta::FromMicroseconds(10000)); | |
| 890 Initialize(2u); | |
| 891 manager_->SetTimeSourceForTesting( | |
| 892 make_scoped_ptr(new TestTimeSource(clock.get()))); | |
| 893 | |
| 894 // With no delayed tasks. | |
| 895 EXPECT_TRUE(manager_->NextPendingDelayedTaskRunTime().is_null()); | |
| 896 | |
| 897 // With a non-delayed task. | |
| 898 runners_[0]->PostTask(FROM_HERE, base::Bind(&NopTask)); | |
| 899 EXPECT_TRUE(manager_->NextPendingDelayedTaskRunTime().is_null()); | |
| 900 | |
| 901 // With a delayed task. | |
| 902 base::TimeDelta expected_delay = base::TimeDelta::FromMilliseconds(50); | |
| 903 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&NopTask), expected_delay); | |
| 904 EXPECT_EQ(clock->NowTicks() + expected_delay, | |
| 905 manager_->NextPendingDelayedTaskRunTime()); | |
| 906 | |
| 907 // With another delayed task in the same queue with a longer delay. | |
| 908 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&NopTask), | |
| 909 base::TimeDelta::FromMilliseconds(100)); | |
| 910 EXPECT_EQ(clock->NowTicks() + expected_delay, | |
| 911 manager_->NextPendingDelayedTaskRunTime()); | |
| 912 | |
| 913 // With another delayed task in the same queue with a shorter delay. | |
| 914 expected_delay = base::TimeDelta::FromMilliseconds(20); | |
| 915 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&NopTask), expected_delay); | |
| 916 EXPECT_EQ(clock->NowTicks() + expected_delay, | |
| 917 manager_->NextPendingDelayedTaskRunTime()); | |
| 918 | |
| 919 // With another delayed task in a different queue with a shorter delay. | |
| 920 expected_delay = base::TimeDelta::FromMilliseconds(10); | |
| 921 runners_[1]->PostDelayedTask(FROM_HERE, base::Bind(&NopTask), expected_delay); | |
| 922 EXPECT_EQ(clock->NowTicks() + expected_delay, | |
| 923 manager_->NextPendingDelayedTaskRunTime()); | |
| 924 | |
| 925 // Test it updates as time progresses | |
| 926 clock->Advance(expected_delay); | |
| 927 EXPECT_EQ(clock->NowTicks(), manager_->NextPendingDelayedTaskRunTime()); | |
| 928 } | |
| 929 | |
| 930 TEST_F(TaskQueueManagerTest, NextPendingDelayedTaskRunTime_MultipleQueues) { | |
| 931 Initialize(3u); | |
| 932 | |
| 933 base::TimeDelta delay1 = base::TimeDelta::FromMilliseconds(50); | |
| 934 base::TimeDelta delay2 = base::TimeDelta::FromMilliseconds(5); | |
| 935 base::TimeDelta delay3 = base::TimeDelta::FromMilliseconds(10); | |
| 936 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&NopTask), delay1); | |
| 937 runners_[1]->PostDelayedTask(FROM_HERE, base::Bind(&NopTask), delay2); | |
| 938 runners_[2]->PostDelayedTask(FROM_HERE, base::Bind(&NopTask), delay3); | |
| 939 | |
| 940 EXPECT_EQ(now_src_->NowTicks() + delay2, | |
| 941 manager_->NextPendingDelayedTaskRunTime()); | |
| 942 } | |
| 943 | |
| 944 TEST_F(TaskQueueManagerTest, DeleteTaskQueueManagerInsideATask) { | |
| 945 Initialize(1u); | |
| 946 | |
| 947 runners_[0]->PostTask( | |
| 948 FROM_HERE, base::Bind(&TaskQueueManagerTest::DeleteTaskQueueManager, | |
| 949 base::Unretained(this))); | |
| 950 | |
| 951 // This should not crash, assuming DoWork detects the TaskQueueManager has | |
| 952 // been deleted. | |
| 953 test_task_runner_->RunUntilIdle(); | |
| 954 } | |
| 955 | |
| 956 TEST_F(TaskQueueManagerTest, GetAndClearSystemIsQuiescentBit) { | |
| 957 Initialize(3u); | |
| 958 | |
| 959 scoped_refptr<internal::TaskQueueImpl> queue0 = manager_->NewTaskQueue( | |
| 960 TaskQueue::Spec("test_queue 0").SetShouldMonitorQuiescence(true)); | |
| 961 scoped_refptr<internal::TaskQueueImpl> queue1 = manager_->NewTaskQueue( | |
| 962 TaskQueue::Spec("test_queue 1").SetShouldMonitorQuiescence(true)); | |
| 963 scoped_refptr<internal::TaskQueueImpl> queue2 = manager_->NewTaskQueue( | |
| 964 TaskQueue::Spec("test_queue 2").SetShouldMonitorQuiescence(false)); | |
| 965 | |
| 966 EXPECT_TRUE(manager_->GetAndClearSystemIsQuiescentBit()); | |
| 967 | |
| 968 queue0->PostTask(FROM_HERE, base::Bind(&NopTask)); | |
| 969 test_task_runner_->RunUntilIdle(); | |
| 970 EXPECT_FALSE(manager_->GetAndClearSystemIsQuiescentBit()); | |
| 971 EXPECT_TRUE(manager_->GetAndClearSystemIsQuiescentBit()); | |
| 972 | |
| 973 queue1->PostTask(FROM_HERE, base::Bind(&NopTask)); | |
| 974 test_task_runner_->RunUntilIdle(); | |
| 975 EXPECT_FALSE(manager_->GetAndClearSystemIsQuiescentBit()); | |
| 976 EXPECT_TRUE(manager_->GetAndClearSystemIsQuiescentBit()); | |
| 977 | |
| 978 queue2->PostTask(FROM_HERE, base::Bind(&NopTask)); | |
| 979 test_task_runner_->RunUntilIdle(); | |
| 980 EXPECT_TRUE(manager_->GetAndClearSystemIsQuiescentBit()); | |
| 981 | |
| 982 queue0->PostTask(FROM_HERE, base::Bind(&NopTask)); | |
| 983 queue1->PostTask(FROM_HERE, base::Bind(&NopTask)); | |
| 984 test_task_runner_->RunUntilIdle(); | |
| 985 EXPECT_FALSE(manager_->GetAndClearSystemIsQuiescentBit()); | |
| 986 EXPECT_TRUE(manager_->GetAndClearSystemIsQuiescentBit()); | |
| 987 } | |
| 988 | |
| 989 TEST_F(TaskQueueManagerTest, IsQueueEmpty) { | |
| 990 Initialize(2u); | |
| 991 internal::TaskQueueImpl* queue0 = runners_[0].get(); | |
| 992 internal::TaskQueueImpl* queue1 = runners_[1].get(); | |
| 993 queue0->SetPumpPolicy(TaskQueue::PumpPolicy::AUTO); | |
| 994 queue1->SetPumpPolicy(TaskQueue::PumpPolicy::MANUAL); | |
| 995 | |
| 996 EXPECT_TRUE(queue0->IsQueueEmpty()); | |
| 997 EXPECT_TRUE(queue1->IsQueueEmpty()); | |
| 998 | |
| 999 queue0->PostTask(FROM_HERE, base::Bind(NullTask)); | |
| 1000 queue1->PostTask(FROM_HERE, base::Bind(NullTask)); | |
| 1001 EXPECT_FALSE(queue0->IsQueueEmpty()); | |
| 1002 EXPECT_FALSE(queue1->IsQueueEmpty()); | |
| 1003 | |
| 1004 test_task_runner_->RunUntilIdle(); | |
| 1005 EXPECT_TRUE(queue0->IsQueueEmpty()); | |
| 1006 EXPECT_FALSE(queue1->IsQueueEmpty()); | |
| 1007 | |
| 1008 queue1->PumpQueue(); | |
| 1009 EXPECT_TRUE(queue0->IsQueueEmpty()); | |
| 1010 EXPECT_FALSE(queue1->IsQueueEmpty()); | |
| 1011 | |
| 1012 test_task_runner_->RunUntilIdle(); | |
| 1013 EXPECT_TRUE(queue0->IsQueueEmpty()); | |
| 1014 EXPECT_TRUE(queue1->IsQueueEmpty()); | |
| 1015 } | |
| 1016 | |
| 1017 TEST_F(TaskQueueManagerTest, GetQueueState) { | |
| 1018 Initialize(2u); | |
| 1019 internal::TaskQueueImpl* queue0 = runners_[0].get(); | |
| 1020 internal::TaskQueueImpl* queue1 = runners_[1].get(); | |
| 1021 queue0->SetPumpPolicy(TaskQueue::PumpPolicy::AUTO); | |
| 1022 queue1->SetPumpPolicy(TaskQueue::PumpPolicy::MANUAL); | |
| 1023 | |
| 1024 EXPECT_EQ(TaskQueue::QueueState::EMPTY, queue0->GetQueueState()); | |
| 1025 EXPECT_EQ(TaskQueue::QueueState::EMPTY, queue1->GetQueueState()); | |
| 1026 | |
| 1027 queue0->PostTask(FROM_HERE, base::Bind(NullTask)); | |
| 1028 queue0->PostTask(FROM_HERE, base::Bind(NullTask)); | |
| 1029 queue1->PostTask(FROM_HERE, base::Bind(NullTask)); | |
| 1030 EXPECT_EQ(TaskQueue::QueueState::NEEDS_PUMPING, queue0->GetQueueState()); | |
| 1031 EXPECT_EQ(TaskQueue::QueueState::NEEDS_PUMPING, queue1->GetQueueState()); | |
| 1032 | |
| 1033 test_task_runner_->SetRunTaskLimit(1); | |
| 1034 test_task_runner_->RunPendingTasks(); | |
| 1035 EXPECT_EQ(TaskQueue::QueueState::HAS_WORK, queue0->GetQueueState()); | |
| 1036 EXPECT_EQ(TaskQueue::QueueState::NEEDS_PUMPING, queue1->GetQueueState()); | |
| 1037 | |
| 1038 test_task_runner_->ClearRunTaskLimit(); | |
| 1039 test_task_runner_->RunUntilIdle(); | |
| 1040 EXPECT_EQ(TaskQueue::QueueState::EMPTY, queue0->GetQueueState()); | |
| 1041 EXPECT_EQ(TaskQueue::QueueState::NEEDS_PUMPING, queue1->GetQueueState()); | |
| 1042 | |
| 1043 queue1->PumpQueue(); | |
| 1044 EXPECT_EQ(TaskQueue::QueueState::EMPTY, queue0->GetQueueState()); | |
| 1045 EXPECT_EQ(TaskQueue::QueueState::HAS_WORK, queue1->GetQueueState()); | |
| 1046 | |
| 1047 test_task_runner_->RunUntilIdle(); | |
| 1048 EXPECT_EQ(TaskQueue::QueueState::EMPTY, queue0->GetQueueState()); | |
| 1049 EXPECT_EQ(TaskQueue::QueueState::EMPTY, queue1->GetQueueState()); | |
| 1050 } | |
| 1051 | |
| 1052 TEST_F(TaskQueueManagerTest, DelayedTaskDoesNotSkipAHeadOfNonDelayedTask) { | |
| 1053 Initialize(2u); | |
| 1054 | |
| 1055 std::vector<int> run_order; | |
| 1056 base::TimeDelta delay = base::TimeDelta::FromMilliseconds(10); | |
| 1057 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order), | |
| 1058 delay); | |
| 1059 runners_[1]->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 1060 runners_[1]->PostTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order)); | |
| 1061 | |
| 1062 now_src_->Advance(delay * 2); | |
| 1063 // After task 2 has run, the automatic selector will have to choose between | |
| 1064 // tasks 1 and 3. The sequence numbers are used to choose between the two | |
| 1065 // tasks and if they are correct task 1 will run last. | |
| 1066 test_task_runner_->RunUntilIdle(); | |
| 1067 | |
| 1068 EXPECT_THAT(run_order, ElementsAre(2, 3, 1)); | |
| 1069 } | |
| 1070 | |
| 1071 TEST_F(TaskQueueManagerTest, DelayedTaskDoesNotSkipAHeadOfShorterDelayedTask) { | |
| 1072 Initialize(2u); | |
| 1073 | |
| 1074 std::vector<int> run_order; | |
| 1075 base::TimeDelta delay1 = base::TimeDelta::FromMilliseconds(10); | |
| 1076 base::TimeDelta delay2 = base::TimeDelta::FromMilliseconds(5); | |
| 1077 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order), | |
| 1078 delay1); | |
| 1079 runners_[1]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order), | |
| 1080 delay2); | |
| 1081 | |
| 1082 now_src_->Advance(delay1 * 2); | |
| 1083 test_task_runner_->RunUntilIdle(); | |
| 1084 | |
| 1085 EXPECT_THAT(run_order, ElementsAre(2, 1)); | |
| 1086 } | |
| 1087 | |
| 1088 TEST_F(TaskQueueManagerTest, DelayedTaskWithAbsoluteRunTime) { | |
| 1089 Initialize(1u); | |
| 1090 | |
| 1091 // One task in the past, two with the exact same run time and one in the | |
| 1092 // future. | |
| 1093 base::TimeDelta delay = base::TimeDelta::FromMilliseconds(10); | |
| 1094 base::TimeTicks runTime1 = now_src_->NowTicks() - delay; | |
| 1095 base::TimeTicks runTime2 = now_src_->NowTicks(); | |
| 1096 base::TimeTicks runTime3 = now_src_->NowTicks(); | |
| 1097 base::TimeTicks runTime4 = now_src_->NowTicks() + delay; | |
| 1098 | |
| 1099 std::vector<int> run_order; | |
| 1100 runners_[0]->PostDelayedTaskAt( | |
| 1101 FROM_HERE, base::Bind(&TestTask, 1, &run_order), runTime1); | |
| 1102 runners_[0]->PostDelayedTaskAt( | |
| 1103 FROM_HERE, base::Bind(&TestTask, 2, &run_order), runTime2); | |
| 1104 runners_[0]->PostDelayedTaskAt( | |
| 1105 FROM_HERE, base::Bind(&TestTask, 3, &run_order), runTime3); | |
| 1106 runners_[0]->PostDelayedTaskAt( | |
| 1107 FROM_HERE, base::Bind(&TestTask, 4, &run_order), runTime4); | |
| 1108 | |
| 1109 now_src_->Advance(2 * delay); | |
| 1110 test_task_runner_->RunUntilIdle(); | |
| 1111 | |
| 1112 EXPECT_THAT(run_order, ElementsAre(1, 2, 3, 4)); | |
| 1113 } | |
| 1114 | |
| 1115 void CheckIsNested(bool* is_nested) { | |
| 1116 *is_nested = base::MessageLoop::current()->IsNested(); | |
| 1117 } | |
| 1118 | |
| 1119 void PostAndQuitFromNestedRunloop(base::RunLoop* run_loop, | |
| 1120 base::SingleThreadTaskRunner* runner, | |
| 1121 bool* was_nested) { | |
| 1122 base::MessageLoop::ScopedNestableTaskAllower allow( | |
| 1123 base::MessageLoop::current()); | |
| 1124 runner->PostTask(FROM_HERE, run_loop->QuitClosure()); | |
| 1125 runner->PostTask(FROM_HERE, base::Bind(&CheckIsNested, was_nested)); | |
| 1126 run_loop->Run(); | |
| 1127 } | |
| 1128 | |
| 1129 TEST_F(TaskQueueManagerTest, QuitWhileNested) { | |
| 1130 // This test makes sure we don't continue running a work batch after a nested | |
| 1131 // run loop has been exited in the middle of the batch. | |
| 1132 InitializeWithRealMessageLoop(1u); | |
| 1133 manager_->SetWorkBatchSize(2); | |
| 1134 | |
| 1135 bool was_nested = true; | |
| 1136 base::RunLoop run_loop; | |
| 1137 runners_[0]->PostTask( | |
| 1138 FROM_HERE, | |
| 1139 base::Bind(&PostAndQuitFromNestedRunloop, base::Unretained(&run_loop), | |
| 1140 runners_[0], base::Unretained(&was_nested))); | |
| 1141 | |
| 1142 message_loop_->RunUntilIdle(); | |
| 1143 EXPECT_FALSE(was_nested); | |
| 1144 } | |
| 1145 | |
| 1146 class SequenceNumberCapturingTaskObserver | |
| 1147 : public base::MessageLoop::TaskObserver { | |
| 1148 public: | |
| 1149 // MessageLoop::TaskObserver overrides. | |
| 1150 void WillProcessTask(const base::PendingTask& pending_task) override {} | |
| 1151 void DidProcessTask(const base::PendingTask& pending_task) override { | |
| 1152 sequence_numbers_.push_back(pending_task.sequence_num); | |
| 1153 } | |
| 1154 | |
| 1155 const std::vector<int>& sequence_numbers() const { return sequence_numbers_; } | |
| 1156 | |
| 1157 private: | |
| 1158 std::vector<int> sequence_numbers_; | |
| 1159 }; | |
| 1160 | |
| 1161 TEST_F(TaskQueueManagerTest, SequenceNumSetWhenTaskIsPosted) { | |
| 1162 Initialize(1u); | |
| 1163 | |
| 1164 SequenceNumberCapturingTaskObserver observer; | |
| 1165 manager_->AddTaskObserver(&observer); | |
| 1166 | |
| 1167 // Register four tasks that will run in reverse order. | |
| 1168 std::vector<int> run_order; | |
| 1169 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order), | |
| 1170 base::TimeDelta::FromMilliseconds(30)); | |
| 1171 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order), | |
| 1172 base::TimeDelta::FromMilliseconds(20)); | |
| 1173 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order), | |
| 1174 base::TimeDelta::FromMilliseconds(10)); | |
| 1175 runners_[0]->PostTask(FROM_HERE, base::Bind(&TestTask, 4, &run_order)); | |
| 1176 | |
| 1177 test_task_runner_->RunForPeriod(base::TimeDelta::FromMilliseconds(40)); | |
| 1178 ASSERT_THAT(run_order, ElementsAre(4, 3, 2, 1)); | |
| 1179 | |
| 1180 // The sequence numbers are a zero-based monotonically incrememting counter | |
| 1181 // which should be set when the task is posted rather than when it's enqueued | |
| 1182 // onto the incomming queue. | |
| 1183 EXPECT_THAT(observer.sequence_numbers(), ElementsAre(3, 2, 1, 0)); | |
| 1184 | |
| 1185 manager_->RemoveTaskObserver(&observer); | |
| 1186 } | |
| 1187 | |
| 1188 TEST_F(TaskQueueManagerTest, NewTaskQueues) { | |
| 1189 Initialize(1u); | |
| 1190 | |
| 1191 scoped_refptr<internal::TaskQueueImpl> queue1 = | |
| 1192 manager_->NewTaskQueue(TaskQueue::Spec("foo")); | |
| 1193 scoped_refptr<internal::TaskQueueImpl> queue2 = | |
| 1194 manager_->NewTaskQueue(TaskQueue::Spec("bar")); | |
| 1195 scoped_refptr<internal::TaskQueueImpl> queue3 = | |
| 1196 manager_->NewTaskQueue(TaskQueue::Spec("baz")); | |
| 1197 | |
| 1198 ASSERT_NE(queue1, queue2); | |
| 1199 ASSERT_NE(queue1, queue3); | |
| 1200 ASSERT_NE(queue2, queue3); | |
| 1201 | |
| 1202 std::vector<int> run_order; | |
| 1203 queue1->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 1204 queue2->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 1205 queue3->PostTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order)); | |
| 1206 test_task_runner_->RunUntilIdle(); | |
| 1207 | |
| 1208 EXPECT_THAT(run_order, ElementsAre(1, 2, 3)); | |
| 1209 } | |
| 1210 | |
| 1211 TEST_F(TaskQueueManagerTest, UnregisterTaskQueue) { | |
| 1212 Initialize(1u); | |
| 1213 | |
| 1214 scoped_refptr<internal::TaskQueueImpl> queue1 = | |
| 1215 manager_->NewTaskQueue(TaskQueue::Spec("foo")); | |
| 1216 scoped_refptr<internal::TaskQueueImpl> queue2 = | |
| 1217 manager_->NewTaskQueue(TaskQueue::Spec("bar")); | |
| 1218 scoped_refptr<internal::TaskQueueImpl> queue3 = | |
| 1219 manager_->NewTaskQueue(TaskQueue::Spec("baz")); | |
| 1220 | |
| 1221 ASSERT_NE(queue1, queue2); | |
| 1222 ASSERT_NE(queue1, queue3); | |
| 1223 ASSERT_NE(queue2, queue3); | |
| 1224 | |
| 1225 std::vector<int> run_order; | |
| 1226 queue1->PostTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order)); | |
| 1227 queue2->PostTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order)); | |
| 1228 queue3->PostTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order)); | |
| 1229 | |
| 1230 queue2->UnregisterTaskQueue(); | |
| 1231 test_task_runner_->RunUntilIdle(); | |
| 1232 | |
| 1233 EXPECT_THAT(run_order, ElementsAre(1, 3)); | |
| 1234 } | |
| 1235 | |
| 1236 TEST_F(TaskQueueManagerTest, UnregisterTaskQueue_WithDelayedTasks) { | |
| 1237 Initialize(2u); | |
| 1238 | |
| 1239 // Register three delayed tasks | |
| 1240 std::vector<int> run_order; | |
| 1241 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 1, &run_order), | |
| 1242 base::TimeDelta::FromMilliseconds(10)); | |
| 1243 runners_[1]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 2, &run_order), | |
| 1244 base::TimeDelta::FromMilliseconds(20)); | |
| 1245 runners_[0]->PostDelayedTask(FROM_HERE, base::Bind(&TestTask, 3, &run_order), | |
| 1246 base::TimeDelta::FromMilliseconds(30)); | |
| 1247 | |
| 1248 runners_[1]->UnregisterTaskQueue(); | |
| 1249 test_task_runner_->RunUntilIdle(); | |
| 1250 | |
| 1251 test_task_runner_->RunForPeriod(base::TimeDelta::FromMilliseconds(40)); | |
| 1252 ASSERT_THAT(run_order, ElementsAre(1, 3)); | |
| 1253 } | |
| 1254 | |
| 1255 void PostTestTasksFromNestedMessageLoop( | |
| 1256 base::MessageLoop* message_loop, | |
| 1257 scoped_refptr<base::SingleThreadTaskRunner> main_runner, | |
| 1258 scoped_refptr<base::SingleThreadTaskRunner> wake_up_runner, | |
| 1259 std::vector<int>* run_order) { | |
| 1260 base::MessageLoop::ScopedNestableTaskAllower allow(message_loop); | |
| 1261 main_runner->PostNonNestableTask(FROM_HERE, | |
| 1262 base::Bind(&TestTask, 1, run_order)); | |
| 1263 // The following should never get executed. | |
| 1264 wake_up_runner->PostTask(FROM_HERE, base::Bind(&TestTask, 2, run_order)); | |
| 1265 message_loop->RunUntilIdle(); | |
| 1266 } | |
| 1267 | |
| 1268 TEST_F(TaskQueueManagerTest, DeferredNonNestableTaskDoesNotTriggerWakeUp) { | |
| 1269 // This test checks that running (i.e., deferring) a non-nestable task in a | |
| 1270 // nested run loop does not trigger the pumping of an on-wakeup queue. | |
| 1271 InitializeWithRealMessageLoop(2u); | |
| 1272 runners_[1]->SetPumpPolicy(TaskQueue::PumpPolicy::AFTER_WAKEUP); | |
| 1273 | |
| 1274 std::vector<int> run_order; | |
| 1275 runners_[0]->PostTask( | |
| 1276 FROM_HERE, | |
| 1277 base::Bind(&PostTestTasksFromNestedMessageLoop, message_loop_.get(), | |
| 1278 runners_[0], runners_[1], base::Unretained(&run_order))); | |
| 1279 | |
| 1280 message_loop_->RunUntilIdle(); | |
| 1281 ASSERT_THAT(run_order, ElementsAre(1)); | |
| 1282 } | |
| 1283 | |
| 1284 namespace { | |
| 1285 | |
| 1286 class MockObserver : public TaskQueueManager::Observer { | |
| 1287 public: | |
| 1288 MOCK_METHOD1(OnUnregisterTaskQueue, | |
| 1289 void(const scoped_refptr<internal::TaskQueueImpl>& queue)); | |
| 1290 }; | |
| 1291 | |
| 1292 } // namespace | |
| 1293 | |
| 1294 TEST_F(TaskQueueManagerTest, OnUnregisterTaskQueue) { | |
| 1295 Initialize(0u); | |
| 1296 | |
| 1297 MockObserver observer; | |
| 1298 manager_->SetObserver(&observer); | |
| 1299 | |
| 1300 scoped_refptr<internal::TaskQueueImpl> task_queue = | |
| 1301 manager_->NewTaskQueue(TaskQueue::Spec("test_queue")); | |
| 1302 | |
| 1303 EXPECT_CALL(observer, OnUnregisterTaskQueue(_)).Times(1); | |
| 1304 task_queue->UnregisterTaskQueue(); | |
| 1305 | |
| 1306 manager_->SetObserver(nullptr); | |
| 1307 } | |
| 1308 | |
| 1309 } // namespace scheduler | |
| OLD | NEW |