OLD | NEW |
---|---|
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #ifndef CC_SCHEDULER_BEGIN_FRAME_SOURCE_H_ | 5 #ifndef CC_SCHEDULER_BEGIN_FRAME_SOURCE_H_ |
6 #define CC_SCHEDULER_BEGIN_FRAME_SOURCE_H_ | 6 #define CC_SCHEDULER_BEGIN_FRAME_SOURCE_H_ |
7 | 7 |
8 #include <stddef.h> | 8 #include <stddef.h> |
9 #include <stdint.h> | 9 #include <stdint.h> |
10 | 10 |
11 #include <set> | 11 #include <set> |
12 #include <string> | 12 #include <string> |
13 #include <unordered_set> | |
13 | 14 |
14 #include "base/logging.h" | 15 #include "base/logging.h" |
15 #include "base/macros.h" | 16 #include "base/macros.h" |
16 #include "base/trace_event/trace_event.h" | 17 #include "base/trace_event/trace_event.h" |
17 #include "cc/output/begin_frame_args.h" | 18 #include "cc/output/begin_frame_args.h" |
18 #include "cc/scheduler/delay_based_time_source.h" | 19 #include "cc/scheduler/delay_based_time_source.h" |
19 | 20 |
20 namespace cc { | 21 namespace cc { |
21 | 22 |
22 // (Pure) Interface for observing BeginFrame messages from BeginFrameSource | 23 // (Pure) Interface for observing BeginFrame messages from BeginFrameSource |
23 // objects. | 24 // objects. |
24 class CC_EXPORT BeginFrameObserver { | 25 class CC_EXPORT BeginFrameObserver { |
25 public: | 26 public: |
26 virtual ~BeginFrameObserver() {} | 27 virtual ~BeginFrameObserver() {} |
27 | 28 |
28 // The |args| given to OnBeginFrame is guaranteed to have | 29 // The |args| given to OnBeginFrame is guaranteed to have |
29 // |args|.IsValid()==true and have |args|.frame_time | 30 // |args|.IsValid()==true. If |args|.source_id did not change between |
30 // field be strictly greater than the previous call. | 31 // invocations, |args|.sequence_number is guaranteed to be be strictly greater |
32 // than the previous call. Further, |args|.frame_time is guaranteed to be | |
33 // greater than or equal to the previous call. | |
31 // | 34 // |
32 // Side effects: This function can (and most of the time *will*) change the | 35 // Side effects: This function can (and most of the time *will*) change the |
33 // return value of the LastUsedBeginFrameArgs method. See the documentation | 36 // return value of the LastUsedBeginFrameArgs method. See the documentation |
34 // on that method for more information. | 37 // on that method for more information. |
35 virtual void OnBeginFrame(const BeginFrameArgs& args) = 0; | 38 virtual void OnBeginFrame(const BeginFrameArgs& args) = 0; |
36 | 39 |
37 // Returns the last BeginFrameArgs used by the observer. This method's return | 40 // Returns the last BeginFrameArgs used by the observer. This method's return |
38 // value is affected by the OnBeginFrame method! | 41 // value is affected by the OnBeginFrame method! |
39 // | 42 // |
40 // - Before the first call of OnBeginFrame, this method should return a | 43 // - Before the first call of OnBeginFrame, this method should return a |
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
92 // BeginFrameObserver. | 95 // BeginFrameObserver. |
93 // | 96 // |
94 // BeginFrame calls *normally* occur just after a vsync interrupt when input | 97 // BeginFrame calls *normally* occur just after a vsync interrupt when input |
95 // processing has been finished and provide information about the time values | 98 // processing has been finished and provide information about the time values |
96 // of the vsync times. *However*, these values can be heavily modified or even | 99 // of the vsync times. *However*, these values can be heavily modified or even |
97 // plain made up (when no vsync signal is available or vsync throttling is | 100 // plain made up (when no vsync signal is available or vsync throttling is |
98 // turned off). See the BeginFrameObserver for information about the guarantees | 101 // turned off). See the BeginFrameObserver for information about the guarantees |
99 // all BeginFrameSources *must* provide. | 102 // all BeginFrameSources *must* provide. |
100 class CC_EXPORT BeginFrameSource { | 103 class CC_EXPORT BeginFrameSource { |
101 public: | 104 public: |
105 BeginFrameSource(); | |
102 virtual ~BeginFrameSource() {} | 106 virtual ~BeginFrameSource() {} |
103 | 107 |
104 // DidFinishFrame provides back pressure to a frame source about frame | 108 // BeginFrameObservers use DidFinishFrame to acknowledge that they have |
105 // processing (rather than toggling SetNeedsBeginFrames every frame). It is | 109 // completed handling a BeginFrame. |
106 // used by systems like the BackToBackFrameSource to make sure only one frame | 110 // |
107 // is pending at a time. | 111 // The DisplayScheduler uses these acknowledgments to trigger an early |
112 // deadline once all BeginFrameObservers have completed a frame. | |
113 // | |
114 // They also provide back pressure to a frame source about frame processing | |
115 // (rather than toggling SetNeedsBeginFrames every frame). For example, the | |
116 // BackToBackFrameSource uses them to make sure only one frame is pending at a | |
117 // time. | |
108 virtual void DidFinishFrame(BeginFrameObserver* obs, | 118 virtual void DidFinishFrame(BeginFrameObserver* obs, |
109 size_t remaining_frames) = 0; | 119 const BeginFrameAck& ack) = 0; |
110 | 120 |
111 // Add/Remove an observer from the source. When no observers are added the BFS | 121 // Add/Remove an observer from the source. When no observers are added the BFS |
112 // should shut down its timers, disable vsync, etc. | 122 // should shut down its timers, disable vsync, etc. |
113 virtual void AddObserver(BeginFrameObserver* obs) = 0; | 123 virtual void AddObserver(BeginFrameObserver* obs) = 0; |
114 virtual void RemoveObserver(BeginFrameObserver* obs) = 0; | 124 virtual void RemoveObserver(BeginFrameObserver* obs) = 0; |
115 | 125 |
116 // Returns false if the begin frame source will just continue to produce | 126 // Returns false if the begin frame source will just continue to produce |
117 // begin frames without waiting. | 127 // begin frames without waiting. |
118 virtual bool IsThrottled() const = 0; | 128 virtual bool IsThrottled() const = 0; |
129 | |
130 // Returns an identifier for this BeginFrameSource. Guaranteed unique within a | |
131 // process, and very likely unique across processes. | |
132 virtual uint64_t source_id() const; | |
Sami
2016/12/06 12:41:07
Does this need to be virtual?
Eric Seckler
2016/12/06 17:34:00
Yup, for the DelegatingBFS.
Sami
2016/12/07 16:59:40
Oh I see, it needs to lie about its id.
Eric Seckler
2016/12/08 17:54:28
Actually, given that the DelegatingBFS doesn't pro
| |
133 | |
134 private: | |
135 uint64_t source_id_; | |
119 }; | 136 }; |
120 | 137 |
121 // A BeginFrameSource that does nothing. | 138 // A BeginFrameSource that does nothing. |
122 class CC_EXPORT StubBeginFrameSource : public BeginFrameSource { | 139 class CC_EXPORT StubBeginFrameSource : public BeginFrameSource { |
123 public: | 140 public: |
124 void DidFinishFrame(BeginFrameObserver* obs, | 141 void DidFinishFrame(BeginFrameObserver* obs, |
125 size_t remaining_frames) override {} | 142 const BeginFrameAck& ack) override {} |
126 void AddObserver(BeginFrameObserver* obs) override {} | 143 void AddObserver(BeginFrameObserver* obs) override {} |
127 void RemoveObserver(BeginFrameObserver* obs) override {} | 144 void RemoveObserver(BeginFrameObserver* obs) override {} |
128 bool IsThrottled() const override; | 145 bool IsThrottled() const override; |
129 }; | 146 }; |
130 | 147 |
131 // A frame source which ticks itself independently. | 148 // A frame source which ticks itself independently. |
132 class CC_EXPORT SyntheticBeginFrameSource : public BeginFrameSource { | 149 class CC_EXPORT SyntheticBeginFrameSource : public BeginFrameSource { |
133 public: | 150 public: |
134 ~SyntheticBeginFrameSource() override; | 151 ~SyntheticBeginFrameSource() override; |
135 | 152 |
136 virtual void OnUpdateVSyncParameters(base::TimeTicks timebase, | 153 virtual void OnUpdateVSyncParameters(base::TimeTicks timebase, |
137 base::TimeDelta interval) = 0; | 154 base::TimeDelta interval) = 0; |
138 // This overrides any past or future interval from updating vsync parameters. | 155 // This overrides any past or future interval from updating vsync parameters. |
139 virtual void SetAuthoritativeVSyncInterval(base::TimeDelta interval) = 0; | 156 virtual void SetAuthoritativeVSyncInterval(base::TimeDelta interval) = 0; |
140 }; | 157 }; |
141 | 158 |
142 // A frame source which calls BeginFrame (at the next possible time) as soon as | 159 // A frame source which calls BeginFrame (at the next possible time) as soon as |
143 // remaining frames reaches zero. | 160 // remaining frames reaches zero. |
144 class CC_EXPORT BackToBackBeginFrameSource : public SyntheticBeginFrameSource, | 161 class CC_EXPORT BackToBackBeginFrameSource : public SyntheticBeginFrameSource, |
145 public DelayBasedTimeSourceClient { | 162 public DelayBasedTimeSourceClient { |
146 public: | 163 public: |
147 explicit BackToBackBeginFrameSource( | 164 explicit BackToBackBeginFrameSource( |
148 std::unique_ptr<DelayBasedTimeSource> time_source); | 165 std::unique_ptr<DelayBasedTimeSource> time_source); |
149 ~BackToBackBeginFrameSource() override; | 166 ~BackToBackBeginFrameSource() override; |
150 | 167 |
151 // BeginFrameSource implementation. | 168 // BeginFrameSource implementation. |
152 void AddObserver(BeginFrameObserver* obs) override; | 169 void AddObserver(BeginFrameObserver* obs) override; |
153 void RemoveObserver(BeginFrameObserver* obs) override; | 170 void RemoveObserver(BeginFrameObserver* obs) override; |
154 void DidFinishFrame(BeginFrameObserver* obs, | 171 void DidFinishFrame(BeginFrameObserver* obs, |
155 size_t remaining_frames) override; | 172 const BeginFrameAck& ack) override; |
156 bool IsThrottled() const override; | 173 bool IsThrottled() const override; |
157 | 174 |
158 // SyntheticBeginFrameSource implementation. | 175 // SyntheticBeginFrameSource implementation. |
159 void OnUpdateVSyncParameters(base::TimeTicks timebase, | 176 void OnUpdateVSyncParameters(base::TimeTicks timebase, |
160 base::TimeDelta interval) override {} | 177 base::TimeDelta interval) override {} |
161 void SetAuthoritativeVSyncInterval(base::TimeDelta interval) override {} | 178 void SetAuthoritativeVSyncInterval(base::TimeDelta interval) override {} |
162 | 179 |
163 // DelayBasedTimeSourceClient implementation. | 180 // DelayBasedTimeSourceClient implementation. |
164 void OnTimerTick() override; | 181 void OnTimerTick() override; |
165 | 182 |
166 private: | 183 private: |
167 std::unique_ptr<DelayBasedTimeSource> time_source_; | 184 std::unique_ptr<DelayBasedTimeSource> time_source_; |
168 std::unordered_set<BeginFrameObserver*> observers_; | 185 std::unordered_set<BeginFrameObserver*> observers_; |
169 std::unordered_set<BeginFrameObserver*> pending_begin_frame_observers_; | 186 std::unordered_set<BeginFrameObserver*> pending_begin_frame_observers_; |
187 uint64_t next_sequence_number_; | |
170 base::WeakPtrFactory<BackToBackBeginFrameSource> weak_factory_; | 188 base::WeakPtrFactory<BackToBackBeginFrameSource> weak_factory_; |
171 | 189 |
172 DISALLOW_COPY_AND_ASSIGN(BackToBackBeginFrameSource); | 190 DISALLOW_COPY_AND_ASSIGN(BackToBackBeginFrameSource); |
173 }; | 191 }; |
174 | 192 |
175 // A frame source which is locked to an external parameters provides from a | 193 // A frame source which is locked to an external parameters provides from a |
176 // vsync source and generates BeginFrameArgs for it. | 194 // vsync source and generates BeginFrameArgs for it. |
177 class CC_EXPORT DelayBasedBeginFrameSource : public SyntheticBeginFrameSource, | 195 class CC_EXPORT DelayBasedBeginFrameSource : public SyntheticBeginFrameSource, |
178 public DelayBasedTimeSourceClient { | 196 public DelayBasedTimeSourceClient { |
179 public: | 197 public: |
180 explicit DelayBasedBeginFrameSource( | 198 explicit DelayBasedBeginFrameSource( |
181 std::unique_ptr<DelayBasedTimeSource> time_source); | 199 std::unique_ptr<DelayBasedTimeSource> time_source); |
182 ~DelayBasedBeginFrameSource() override; | 200 ~DelayBasedBeginFrameSource() override; |
183 | 201 |
184 // BeginFrameSource implementation. | 202 // BeginFrameSource implementation. |
185 void AddObserver(BeginFrameObserver* obs) override; | 203 void AddObserver(BeginFrameObserver* obs) override; |
186 void RemoveObserver(BeginFrameObserver* obs) override; | 204 void RemoveObserver(BeginFrameObserver* obs) override; |
187 void DidFinishFrame(BeginFrameObserver* obs, | 205 void DidFinishFrame(BeginFrameObserver* obs, |
188 size_t remaining_frames) override {} | 206 const BeginFrameAck& ack) override {} |
189 bool IsThrottled() const override; | 207 bool IsThrottled() const override; |
190 | 208 |
191 // SyntheticBeginFrameSource implementation. | 209 // SyntheticBeginFrameSource implementation. |
192 void OnUpdateVSyncParameters(base::TimeTicks timebase, | 210 void OnUpdateVSyncParameters(base::TimeTicks timebase, |
193 base::TimeDelta interval) override; | 211 base::TimeDelta interval) override; |
194 void SetAuthoritativeVSyncInterval(base::TimeDelta interval) override; | 212 void SetAuthoritativeVSyncInterval(base::TimeDelta interval) override; |
195 | 213 |
196 // DelayBasedTimeSourceClient implementation. | 214 // DelayBasedTimeSourceClient implementation. |
197 void OnTimerTick() override; | 215 void OnTimerTick() override; |
198 | 216 |
199 private: | 217 private: |
200 BeginFrameArgs CreateBeginFrameArgs(base::TimeTicks frame_time, | 218 BeginFrameArgs CreateBeginFrameArgs(uint64_t sequence_number, |
219 base::TimeTicks frame_time, | |
201 BeginFrameArgs::BeginFrameArgsType type); | 220 BeginFrameArgs::BeginFrameArgsType type); |
202 | 221 |
203 std::unique_ptr<DelayBasedTimeSource> time_source_; | 222 std::unique_ptr<DelayBasedTimeSource> time_source_; |
204 std::unordered_set<BeginFrameObserver*> observers_; | 223 std::unordered_set<BeginFrameObserver*> observers_; |
205 base::TimeTicks last_timebase_; | 224 base::TimeTicks last_timebase_; |
206 base::TimeDelta authoritative_interval_; | 225 base::TimeDelta authoritative_interval_; |
226 uint64_t current_sequence_number_; | |
227 base::TimeTicks current_begin_frame_time_; | |
207 | 228 |
208 DISALLOW_COPY_AND_ASSIGN(DelayBasedBeginFrameSource); | 229 DISALLOW_COPY_AND_ASSIGN(DelayBasedBeginFrameSource); |
209 }; | 230 }; |
210 | 231 |
232 // Helper class that tracks outstanding acknowledgments from | |
233 // BeginFrameObservers. | |
234 class CC_EXPORT BeginFrameObserverAckTracker { | |
235 public: | |
236 BeginFrameObserverAckTracker(); | |
237 virtual ~BeginFrameObserverAckTracker(); | |
238 | |
239 // The BeginFrameSource uses these methods to notify us when a BeginFrame was | |
240 // started and sent to a specific observer, an observer finished a frame, or | |
241 // an observer was added/removed. | |
242 void OnBeginFrame(const BeginFrameArgs& args); | |
243 void OnObserverBeginFrame(BeginFrameObserver* obs, | |
244 const BeginFrameArgs& args); | |
245 void OnObserverFinishedFrame(BeginFrameObserver* obs, | |
246 const BeginFrameAck& ack); | |
247 void OnObserverAdded(BeginFrameObserver* obs); | |
248 void OnObserverRemoved(BeginFrameObserver* obs); | |
249 | |
250 // Returns |true| if all the source's observers completed the current frame. | |
251 bool ObserversFinishedFrame(); | |
Sami
2016/12/06 12:41:07
bikeshed: AllObserversFinishedFrame() / AnyObserve
Eric Seckler
2016/12/06 17:34:00
Done.
| |
252 | |
253 // Returns |true| if any observer had updates during the current frame. | |
254 bool ObserversHadUpdates(); | |
255 | |
256 // Returns the sequence number of the oldest_incorporated_frame that any of | |
257 // the observers have contributed for the latest frame. | |
258 uint64_t OldestIncorporatedFrame(); | |
259 | |
260 private: | |
261 void SourceChanged(const BeginFrameArgs& args); | |
262 | |
263 uint64_t current_source_id_; | |
264 uint64_t current_sequence_number_; | |
265 std::set<BeginFrameObserver*> observers_; | |
Sami
2016/12/06 12:41:06
nit: unordered sets?
Eric Seckler
2016/12/06 17:34:00
That would make the AllObserversFinishedFrame calc
Sami
2016/12/07 16:59:40
Alright.
| |
266 std::set<BeginFrameObserver*> finished_observers_; | |
267 bool observers_had_updates_; | |
268 std::unordered_map<BeginFrameObserver*, uint64_t> oldest_incorporated_frames_; | |
269 }; | |
270 | |
211 class CC_EXPORT ExternalBeginFrameSourceClient { | 271 class CC_EXPORT ExternalBeginFrameSourceClient { |
212 public: | 272 public: |
213 // Only called when changed. Assumed false by default. | 273 // Only called when changed. Assumed false by default. |
214 virtual void OnNeedsBeginFrames(bool needs_begin_frames) = 0; | 274 virtual void OnNeedsBeginFrames(bool needs_begin_frames) = 0; |
275 // Called when all observers have completed a frame. | |
276 virtual void OnDidFinishFrame(const BeginFrameAck& ack) = 0; | |
215 }; | 277 }; |
216 | 278 |
217 // A BeginFrameSource that is only ticked manually. Usually the endpoint | 279 // A BeginFrameSource that is only ticked manually. Usually the endpoint |
218 // of messages from some other thread/process that send OnBeginFrame and | 280 // of messages from some other thread/process that send OnBeginFrame and |
219 // receive SetNeedsBeginFrame messages. This turns such messages back into | 281 // receive SetNeedsBeginFrame messages. This turns such messages back into |
220 // an observable BeginFrameSource. | 282 // an observable BeginFrameSource. |
221 class CC_EXPORT ExternalBeginFrameSource : public BeginFrameSource { | 283 class CC_EXPORT ExternalBeginFrameSource : public BeginFrameSource { |
222 public: | 284 public: |
223 // Client lifetime must be preserved by owner past the lifetime of this class. | 285 // Client lifetime must be preserved by owner past the lifetime of this class. |
224 explicit ExternalBeginFrameSource(ExternalBeginFrameSourceClient* client); | 286 explicit ExternalBeginFrameSource(ExternalBeginFrameSourceClient* client); |
225 ~ExternalBeginFrameSource() override; | 287 ~ExternalBeginFrameSource() override; |
226 | 288 |
227 // BeginFrameSource implementation. | 289 // BeginFrameSource implementation. |
228 void AddObserver(BeginFrameObserver* obs) override; | 290 void AddObserver(BeginFrameObserver* obs) override; |
229 void RemoveObserver(BeginFrameObserver* obs) override; | 291 void RemoveObserver(BeginFrameObserver* obs) override; |
230 void DidFinishFrame(BeginFrameObserver* obs, | 292 void DidFinishFrame(BeginFrameObserver* obs, |
231 size_t remaining_frames) override {} | 293 const BeginFrameAck& ack) override; |
232 bool IsThrottled() const override; | 294 bool IsThrottled() const override; |
233 | 295 |
234 void OnSetBeginFrameSourcePaused(bool paused); | 296 void OnSetBeginFrameSourcePaused(bool paused); |
235 void OnBeginFrame(const BeginFrameArgs& args); | 297 void OnBeginFrame(const BeginFrameArgs& args); |
236 | 298 |
237 protected: | 299 protected: |
300 void MaybeFinishFrame(); | |
301 void FinishFrame(); | |
302 | |
238 BeginFrameArgs missed_begin_frame_args_; | 303 BeginFrameArgs missed_begin_frame_args_; |
239 std::unordered_set<BeginFrameObserver*> observers_; | 304 std::unordered_set<BeginFrameObserver*> observers_; |
240 ExternalBeginFrameSourceClient* client_; | 305 ExternalBeginFrameSourceClient* client_; |
241 bool paused_ = false; | 306 bool paused_ = false; |
307 bool frame_active_ = false; | |
308 BeginFrameObserverAckTracker ack_tracker_; | |
242 | 309 |
243 private: | 310 private: |
244 DISALLOW_COPY_AND_ASSIGN(ExternalBeginFrameSource); | 311 DISALLOW_COPY_AND_ASSIGN(ExternalBeginFrameSource); |
245 }; | 312 }; |
246 | 313 |
314 // A BeginFrameSource that delegates to another given source. | |
315 class CC_EXPORT DelegatingBeginFrameSource : public BeginFrameSource { | |
316 public: | |
317 // |delegate| lifetime must be preserved past the lifetime of this class. | |
318 explicit DelegatingBeginFrameSource(BeginFrameSource* delegate); | |
319 ~DelegatingBeginFrameSource() override {} | |
320 | |
321 // BeginFrameSource implementation. | |
322 void DidFinishFrame(BeginFrameObserver* obs, | |
323 const BeginFrameAck& ack) override; | |
324 void AddObserver(BeginFrameObserver* obs) override; | |
325 void RemoveObserver(BeginFrameObserver* obs) override; | |
326 bool IsThrottled() const override; | |
327 uint64_t source_id() const override; | |
328 | |
329 private: | |
330 BeginFrameSource* delegate_; // Not owned. | |
331 }; | |
332 | |
247 } // namespace cc | 333 } // namespace cc |
248 | 334 |
249 #endif // CC_SCHEDULER_BEGIN_FRAME_SOURCE_H_ | 335 #endif // CC_SCHEDULER_BEGIN_FRAME_SOURCE_H_ |
OLD | NEW |