1 // Copyright 2015 The Chromium OS Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #ifndef LIBBRILLO_BRILLO_MESSAGE_LOOPS_FAKE_MESSAGE_LOOP_H_ 6 #define LIBBRILLO_BRILLO_MESSAGE_LOOPS_FAKE_MESSAGE_LOOP_H_ 7 8 #include <functional> 9 #include <map> 10 #include <queue> 11 #include <set> 12 #include <utility> 13 #include <vector> 14 15 #include <base/location.h> 16 #include <base/test/simple_test_clock.h> 17 #include <base/time/time.h> 18 19 #include <brillo/brillo_export.h> 20 #include <brillo/message_loops/message_loop.h> 21 22 namespace brillo { 23 24 // The FakeMessageLoop implements a message loop that doesn't block or wait for 25 // time based tasks to be ready. The tasks are executed in the order they should 26 // be executed in a real message loop implementation, but the time is advanced 27 // to the time when the first task should be executed instead of blocking. 28 // To keep a consistent notion of time for other classes, FakeMessageLoop 29 // optionally updates a SimpleTestClock instance when it needs to advance the 30 // clock. 31 // This message loop implementation is useful for unittests. 32 class BRILLO_EXPORT FakeMessageLoop : public MessageLoop { 33 public: 34 // Create a FakeMessageLoop optionally using a SimpleTestClock to update the 35 // time when Run() or RunOnce(true) are called and should block. 36 explicit FakeMessageLoop(base::SimpleTestClock* clock); 37 ~FakeMessageLoop() override = default; 38 39 TaskId PostDelayedTask(const base::Location& from_here, 40 base::OnceClosure task, 41 base::TimeDelta delay) override; 42 using MessageLoop::PostDelayedTask; 43 bool CancelTask(TaskId task_id) override; 44 bool RunOnce(bool may_block) override; 45 46 // FakeMessageLoop methods: 47 48 // Return whether there are peding tasks. Useful to check that no 49 // callbacks were leaked. 50 bool PendingTasks(); 51 52 private: 53 struct ScheduledTask { 54 base::Location location; 55 base::OnceClosure callback; 56 }; 57 58 // The sparse list of scheduled pending callbacks. 59 std::map<MessageLoop::TaskId, ScheduledTask> tasks_; 60 61 // Using std::greater<> for the priority_queue means that the top() of the 62 // queue is the lowest (earliest) time, and for the same time, the smallest 63 // TaskId. This determines the order in which the tasks will be fired. 64 std::priority_queue< 65 std::pair<base::Time, MessageLoop::TaskId>, 66 std::vector<std::pair<base::Time, MessageLoop::TaskId>>, 67 std::greater<std::pair<base::Time, MessageLoop::TaskId>>> fire_order_; 68 69 base::SimpleTestClock* test_clock_ = nullptr; 70 base::Time current_time_ = base::Time::FromDoubleT(1246996800.); 71 72 MessageLoop::TaskId last_id_ = kTaskIdNull; 73 74 DISALLOW_COPY_AND_ASSIGN(FakeMessageLoop); 75 }; 76 77 } // namespace brillo 78 79 #endif // LIBBRILLO_BRILLO_MESSAGE_LOOPS_FAKE_MESSAGE_LOOP_H_ 80