Bug 1867190 - Initialise the PHC allocate delay later r=glandium
[gecko.git] / xpcom / threads / EventQueue.h
blobb7af71be82c0735f33d26737c2e6f20eba2dcfca
1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */
3 /* This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7 #ifndef mozilla_EventQueue_h
8 #define mozilla_EventQueue_h
10 #include "mozilla/Mutex.h"
11 #include "mozilla/Queue.h"
12 #include "mozilla/TimeStamp.h"
13 #include "nsCOMPtr.h"
14 #include "nsIRunnable.h"
16 namespace mozilla {
18 #define EVENT_QUEUE_PRIORITY_LIST(EVENT_PRIORITY) \
19 EVENT_PRIORITY(Idle, 0) \
20 EVENT_PRIORITY(DeferredTimers, 1) \
21 EVENT_PRIORITY(Low, 2) \
22 EVENT_PRIORITY(InputLow, 3) \
23 EVENT_PRIORITY(Normal, 4) \
24 EVENT_PRIORITY(MediumHigh, 5) \
25 EVENT_PRIORITY(InputHigh, 6) \
26 EVENT_PRIORITY(Vsync, 7) \
27 EVENT_PRIORITY(InputHighest, 8) \
28 EVENT_PRIORITY(RenderBlocking, 9) \
29 EVENT_PRIORITY(Control, 10)
31 enum class EventQueuePriority {
32 #define EVENT_PRIORITY(NAME, VALUE) NAME = VALUE,
33 EVENT_QUEUE_PRIORITY_LIST(EVENT_PRIORITY)
34 #undef EVENT_PRIORITY
35 Invalid
38 class IdlePeriodState;
40 namespace detail {
42 // EventQueue is our unsynchronized event queue implementation. It is a queue
43 // of runnables used for non-main thread, as well as optionally providing
44 // forwarding to TaskController.
46 // Since EventQueue is unsynchronized, it should be wrapped in an outer
47 // SynchronizedEventQueue implementation (like ThreadEventQueue).
48 template <size_t ItemsPerPage>
49 class EventQueueInternal {
50 public:
51 explicit EventQueueInternal(bool aForwardToTC) : mForwardToTC(aForwardToTC) {}
53 // Add an event to the end of the queue. Implementors are free to use
54 // aPriority however they wish. If the runnable supports
55 // nsIRunnablePriority and the implementing class supports
56 // prioritization, aPriority represents the result of calling
57 // nsIRunnablePriority::GetPriority(). *aDelay is time the event has
58 // already been delayed (used when moving an event from one queue to
59 // another)
60 void PutEvent(already_AddRefed<nsIRunnable>&& aEvent,
61 EventQueuePriority aPriority, const MutexAutoLock& aProofOfLock,
62 mozilla::TimeDuration* aDelay = nullptr);
64 // Get an event from the front of the queue. This should return null if the
65 // queue is non-empty but the event in front is not ready to run.
66 // *aLastEventDelay is the time the event spent in queues before being
67 // retrieved.
68 already_AddRefed<nsIRunnable> GetEvent(
69 const MutexAutoLock& aProofOfLock,
70 mozilla::TimeDuration* aLastEventDelay = nullptr);
72 // Returns true if the queue is empty. Implies !HasReadyEvent().
73 bool IsEmpty(const MutexAutoLock& aProofOfLock);
75 // Returns true if the queue is non-empty and if the event in front is ready
76 // to run. Implies !IsEmpty(). This should return true iff GetEvent returns a
77 // non-null value.
78 bool HasReadyEvent(const MutexAutoLock& aProofOfLock);
80 // Returns the number of events in the queue.
81 size_t Count(const MutexAutoLock& aProofOfLock) const;
82 // For some reason, if we put this in the .cpp file the linker can't find it
83 already_AddRefed<nsIRunnable> PeekEvent(const MutexAutoLock& aProofOfLock) {
84 if (mQueue.IsEmpty()) {
85 return nullptr;
88 nsCOMPtr<nsIRunnable> result = mQueue.FirstElement();
89 return result.forget();
92 void EnableInputEventPrioritization(const MutexAutoLock& aProofOfLock) {}
93 void FlushInputEventPrioritization(const MutexAutoLock& aProofOfLock) {}
94 void SuspendInputEventPrioritization(const MutexAutoLock& aProofOfLock) {}
95 void ResumeInputEventPrioritization(const MutexAutoLock& aProofOfLock) {}
97 size_t SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const {
98 return aMallocSizeOf(this) + SizeOfExcludingThis(aMallocSizeOf);
101 size_t SizeOfExcludingThis(mozilla::MallocSizeOf aMallocSizeOf) const {
102 size_t size = mQueue.ShallowSizeOfExcludingThis(aMallocSizeOf);
103 size += mDispatchTimes.ShallowSizeOfExcludingThis(aMallocSizeOf);
104 return size;
107 private:
108 mozilla::Queue<nsCOMPtr<nsIRunnable>, ItemsPerPage> mQueue;
109 // This queue is only populated when the profiler is turned on.
110 mozilla::Queue<mozilla::TimeStamp, ItemsPerPage> mDispatchTimes;
111 TimeDuration mLastEventDelay;
112 // This indicates PutEvent forwards runnables to the TaskController. This
113 // should be true for the top level event queue on the main thread.
114 bool mForwardToTC;
117 } // namespace detail
119 class EventQueue final : public mozilla::detail::EventQueueInternal<16> {
120 public:
121 explicit EventQueue(bool aForwardToTC = false)
122 : mozilla::detail::EventQueueInternal<16>(aForwardToTC) {}
125 template <size_t ItemsPerPage = 16>
126 class EventQueueSized final
127 : public mozilla::detail::EventQueueInternal<ItemsPerPage> {
128 public:
129 explicit EventQueueSized(bool aForwardToTC = false)
130 : mozilla::detail::EventQueueInternal<ItemsPerPage>(aForwardToTC) {}
133 } // namespace mozilla
135 #endif // mozilla_EventQueue_h