Update To 11.40.268.0
[platform/framework/web/crosswalk.git] / src / cc / scheduler / scheduler_state_machine.h
1 // Copyright 2011 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_SCHEDULER_SCHEDULER_STATE_MACHINE_H_
6 #define CC_SCHEDULER_SCHEDULER_STATE_MACHINE_H_
7
8 #include <string>
9
10 #include "base/basictypes.h"
11 #include "base/memory/scoped_ptr.h"
12 #include "base/time/time.h"
13 #include "cc/base/cc_export.h"
14 #include "cc/output/begin_frame_args.h"
15 #include "cc/scheduler/draw_result.h"
16 #include "cc/scheduler/scheduler_settings.h"
17
18 namespace base {
19 namespace debug {
20 class ConvertableToTraceFormat;
21 class TracedValue;
22 }
23 class Value;
24 }
25
26 namespace cc {
27
28 // The SchedulerStateMachine decides how to coordinate main thread activites
29 // like painting/running javascript with rendering and input activities on the
30 // impl thread.
31 //
32 // The state machine tracks internal state but is also influenced by external
33 // state.  Internal state includes things like whether a frame has been
34 // requested, while external state includes things like the current time being
35 // near to the vblank time.
36 //
37 // The scheduler seperates "what to do next" from the updating of its internal
38 // state to make testing cleaner.
39 class CC_EXPORT SchedulerStateMachine {
40  public:
41   // settings must be valid for the lifetime of this class.
42   explicit SchedulerStateMachine(const SchedulerSettings& settings);
43
44   enum OutputSurfaceState {
45     OUTPUT_SURFACE_ACTIVE,
46     OUTPUT_SURFACE_LOST,
47     OUTPUT_SURFACE_CREATING,
48     OUTPUT_SURFACE_WAITING_FOR_FIRST_COMMIT,
49     OUTPUT_SURFACE_WAITING_FOR_FIRST_ACTIVATION,
50   };
51   static const char* OutputSurfaceStateToString(OutputSurfaceState state);
52
53   // Note: BeginImplFrameState will always cycle through all the states in
54   // order. Whether or not it actually waits or draws, it will at least try to
55   // wait in BEGIN_IMPL_FRAME_STATE_INSIDE_BEGIN_FRAME and try to draw in
56   // BEGIN_IMPL_FRAME_STATE_INSIDE_DEADLINE
57   enum BeginImplFrameState {
58     BEGIN_IMPL_FRAME_STATE_IDLE,
59     BEGIN_IMPL_FRAME_STATE_BEGIN_FRAME_STARTING,
60     BEGIN_IMPL_FRAME_STATE_INSIDE_BEGIN_FRAME,
61     BEGIN_IMPL_FRAME_STATE_INSIDE_DEADLINE,
62   };
63   static const char* BeginImplFrameStateToString(BeginImplFrameState state);
64
65   enum CommitState {
66     COMMIT_STATE_IDLE,
67     COMMIT_STATE_BEGIN_MAIN_FRAME_SENT,
68     COMMIT_STATE_BEGIN_MAIN_FRAME_STARTED,
69     COMMIT_STATE_READY_TO_COMMIT,
70     COMMIT_STATE_WAITING_FOR_ACTIVATION,
71   };
72   static const char* CommitStateToString(CommitState state);
73
74   enum ForcedRedrawOnTimeoutState {
75     FORCED_REDRAW_STATE_IDLE,
76     FORCED_REDRAW_STATE_WAITING_FOR_COMMIT,
77     FORCED_REDRAW_STATE_WAITING_FOR_ACTIVATION,
78     FORCED_REDRAW_STATE_WAITING_FOR_DRAW,
79   };
80   static const char* ForcedRedrawOnTimeoutStateToString(
81       ForcedRedrawOnTimeoutState state);
82
83   bool CommitPending() const {
84     return commit_state_ == COMMIT_STATE_BEGIN_MAIN_FRAME_SENT ||
85            commit_state_ == COMMIT_STATE_BEGIN_MAIN_FRAME_STARTED ||
86            commit_state_ == COMMIT_STATE_READY_TO_COMMIT;
87   }
88   CommitState commit_state() const { return commit_state_; }
89
90   bool RedrawPending() const { return needs_redraw_; }
91   bool ManageTilesPending() const { return needs_manage_tiles_; }
92
93   enum Action {
94     ACTION_NONE,
95     ACTION_ANIMATE,
96     ACTION_SEND_BEGIN_MAIN_FRAME,
97     ACTION_COMMIT,
98     ACTION_UPDATE_VISIBLE_TILES,
99     ACTION_ACTIVATE_SYNC_TREE,
100     ACTION_DRAW_AND_SWAP_IF_POSSIBLE,
101     ACTION_DRAW_AND_SWAP_FORCED,
102     ACTION_DRAW_AND_SWAP_ABORT,
103     ACTION_BEGIN_OUTPUT_SURFACE_CREATION,
104     ACTION_MANAGE_TILES,
105   };
106   static const char* ActionToString(Action action);
107
108   scoped_refptr<base::debug::ConvertableToTraceFormat> AsValue() const;
109   void AsValueInto(base::debug::TracedValue* dict, base::TimeTicks now) const;
110
111   Action NextAction() const;
112   void UpdateState(Action action);
113
114   // Indicates whether the impl thread needs a BeginImplFrame callback in order
115   // to make progress.
116   bool BeginFrameNeeded() const;
117
118   // Indicates that we need to independently poll for new state and actions
119   // because we can't expect a BeginImplFrame. This is mostly used to avoid
120   // drawing repeat frames with the synchronous compositor without dropping
121   // necessary actions on the floor.
122   bool ShouldPollForAnticipatedDrawTriggers() const;
123
124   // Indicates that the system has entered and left a BeginImplFrame callback.
125   // The scheduler will not draw more than once in a given BeginImplFrame
126   // callback nor send more than one BeginMainFrame message.
127   void OnBeginImplFrame(const BeginFrameArgs& args);
128   void OnBeginImplFrameDeadlinePending();
129   void OnBeginImplFrameDeadline();
130   void OnBeginImplFrameIdle();
131   bool ShouldTriggerBeginImplFrameDeadlineEarly() const;
132   BeginImplFrameState begin_impl_frame_state() const {
133     return begin_impl_frame_state_;
134   }
135
136   // If the main thread didn't manage to produce a new frame in time for the
137   // impl thread to draw, it is in a high latency mode.
138   bool MainThreadIsInHighLatencyMode() const;
139
140   // PollForAnticipatedDrawTriggers is used by the synchronous compositor to
141   // avoid requesting BeginImplFrames when we won't actually draw but still
142   // need to advance our state at vsync intervals.
143   void DidEnterPollForAnticipatedDrawTriggers();
144   void DidLeavePollForAnticipatedDrawTriggers();
145   bool inside_poll_for_anticipated_draw_triggers() const {
146     return inside_poll_for_anticipated_draw_triggers_;
147   }
148
149   // Indicates whether the LayerTreeHostImpl is visible.
150   void SetVisible(bool visible);
151
152   // Indicates that a redraw is required, either due to the impl tree changing
153   // or the screen being damaged and simply needing redisplay.
154   void SetNeedsRedraw();
155   bool needs_redraw() const { return needs_redraw_; }
156
157   void SetNeedsAnimate();
158   bool needs_animate() const { return needs_animate_; }
159
160   // Indicates that manage-tiles is required. This guarantees another
161   // ManageTiles will occur shortly (even if no redraw is required).
162   void SetNeedsManageTiles();
163
164   // Sets how many swaps can be pending to the OutputSurface.
165   void SetMaxSwapsPending(int max);
166
167   // If the scheduler attempted to draw and swap, this provides feedback
168   // regarding whether or not the swap actually occured. We might skip the
169   // swap when there is not damage, for example.
170   void DidSwapBuffers();
171
172   // Indicates whether a redraw is required because we are currently rendering
173   // with a low resolution or checkerboarded tile.
174   void SetSwapUsedIncompleteTile(bool used_incomplete_tile);
175
176   // Notification from the OutputSurface that a swap has been consumed.
177   void DidSwapBuffersComplete();
178
179   // Indicates whether to prioritize impl thread latency (i.e., animation
180   // smoothness) over new content activation.
181   void SetImplLatencyTakesPriority(bool impl_latency_takes_priority);
182   bool impl_latency_takes_priority() const {
183     return impl_latency_takes_priority_;
184   }
185
186   // Indicates whether ACTION_DRAW_AND_SWAP_IF_POSSIBLE drew to the screen.
187   void DidDrawIfPossibleCompleted(DrawResult result);
188
189   // Indicates that a new commit flow needs to be performed, either to pull
190   // updates from the main thread to the impl, or to push deltas from the impl
191   // thread to main.
192   void SetNeedsCommit();
193
194   // Call this only in response to receiving an ACTION_SEND_BEGIN_MAIN_FRAME
195   // from NextAction.
196   // Indicates that all painting is complete.
197   void NotifyReadyToCommit();
198
199   // Call this only in response to receiving an ACTION_SEND_BEGIN_MAIN_FRAME
200   // from NextAction if the client rejects the BeginMainFrame message.
201   // If did_handle is false, then another commit will be retried soon.
202   void BeginMainFrameAborted(bool did_handle);
203
204   // Set that we can create the first OutputSurface and start the scheduler.
205   void SetCanStart() { can_start_ = true; }
206
207   void SetSkipNextBeginMainFrameToReduceLatency();
208
209   // Indicates whether drawing would, at this time, make sense.
210   // CanDraw can be used to suppress flashes or checkerboarding
211   // when such behavior would be undesirable.
212   void SetCanDraw(bool can);
213
214   // Indicates that scheduled BeginMainFrame is started.
215   void NotifyBeginMainFrameStarted();
216
217   // Indicates that the pending tree is ready for activation.
218   void NotifyReadyToActivate();
219
220   bool has_pending_tree() const { return has_pending_tree_; }
221   bool active_tree_needs_first_draw() const {
222     return active_tree_needs_first_draw_;
223   }
224
225   void DidManageTiles();
226   void DidLoseOutputSurface();
227   void DidCreateAndInitializeOutputSurface();
228   bool HasInitializedOutputSurface() const;
229
230   // True if we need to abort draws to make forward progress.
231   bool PendingDrawsShouldBeAborted() const;
232
233   bool SupportsProactiveBeginFrame() const;
234
235   void SetContinuousPainting(bool continuous_painting) {
236     continuous_painting_ = continuous_painting;
237   }
238
239   bool CouldSendBeginMainFrame() const;
240
241   void SetImplLatencyTakesPriorityOnBattery(
242       bool impl_latency_takes_priority_on_battery) {
243     impl_latency_takes_priority_on_battery_ =
244         impl_latency_takes_priority_on_battery;
245   }
246
247   // TODO(zmo): This is temporary for debugging crbug.com/393331.
248   // We should remove it afterwards.
249   std::string GetStatesForDebugging() const;
250
251  protected:
252   bool BeginFrameNeededToAnimateOrDraw() const;
253   bool ProactiveBeginFrameWanted() const;
254
255   // True if we need to force activations to make forward progress.
256   bool PendingActivationsShouldBeForced() const;
257
258   bool ShouldAnimate() const;
259   bool ShouldBeginOutputSurfaceCreation() const;
260   bool ShouldDrawForced() const;
261   bool ShouldDraw() const;
262   bool ShouldActivatePendingTree() const;
263   bool ShouldUpdateVisibleTiles() const;
264   bool ShouldSendBeginMainFrame() const;
265   bool ShouldCommit() const;
266   bool ShouldManageTiles() const;
267
268   void AdvanceCurrentFrameNumber();
269   bool HasAnimatedThisFrame() const;
270   bool HasSentBeginMainFrameThisFrame() const;
271   bool HasUpdatedVisibleTilesThisFrame() const;
272   bool HasRequestedSwapThisFrame() const;
273   bool HasSwappedThisFrame() const;
274
275   void UpdateStateOnCommit(bool commit_was_aborted);
276   void UpdateStateOnActivation();
277   void UpdateStateOnDraw(bool did_request_swap);
278   void UpdateStateOnManageTiles();
279
280   const SchedulerSettings settings_;
281
282   OutputSurfaceState output_surface_state_;
283   BeginImplFrameState begin_impl_frame_state_;
284   CommitState commit_state_;
285   ForcedRedrawOnTimeoutState forced_redraw_state_;
286
287   BeginFrameArgs begin_impl_frame_args_;
288
289   int commit_count_;
290   int current_frame_number_;
291   int last_frame_number_animate_performed_;
292   int last_frame_number_swap_performed_;
293   int last_frame_number_swap_requested_;
294   int last_frame_number_begin_main_frame_sent_;
295   int last_frame_number_update_visible_tiles_was_called_;
296
297   // manage_tiles_funnel_ is "filled" each time ManageTiles is called
298   // and "drained" on each BeginImplFrame. If the funnel gets too full,
299   // we start throttling ACTION_MANAGE_TILES such that we average one
300   // ManageTile per BeginImplFrame.
301   int manage_tiles_funnel_;
302   int consecutive_checkerboard_animations_;
303   int max_pending_swaps_;
304   int pending_swaps_;
305   bool needs_redraw_;
306   bool needs_animate_;
307   bool needs_manage_tiles_;
308   bool swap_used_incomplete_tile_;
309   bool needs_commit_;
310   bool inside_poll_for_anticipated_draw_triggers_;
311   bool visible_;
312   bool can_start_;
313   bool can_draw_;
314   bool has_pending_tree_;
315   bool pending_tree_is_ready_for_activation_;
316   bool active_tree_needs_first_draw_;
317   bool did_commit_after_animating_;
318   bool did_create_and_initialize_first_output_surface_;
319   bool impl_latency_takes_priority_;
320   bool skip_next_begin_main_frame_to_reduce_latency_;
321   bool skip_begin_main_frame_to_reduce_latency_;
322   bool continuous_painting_;
323   bool impl_latency_takes_priority_on_battery_;
324
325  private:
326   DISALLOW_COPY_AND_ASSIGN(SchedulerStateMachine);
327 };
328
329 }  // namespace cc
330
331 #endif  // CC_SCHEDULER_SCHEDULER_STATE_MACHINE_H_