Home | History | Annotate | Download | only in test
      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 #ifndef CC_TEST_ORDERED_SIMPLE_TASK_RUNNER_H_
      6 #define CC_TEST_ORDERED_SIMPLE_TASK_RUNNER_H_
      7 
      8 #include <limits>
      9 #include <set>
     10 #include <vector>
     11 
     12 #include "base/basictypes.h"
     13 #include "base/compiler_specific.h"
     14 #include "base/debug/trace_event.h"
     15 #include "base/logging.h"
     16 #include "base/test/test_simple_task_runner.h"
     17 #include "cc/test/test_now_source.h"
     18 
     19 namespace cc {
     20 
     21 // Subclass of TestPendingTask which has a unique ID for every task, supports
     22 // being used inside a std::set and has debug tracing support.
     23 class TestOrderablePendingTask : public base::TestPendingTask {
     24  public:
     25   TestOrderablePendingTask();
     26   TestOrderablePendingTask(const tracked_objects::Location& location,
     27                            const base::Closure& task,
     28                            base::TimeTicks post_time,
     29                            base::TimeDelta delay,
     30                            TestNestability nestability);
     31   ~TestOrderablePendingTask();
     32 
     33   // operators needed by std::set and comparison
     34   bool operator==(const TestOrderablePendingTask& other) const;
     35   bool operator<(const TestOrderablePendingTask& other) const;
     36 
     37   // debug tracing functions
     38   scoped_refptr<base::debug::ConvertableToTraceFormat> AsValue() const;
     39   void AsValueInto(base::debug::TracedValue* state) const;
     40 
     41  private:
     42   static size_t task_id_counter;
     43   const size_t task_id_;
     44 };
     45 
     46 // This runs pending tasks based on task's post_time + delay.
     47 // We should not execute a delayed task sooner than some of the queued tasks
     48 // which don't have a delay even though it is queued early.
     49 class OrderedSimpleTaskRunner : public base::SingleThreadTaskRunner {
     50  public:
     51   OrderedSimpleTaskRunner();
     52   OrderedSimpleTaskRunner(scoped_refptr<TestNowSource> now_src,
     53                           bool advance_now);
     54 
     55   // base::TestSimpleTaskRunner implementation:
     56   virtual bool PostDelayedTask(const tracked_objects::Location& from_here,
     57                                const base::Closure& task,
     58                                base::TimeDelta delay) OVERRIDE;
     59   virtual bool PostNonNestableDelayedTask(
     60       const tracked_objects::Location& from_here,
     61       const base::Closure& task,
     62       base::TimeDelta delay) OVERRIDE;
     63 
     64   virtual bool RunsTasksOnCurrentThread() const OVERRIDE;
     65 
     66   // Set a maximum number of tasks to run at once. Useful as a timeout to
     67   // prevent infinite task loops.
     68   static const size_t kAbsoluteMaxTasks;
     69   void SetRunTaskLimit(size_t max_tasks) { max_tasks_ = max_tasks; }
     70   void ClearRunTaskLimit() { max_tasks_ = kAbsoluteMaxTasks; }
     71 
     72   // Allow task runner to advance now when running tasks.
     73   void SetAutoAdvanceNowToPendingTasks(bool advance_now) {
     74     advance_now_ = advance_now;
     75   }
     76 
     77   base::TimeTicks NextTaskTime();
     78   base::TimeDelta DelayToNextTaskTime();
     79 
     80   // Run tasks while the callback returns true or too many tasks have been run.
     81   // Returns true if there are still pending tasks left.
     82   bool RunTasksWhile(base::Callback<bool(void)> condition);
     83 
     84   // Run tasks while *all* of the callbacks return true or too many tasks have
     85   // been run. Exits on the *first* condition which returns false, skipping
     86   // calling all remaining conditions. Conditions can have side effects,
     87   // including modifying the task queue.
     88   // Returns true if there are still pending tasks left.
     89   bool RunTasksWhile(
     90       const std::vector<base::Callback<bool(void)> >& conditions);
     91 
     92   // Convenience functions to run tasks with common conditions.
     93 
     94   // Run tasks which existed at the start of this call.
     95   // Return code indicates tasks still exist to run.
     96   bool RunPendingTasks();
     97   // Keep running tasks until no tasks are left.
     98   // Return code indicates tasks still exist to run which also indicates if
     99   // runner reached idle.
    100   bool RunUntilIdle();
    101   // Keep running tasks until given time period.
    102   // Return code indicates tasks still exist to run.
    103   bool RunUntilTime(base::TimeTicks time);
    104   bool RunForPeriod(base::TimeDelta period);
    105 
    106   // base::debug tracing functionality
    107   scoped_refptr<base::debug::ConvertableToTraceFormat> AsValue() const;
    108   virtual void AsValueInto(base::debug::TracedValue* state) const;
    109 
    110   // Common conditions to run for, exposed publicly to allow external users to
    111   // use their own combinations.
    112   // -------------------------------------------------------------------------
    113 
    114   // Keep running until the given number of tasks have run.
    115   // You generally shouldn't use this check as it will cause your tests to fail
    116   // when code is changed adding a new task. It is useful as a "timeout" type
    117   // solution.
    118   base::Callback<bool(void)> TaskRunCountBelow(size_t max_tasks);
    119 
    120   // Keep running until a task which didn't exist initially would run.
    121   base::Callback<bool(void)> TaskExistedInitially();
    122 
    123   // Stop running tasks when NextTaskTime() >= stop_at
    124   base::Callback<bool(void)> NowBefore(base::TimeTicks stop_at);
    125 
    126   // Advance Now() to the next task to run.
    127   base::Callback<bool(void)> AdvanceNow();
    128 
    129  protected:
    130   static bool TaskRunCountBelowCallback(size_t max_tasks, size_t* task_run);
    131   bool TaskExistedInitiallyCallback(
    132       const std::set<TestOrderablePendingTask>& existing_tasks);
    133   bool NowBeforeCallback(base::TimeTicks stop_at);
    134   bool AdvanceNowCallback();
    135 
    136   virtual ~OrderedSimpleTaskRunner();
    137 
    138   base::ThreadChecker thread_checker_;
    139 
    140   bool advance_now_;
    141   scoped_refptr<TestNowSource> now_src_;
    142 
    143   size_t max_tasks_;
    144 
    145   bool inside_run_tasks_until_;
    146   std::set<TestOrderablePendingTask> pending_tasks_;
    147 
    148  private:
    149   DISALLOW_COPY_AND_ASSIGN(OrderedSimpleTaskRunner);
    150 };
    151 
    152 }  // namespace cc
    153 
    154 #endif  // CC_TEST_ORDERED_SIMPLE_TASK_RUNNER_H_
    155