| Index: third_party/WebKit/Source/platform/scheduler/base/task_queue_impl.h
|
| diff --git a/third_party/WebKit/Source/platform/scheduler/base/task_queue_impl.h b/third_party/WebKit/Source/platform/scheduler/base/task_queue_impl.h
|
| index dee99194ecc13e1a591d5dd47d570827b46de8b4..f56bb3615cd85453575210e901c239369a867bc6 100644
|
| --- a/third_party/WebKit/Source/platform/scheduler/base/task_queue_impl.h
|
| +++ b/third_party/WebKit/Source/platform/scheduler/base/task_queue_impl.h
|
| @@ -28,6 +28,32 @@ namespace internal {
|
| class WorkQueue;
|
| class WorkQueueSets;
|
|
|
| +// TaskQueueImpl has four main queues:
|
| +//
|
| +// Immediate (non-delayed) tasks:
|
| +// immediate_incoming_queue - PostTask enqueues tasks here
|
| +// immediate_work_queue
|
| +//
|
| +// Delayed tasks
|
| +// delayed_incoming_queue - PostDelayedTask enqueues tasks here
|
| +// delayed_work_queue
|
| +//
|
| +// The immediate_incoming_queue can be accessed from any thread, the other
|
| +// queues are main-thread only. To reduce the overhead of locking,
|
| +// immediate_work_queue is swapped with immediate_incoming_queue when
|
| +// immediate_work_queue becomes empty.
|
| +//
|
| +// Delayed tasks are initially posted to delayed_incoming_queue and a wakeup
|
| +// is scheduled with the TimeDomain. When the delay has elapsed, the TimeDomain
|
| +// calls UpdateDelayedWorkQueue and ready delayed tasks are moved into the
|
| +// delayed_work_queue. Note the EnqueueOrder (used for ordering) for a delayed
|
| +// task is not set until it's moved into the delayed_work_queue.
|
| +//
|
| +// TaskQueueImpl uses the WorkQueueSets and the TaskQueueSelector to implement
|
| +// prioritization. Task selection is done by the TaskQueueSelector and when a
|
| +// queue is selected, it round-robins between the immediate_work_queue and
|
| +// delayed_work_queue. The reason for this is we want to make sure delayed
|
| +// tasks (normally the most common type) don't starve out immediate work.
|
| class BLINK_PLATFORM_EXPORT TaskQueueImpl final : public TaskQueue {
|
| public:
|
| TaskQueueImpl(TaskQueueManager* task_queue_manager,
|
| @@ -52,6 +78,10 @@ class BLINK_PLATFORM_EXPORT TaskQueueImpl final : public TaskQueue {
|
| bool nestable,
|
| EnqueueOrder enqueue_order);
|
|
|
| + // Create a fake Task based on the handle, suitable for using as a search
|
| + // key.
|
| + static Task CreateFakeTaskFromHandle(const TaskHandle& handle);
|
| +
|
| EnqueueOrder enqueue_order() const {
|
| #ifndef NDEBUG
|
| DCHECK(enqueue_order_set_);
|
| @@ -71,13 +101,33 @@ class BLINK_PLATFORM_EXPORT TaskQueueImpl final : public TaskQueue {
|
| bool enqueue_order_set() const { return enqueue_order_set_; }
|
| #endif
|
|
|
| + using ComparatorFn = bool (*)(const Task&, const Task&);
|
| +
|
| + // Tasks are ordered by |delayed_run_time| smallest first then and by
|
| + // |sequence_num| in case of a tie.
|
| + class DelayedRunTimeComparator {
|
| + public:
|
| + bool operator()(const Task& a, const Task& b) const;
|
| + };
|
| +
|
| + // Tasks are ordered by |enqueue_order_| smallest first.
|
| + static bool EnqueueOrderComparatorFn(const TaskQueueImpl::Task& a,
|
| + const TaskQueueImpl::Task& b);
|
| +
|
| + // Tasks are ordered by |delayed_run_time| smallest first then and by
|
| + // |sequence_num| in case of a tie.
|
| + static bool DelayedRunTimeComparatorFn(const TaskQueueImpl::Task& a,
|
| + const TaskQueueImpl::Task& b);
|
| +
|
| private:
|
| #ifndef NDEBUG
|
| bool enqueue_order_set_;
|
| #endif
|
| - // Similar to sequence number, but the |enqueue_order| is set by
|
| - // EnqueueTasksLocked and is not initially defined for delayed tasks until
|
| - // they are enqueued on the |immediate_incoming_queue_|.
|
| + // Similar to sequence number, but ultimately the |enqueue_order_| is what
|
| + // the scheduler uses for task ordering. For immediate tasks |enqueue_order|
|
| + // is set when posted, but for delayed tasks it's not defined until they are
|
| + // enqueued on the |delayed_work_queue_|. This is because otherwise delayed
|
| + // tasks could run before an immediate task posted after the delayed task.
|
| EnqueueOrder enqueue_order_;
|
| };
|
|
|
| @@ -90,7 +140,11 @@ class BLINK_PLATFORM_EXPORT TaskQueueImpl final : public TaskQueue {
|
| bool PostNonNestableDelayedTask(const tracked_objects::Location& from_here,
|
| const base::Closure& task,
|
| base::TimeDelta delay) override;
|
| -
|
| + TaskHandle PostCancellableDelayedTask(
|
| + const tracked_objects::Location& from_here,
|
| + const base::Closure& task,
|
| + base::TimeDelta delay) override;
|
| + bool CancelTask(const TaskHandle& handle) override;
|
| void SetQueueEnabled(bool enabled) override;
|
| bool IsQueueEnabled() const override;
|
| bool IsEmpty() const override;
|
| @@ -108,6 +162,8 @@ class BLINK_PLATFORM_EXPORT TaskQueueImpl final : public TaskQueue {
|
| TimeDomain* GetTimeDomain() const override;
|
| void SetBlameContext(base::trace_event::BlameContext* blame_context) override;
|
|
|
| + bool IsTaskPending(const TaskHandle& handle) const;
|
| +
|
| void UpdateImmediateWorkQueue(bool should_trigger_wakeup,
|
| const Task* previous_task);
|
| void UpdateDelayedWorkQueue(LazyNow* lazy_now,
|
| @@ -162,6 +218,13 @@ class BLINK_PLATFORM_EXPORT TaskQueueImpl final : public TaskQueue {
|
| private:
|
| friend class WorkQueue;
|
|
|
| + // Note both DelayedRunTimeQueue and ComparatorQueue are sets for fast task
|
| + // cancellation. Typically queue sizes are well under 200 so the overhead of
|
| + // std::set vs std::priority_queue and std::queue is lost in the noise of
|
| + // everything else.
|
| + using DelayedRunTimeQueue = std::set<Task, Task::DelayedRunTimeComparator>;
|
| + using ComparatorQueue = std::set<Task, Task::ComparatorFn>;
|
| +
|
| enum class TaskType {
|
| NORMAL,
|
| NON_NESTABLE,
|
| @@ -180,7 +243,7 @@ class BLINK_PLATFORM_EXPORT TaskQueueImpl final : public TaskQueue {
|
| PumpPolicy pump_policy;
|
| TimeDomain* time_domain;
|
|
|
| - std::queue<Task> immediate_incoming_queue;
|
| + ComparatorQueue immediate_incoming_queue;
|
| };
|
|
|
| struct MainThreadOnly {
|
| @@ -199,7 +262,7 @@ class BLINK_PLATFORM_EXPORT TaskQueueImpl final : public TaskQueue {
|
|
|
| std::unique_ptr<WorkQueue> delayed_work_queue;
|
| std::unique_ptr<WorkQueue> immediate_work_queue;
|
| - std::priority_queue<Task> delayed_incoming_queue;
|
| + DelayedRunTimeQueue delayed_incoming_queue;
|
| base::ObserverList<base::MessageLoop::TaskObserver> task_observers;
|
| size_t set_index;
|
| bool is_enabled;
|
| @@ -258,9 +321,9 @@ class BLINK_PLATFORM_EXPORT TaskQueueImpl final : public TaskQueue {
|
| void PushOntoImmediateIncomingQueueLocked(Task pending_task);
|
|
|
| void TraceQueueSize(bool is_locked) const;
|
| - static void QueueAsValueInto(const std::queue<Task>& queue,
|
| + static void QueueAsValueInto(const ComparatorQueue& queue,
|
| base::trace_event::TracedValue* state);
|
| - static void QueueAsValueInto(const std::priority_queue<Task>& queue,
|
| + static void QueueAsValueInto(const DelayedRunTimeQueue& queue,
|
| base::trace_event::TracedValue* state);
|
| static void TaskAsValueInto(const Task& task,
|
| base::trace_event::TracedValue* state);
|
|
|