Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(379)

Side by Side Diff: cc/trees/single_thread_proxy.cc

Issue 134623005: Make SingleThreadProxy a SchedulerClient (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Abort commits properly, handle swap promises, test those Created 6 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright 2011 The Chromium Authors. All rights reserved. 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 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 #include "cc/trees/single_thread_proxy.h" 5 #include "cc/trees/single_thread_proxy.h"
6 6
7 #include "base/auto_reset.h" 7 #include "base/auto_reset.h"
8 #include "base/debug/trace_event.h" 8 #include "base/debug/trace_event.h"
9 #include "cc/debug/benchmark_instrumentation.h" 9 #include "cc/debug/benchmark_instrumentation.h"
10 #include "cc/output/context_provider.h" 10 #include "cc/output/context_provider.h"
11 #include "cc/output/output_surface.h" 11 #include "cc/output/output_surface.h"
12 #include "cc/quads/draw_quad.h" 12 #include "cc/quads/draw_quad.h"
13 #include "cc/resources/prioritized_resource_manager.h" 13 #include "cc/resources/prioritized_resource_manager.h"
14 #include "cc/resources/resource_update_controller.h" 14 #include "cc/resources/resource_update_controller.h"
15 #include "cc/trees/blocking_task_runner.h" 15 #include "cc/trees/blocking_task_runner.h"
16 #include "cc/trees/layer_tree_host.h" 16 #include "cc/trees/layer_tree_host.h"
17 #include "cc/trees/layer_tree_host_single_thread_client.h" 17 #include "cc/trees/layer_tree_host_single_thread_client.h"
18 #include "cc/trees/layer_tree_impl.h" 18 #include "cc/trees/layer_tree_impl.h"
19 #include "cc/trees/scoped_swap_promise_checker.h"
19 #include "ui/gfx/frame_time.h" 20 #include "ui/gfx/frame_time.h"
20 21
21 namespace cc { 22 namespace cc {
22 23
23 scoped_ptr<Proxy> SingleThreadProxy::Create( 24 scoped_ptr<Proxy> SingleThreadProxy::Create(
24 LayerTreeHost* layer_tree_host, 25 LayerTreeHost* layer_tree_host,
25 LayerTreeHostSingleThreadClient* client, 26 LayerTreeHostSingleThreadClient* client,
26 scoped_refptr<base::SingleThreadTaskRunner> main_task_runner) { 27 scoped_refptr<base::SingleThreadTaskRunner> main_task_runner) {
27 return make_scoped_ptr( 28 return make_scoped_ptr(
28 new SingleThreadProxy(layer_tree_host, client, main_task_runner)) 29 new SingleThreadProxy(layer_tree_host, client, main_task_runner))
29 .PassAs<Proxy>(); 30 .PassAs<Proxy>();
30 } 31 }
31 32
32 SingleThreadProxy::SingleThreadProxy( 33 SingleThreadProxy::SingleThreadProxy(
33 LayerTreeHost* layer_tree_host, 34 LayerTreeHost* layer_tree_host,
34 LayerTreeHostSingleThreadClient* client, 35 LayerTreeHostSingleThreadClient* client,
35 scoped_refptr<base::SingleThreadTaskRunner> main_task_runner) 36 scoped_refptr<base::SingleThreadTaskRunner> main_task_runner)
36 : Proxy(main_task_runner, NULL), 37 : Proxy(main_task_runner, NULL),
37 layer_tree_host_(layer_tree_host), 38 layer_tree_host_(layer_tree_host),
38 client_(client), 39 client_(client),
40 timing_history_(layer_tree_host->rendering_stats_instrumentation()),
39 next_frame_is_newly_committed_frame_(false), 41 next_frame_is_newly_committed_frame_(false),
40 inside_draw_(false) { 42 inside_draw_(false),
43 defer_commits_(false),
44 commit_was_deferred_(false),
45 commit_requested_(false),
46 weak_factory_(this) {
41 TRACE_EVENT0("cc", "SingleThreadProxy::SingleThreadProxy"); 47 TRACE_EVENT0("cc", "SingleThreadProxy::SingleThreadProxy");
42 DCHECK(Proxy::IsMainThread()); 48 DCHECK(Proxy::IsMainThread());
43 DCHECK(layer_tree_host); 49 DCHECK(layer_tree_host);
44 50
45 // Impl-side painting not supported without threaded compositing. 51 // Impl-side painting not supported without threaded compositing.
46 CHECK(!layer_tree_host->settings().impl_side_painting) 52 CHECK(!layer_tree_host->settings().impl_side_painting)
47 << "Threaded compositing must be enabled to use impl-side painting."; 53 << "Threaded compositing must be enabled to use impl-side painting.";
48 } 54 }
49 55
50 void SingleThreadProxy::Start() { 56 void SingleThreadProxy::Start() {
(...skipping 19 matching lines...) Expand all
70 76
71 bool SingleThreadProxy::IsStarted() const { 77 bool SingleThreadProxy::IsStarted() const {
72 DCHECK(Proxy::IsMainThread()); 78 DCHECK(Proxy::IsMainThread());
73 return layer_tree_host_impl_; 79 return layer_tree_host_impl_;
74 } 80 }
75 81
76 void SingleThreadProxy::SetLayerTreeHostClientReady() { 82 void SingleThreadProxy::SetLayerTreeHostClientReady() {
77 TRACE_EVENT0("cc", "SingleThreadProxy::SetLayerTreeHostClientReady"); 83 TRACE_EVENT0("cc", "SingleThreadProxy::SetLayerTreeHostClientReady");
78 // Scheduling is controlled by the embedder in the single thread case, so 84 // Scheduling is controlled by the embedder in the single thread case, so
79 // nothing to do. 85 // nothing to do.
86 DCHECK(Proxy::IsMainThread());
87 DebugScopedSetImplThread impl(this);
88 if (layer_tree_host_->settings().single_thread_proxy_scheduler &&
89 !scheduler_on_impl_thread_) {
90 SchedulerSettings scheduler_settings(layer_tree_host_->settings());
91 scheduler_on_impl_thread_ = Scheduler::Create(this,
92 scheduler_settings,
93 layer_tree_host_->id(),
94 MainThreadTaskRunner());
95 scheduler_on_impl_thread_->SetCanStart();
96 scheduler_on_impl_thread_->SetVisible(layer_tree_host_impl_->visible());
97 }
80 } 98 }
81 99
82 void SingleThreadProxy::SetVisible(bool visible) { 100 void SingleThreadProxy::SetVisible(bool visible) {
83 TRACE_EVENT0("cc", "SingleThreadProxy::SetVisible"); 101 TRACE_EVENT0("cc", "SingleThreadProxy::SetVisible");
84 DebugScopedSetImplThread impl(this); 102 DebugScopedSetImplThread impl(this);
85 layer_tree_host_impl_->SetVisible(visible); 103 layer_tree_host_impl_->SetVisible(visible);
86 104 if (scheduler_on_impl_thread_)
105 scheduler_on_impl_thread_->SetVisible(layer_tree_host_impl_->visible());
87 // Changing visibility could change ShouldComposite(). 106 // Changing visibility could change ShouldComposite().
88 UpdateBackgroundAnimateTicking(); 107 UpdateBackgroundAnimateTicking();
89 } 108 }
90 109
91 void SingleThreadProxy::CreateAndInitializeOutputSurface() { 110 void SingleThreadProxy::CreateAndInitializeOutputSurface() {
92 TRACE_EVENT0( 111 TRACE_EVENT0(
93 "cc", "SingleThreadProxy::CreateAndInitializeOutputSurface"); 112 "cc", "SingleThreadProxy::CreateAndInitializeOutputSurface");
94 DCHECK(Proxy::IsMainThread()); 113 DCHECK(Proxy::IsMainThread());
95 DCHECK(layer_tree_host_->output_surface_lost()); 114 DCHECK(layer_tree_host_->output_surface_lost());
96 115
97 scoped_ptr<OutputSurface> output_surface = 116 scoped_ptr<OutputSurface> output_surface =
98 layer_tree_host_->CreateOutputSurface(); 117 layer_tree_host_->CreateOutputSurface();
99 118
100 renderer_capabilities_for_main_thread_ = RendererCapabilities(); 119 renderer_capabilities_for_main_thread_ = RendererCapabilities();
101 120
102 bool success = !!output_surface; 121 bool success = !!output_surface;
103 if (success) { 122 if (success) {
104 DebugScopedSetMainThreadBlocked main_thread_blocked(this); 123 DebugScopedSetMainThreadBlocked main_thread_blocked(this);
105 DebugScopedSetImplThread impl(this); 124 DebugScopedSetImplThread impl(this);
106 layer_tree_host_->DeleteContentsTexturesOnImplThread( 125 layer_tree_host_->DeleteContentsTexturesOnImplThread(
107 layer_tree_host_impl_->resource_provider()); 126 layer_tree_host_impl_->resource_provider());
108 success = layer_tree_host_impl_->InitializeRenderer(output_surface.Pass()); 127 success = layer_tree_host_impl_->InitializeRenderer(output_surface.Pass());
109 } 128 }
110 129
111 layer_tree_host_->OnCreateAndInitializeOutputSurfaceAttempted(success); 130 layer_tree_host_->OnCreateAndInitializeOutputSurfaceAttempted(success);
112 131
113 if (!success) { 132 if (success) {
114 // Force another recreation attempt to happen by requesting another commit. 133 if (scheduler_on_impl_thread_)
115 SetNeedsCommit(); 134 scheduler_on_impl_thread_->DidCreateAndInitializeOutputSurface();
135 } else if (Proxy::MainThreadTaskRunner()) {
136 MainThreadTaskRunner()->PostTask(
137 FROM_HERE,
138 base::Bind(&SingleThreadProxy::CreateAndInitializeOutputSurface,
139 weak_factory_.GetWeakPtr()));
116 } 140 }
117 } 141 }
118 142
119 const RendererCapabilities& SingleThreadProxy::GetRendererCapabilities() const { 143 const RendererCapabilities& SingleThreadProxy::GetRendererCapabilities() const {
120 DCHECK(Proxy::IsMainThread()); 144 DCHECK(Proxy::IsMainThread());
121 DCHECK(!layer_tree_host_->output_surface_lost()); 145 DCHECK(!layer_tree_host_->output_surface_lost());
122 return renderer_capabilities_for_main_thread_; 146 return renderer_capabilities_for_main_thread_;
123 } 147 }
124 148
125 void SingleThreadProxy::SetNeedsAnimate() { 149 void SingleThreadProxy::SetNeedsAnimate() {
126 TRACE_EVENT0("cc", "SingleThreadProxy::SetNeedsAnimate"); 150 TRACE_EVENT0("cc", "SingleThreadProxy::SetNeedsAnimate");
127 DCHECK(Proxy::IsMainThread()); 151 DCHECK(Proxy::IsMainThread());
128 client_->ScheduleAnimation(); 152 client_->ScheduleAnimation();
153 SetNeedsCommit();
129 } 154 }
130 155
131 void SingleThreadProxy::SetNeedsUpdateLayers() { 156 void SingleThreadProxy::SetNeedsUpdateLayers() {
132 TRACE_EVENT0("cc", "SingleThreadProxy::SetNeedsUpdateLayers"); 157 TRACE_EVENT0("cc", "SingleThreadProxy::SetNeedsUpdateLayers");
133 DCHECK(Proxy::IsMainThread()); 158 DCHECK(Proxy::IsMainThread());
134 client_->ScheduleComposite(); 159 SetNeedsCommit();
135 } 160 }
136 161
137 void SingleThreadProxy::DoCommit(scoped_ptr<ResourceUpdateQueue> queue) { 162 void SingleThreadProxy::DoCommit(base::TimeTicks frame_begin_time) {
138 TRACE_EVENT0("cc", "SingleThreadProxy::DoCommit"); 163 TRACE_EVENT0("cc", "SingleThreadProxy::DoCommit");
139 DCHECK(Proxy::IsMainThread()); 164 DCHECK(Proxy::IsMainThread());
165 layer_tree_host_->WillBeginMainFrame();
166 layer_tree_host_->UpdateClientAnimations(frame_begin_time);
167 layer_tree_host_->AnimateLayers(frame_begin_time);
168 layer_tree_host_->Layout();
169 commit_requested_ = false;
170
171 if (PrioritizedResourceManager* contents_texture_manager =
172 layer_tree_host_->contents_texture_manager()) {
173 contents_texture_manager->UnlinkAndClearEvictedBackings();
174 contents_texture_manager->SetMaxMemoryLimitBytes(
175 layer_tree_host_impl_->memory_allocation_limit_bytes());
176 contents_texture_manager->SetExternalPriorityCutoff(
177 layer_tree_host_impl_->memory_allocation_priority_cutoff());
178 }
179
180 scoped_ptr<ResourceUpdateQueue> queue =
181 make_scoped_ptr(new ResourceUpdateQueue);
182
183 layer_tree_host_->UpdateLayers(queue.get());
184
185 layer_tree_host_->WillCommit();
186
140 // Commit immediately. 187 // Commit immediately.
141 { 188 {
142 DebugScopedSetMainThreadBlocked main_thread_blocked(this); 189 DebugScopedSetMainThreadBlocked main_thread_blocked(this);
143 DebugScopedSetImplThread impl(this); 190 DebugScopedSetImplThread impl(this);
144 191
145 // This CapturePostTasks should be destroyed before CommitComplete() is 192 // This CapturePostTasks should be destroyed before CommitComplete() is
146 // called since that goes out to the embedder, and we want the embedder 193 // called since that goes out to the embedder, and we want the embedder
147 // to receive its callbacks before that. 194 // to receive its callbacks before that.
148 BlockingTaskRunner::CapturePostTasks blocked; 195 BlockingTaskRunner::CapturePostTasks blocked;
149 196
150 layer_tree_host_impl_->BeginCommit(); 197 layer_tree_host_impl_->BeginCommit();
151 198
152 if (PrioritizedResourceManager* contents_texture_manager = 199 if (PrioritizedResourceManager* contents_texture_manager =
153 layer_tree_host_->contents_texture_manager()) { 200 layer_tree_host_->contents_texture_manager()) {
154 contents_texture_manager->PushTexturePrioritiesToBackings(); 201 contents_texture_manager->PushTexturePrioritiesToBackings();
155 } 202 }
156 layer_tree_host_->BeginCommitOnImplThread(layer_tree_host_impl_.get()); 203 layer_tree_host_->BeginCommitOnImplThread(layer_tree_host_impl_.get());
157 204
158 scoped_ptr<ResourceUpdateController> update_controller = 205 scoped_ptr<ResourceUpdateController> update_controller =
159 ResourceUpdateController::Create( 206 ResourceUpdateController::Create(
160 NULL, 207 NULL,
161 Proxy::MainThreadTaskRunner(), 208 MainThreadTaskRunner(),
162 queue.Pass(), 209 queue.Pass(),
163 layer_tree_host_impl_->resource_provider()); 210 layer_tree_host_impl_->resource_provider());
164 update_controller->Finalize(); 211 update_controller->Finalize();
165 212
166 if (layer_tree_host_impl_->EvictedUIResourcesExist()) 213 if (layer_tree_host_impl_->EvictedUIResourcesExist())
167 layer_tree_host_->RecreateUIResources(); 214 layer_tree_host_->RecreateUIResources();
168 215
169 layer_tree_host_->FinishCommitOnImplThread(layer_tree_host_impl_.get()); 216 layer_tree_host_->FinishCommitOnImplThread(layer_tree_host_impl_.get());
170 217
171 layer_tree_host_impl_->CommitComplete(); 218 layer_tree_host_impl_->CommitComplete();
172 219
220 UpdateBackgroundAnimateTicking();
221
173 #if DCHECK_IS_ON 222 #if DCHECK_IS_ON
174 // In the single-threaded case, the scale and scroll deltas should never be 223 // In the single-threaded case, the scale and scroll deltas should never be
175 // touched on the impl layer tree. 224 // touched on the impl layer tree.
176 scoped_ptr<ScrollAndScaleSet> scroll_info = 225 scoped_ptr<ScrollAndScaleSet> scroll_info =
177 layer_tree_host_impl_->ProcessScrollDeltas(); 226 layer_tree_host_impl_->ProcessScrollDeltas();
178 DCHECK(!scroll_info->scrolls.size()); 227 DCHECK(!scroll_info->scrolls.size());
179 DCHECK_EQ(1.f, scroll_info->page_scale_delta); 228 DCHECK_EQ(1.f, scroll_info->page_scale_delta);
180 #endif 229 #endif
181 230
182 RenderingStatsInstrumentation* stats_instrumentation = 231 RenderingStatsInstrumentation* stats_instrumentation =
183 layer_tree_host_->rendering_stats_instrumentation(); 232 layer_tree_host_->rendering_stats_instrumentation();
184 benchmark_instrumentation::IssueMainThreadRenderingStatsEvent( 233 benchmark_instrumentation::IssueMainThreadRenderingStatsEvent(
185 stats_instrumentation->main_thread_rendering_stats()); 234 stats_instrumentation->main_thread_rendering_stats());
186 stats_instrumentation->AccumulateAndClearMainThreadStats(); 235 stats_instrumentation->AccumulateAndClearMainThreadStats();
187 } 236 }
188 layer_tree_host_->CommitComplete(); 237 layer_tree_host_->CommitComplete();
238 layer_tree_host_->DidBeginMainFrame();
239 timing_history_.DidCommit();
240
189 next_frame_is_newly_committed_frame_ = true; 241 next_frame_is_newly_committed_frame_ = true;
190 } 242 }
191 243
192 void SingleThreadProxy::SetNeedsCommit() { 244 void SingleThreadProxy::SetNeedsCommit() {
193 DCHECK(Proxy::IsMainThread()); 245 DCHECK(Proxy::IsMainThread());
246 DebugScopedSetImplThread impl(this);
194 client_->ScheduleComposite(); 247 client_->ScheduleComposite();
248 if (scheduler_on_impl_thread_)
249 scheduler_on_impl_thread_->SetNeedsCommit();
250 commit_requested_ = true;
195 } 251 }
196 252
197 void SingleThreadProxy::SetNeedsRedraw(const gfx::Rect& damage_rect) { 253 void SingleThreadProxy::SetNeedsRedraw(const gfx::Rect& damage_rect) {
198 TRACE_EVENT0("cc", "SingleThreadProxy::SetNeedsRedraw"); 254 TRACE_EVENT0("cc", "SingleThreadProxy::SetNeedsRedraw");
255 DCHECK(Proxy::IsMainThread());
256 DebugScopedSetImplThread impl(this);
257 client_->ScheduleComposite();
199 SetNeedsRedrawRectOnImplThread(damage_rect); 258 SetNeedsRedrawRectOnImplThread(damage_rect);
200 client_->ScheduleComposite();
201 } 259 }
202 260
203 void SingleThreadProxy::SetNextCommitWaitsForActivation() { 261 void SingleThreadProxy::SetNextCommitWaitsForActivation() {
204 // There is no activation here other than commit. So do nothing. 262 // There is no activation here other than commit. So do nothing.
263 DCHECK(Proxy::IsMainThread());
205 } 264 }
206 265
207 void SingleThreadProxy::SetDeferCommits(bool defer_commits) { 266 void SingleThreadProxy::SetDeferCommits(bool defer_commits) {
267 DCHECK(Proxy::IsMainThread());
268 // Deferring commits only makes sense if there's a scheduler.
269 if (!scheduler_on_impl_thread_)
270 return;
271 if (defer_commits_ == defer_commits)
272 return;
273
274 if (defer_commits)
275 TRACE_EVENT_ASYNC_BEGIN0("cc", "SingleThreadProxy::SetDeferCommits", this);
276 else
277 TRACE_EVENT_ASYNC_END0("cc", "SingleThreadProxy::SetDeferCommits", this);
278
279 defer_commits_ = defer_commits;
280 if (!defer_commits_ && commit_was_deferred_) {
281 commit_was_deferred_ = false;
282 BeginMainFrame();
enne (OOO) 2014/08/09 00:04:43 This had to change to have the same swap promise b
283 }
208 } 284 }
209 285
210 bool SingleThreadProxy::CommitRequested() const { return false; } 286 bool SingleThreadProxy::CommitRequested() const {
287 DCHECK(Proxy::IsMainThread());
288 return commit_requested_;
289 }
211 290
212 bool SingleThreadProxy::BeginMainFrameRequested() const { return false; } 291 bool SingleThreadProxy::BeginMainFrameRequested() const {
292 DCHECK(Proxy::IsMainThread());
293 return commit_requested_;
294 }
213 295
214 size_t SingleThreadProxy::MaxPartialTextureUpdates() const { 296 size_t SingleThreadProxy::MaxPartialTextureUpdates() const {
215 return std::numeric_limits<size_t>::max(); 297 return std::numeric_limits<size_t>::max();
216 } 298 }
217 299
218 void SingleThreadProxy::Stop() { 300 void SingleThreadProxy::Stop() {
219 TRACE_EVENT0("cc", "SingleThreadProxy::stop"); 301 TRACE_EVENT0("cc", "SingleThreadProxy::stop");
220 DCHECK(Proxy::IsMainThread()); 302 DCHECK(Proxy::IsMainThread());
221 { 303 {
222 DebugScopedSetMainThreadBlocked main_thread_blocked(this); 304 DebugScopedSetMainThreadBlocked main_thread_blocked(this);
223 DebugScopedSetImplThread impl(this); 305 DebugScopedSetImplThread impl(this);
224 306
225 BlockingTaskRunner::CapturePostTasks blocked; 307 BlockingTaskRunner::CapturePostTasks blocked;
226 layer_tree_host_->DeleteContentsTexturesOnImplThread( 308 layer_tree_host_->DeleteContentsTexturesOnImplThread(
227 layer_tree_host_impl_->resource_provider()); 309 layer_tree_host_impl_->resource_provider());
310 scheduler_on_impl_thread_.reset();
228 layer_tree_host_impl_.reset(); 311 layer_tree_host_impl_.reset();
229 } 312 }
230 layer_tree_host_ = NULL; 313 layer_tree_host_ = NULL;
231 } 314 }
232 315
233 void SingleThreadProxy::OnCanDrawStateChanged(bool can_draw) { 316 void SingleThreadProxy::OnCanDrawStateChanged(bool can_draw) {
234 TRACE_EVENT1( 317 TRACE_EVENT1(
235 "cc", "SingleThreadProxy::OnCanDrawStateChanged", "can_draw", can_draw); 318 "cc", "SingleThreadProxy::OnCanDrawStateChanged", "can_draw", can_draw);
236 DCHECK(Proxy::IsImplThread()); 319 DCHECK(Proxy::IsImplThread());
237 UpdateBackgroundAnimateTicking(); 320 UpdateBackgroundAnimateTicking();
321 if (scheduler_on_impl_thread_)
322 scheduler_on_impl_thread_->SetCanDraw(can_draw);
238 } 323 }
239 324
240 void SingleThreadProxy::NotifyReadyToActivate() { 325 void SingleThreadProxy::NotifyReadyToActivate() {
241 // Thread-only feature. 326 // Impl-side painting only.
242 NOTREACHED(); 327 NOTREACHED();
243 } 328 }
244 329
245 void SingleThreadProxy::SetNeedsRedrawOnImplThread() { 330 void SingleThreadProxy::SetNeedsRedrawOnImplThread() {
246 client_->ScheduleComposite(); 331 client_->ScheduleComposite();
332 if (scheduler_on_impl_thread_)
333 scheduler_on_impl_thread_->SetNeedsRedraw();
247 } 334 }
248 335
249 void SingleThreadProxy::SetNeedsAnimateOnImplThread() { 336 void SingleThreadProxy::SetNeedsAnimateOnImplThread() {
250 SetNeedsRedrawOnImplThread(); 337 SetNeedsRedrawOnImplThread();
251 } 338 }
252 339
253 void SingleThreadProxy::SetNeedsManageTilesOnImplThread() { 340 void SingleThreadProxy::SetNeedsManageTilesOnImplThread() {
254 // Thread-only/Impl-side-painting-only feature. 341 // Impl-side painting only.
255 NOTREACHED(); 342 NOTREACHED();
256 } 343 }
257 344
258 void SingleThreadProxy::SetNeedsRedrawRectOnImplThread( 345 void SingleThreadProxy::SetNeedsRedrawRectOnImplThread(
259 const gfx::Rect& damage_rect) { 346 const gfx::Rect& damage_rect) {
260 // TODO(brianderson): Once we move render_widget scheduling into this class,
261 // we can treat redraw requests more efficiently than CommitAndRedraw
262 // requests.
263 layer_tree_host_impl_->SetViewportDamage(damage_rect); 347 layer_tree_host_impl_->SetViewportDamage(damage_rect);
264 SetNeedsCommit(); 348 SetNeedsRedrawOnImplThread();
265 } 349 }
266 350
267 void SingleThreadProxy::DidInitializeVisibleTileOnImplThread() { 351 void SingleThreadProxy::DidInitializeVisibleTileOnImplThread() {
268 // Impl-side painting only. 352 // Impl-side painting only.
269 NOTREACHED(); 353 NOTREACHED();
270 } 354 }
271 355
272 void SingleThreadProxy::SetNeedsCommitOnImplThread() { 356 void SingleThreadProxy::SetNeedsCommitOnImplThread() {
273 client_->ScheduleComposite(); 357 client_->ScheduleComposite();
358 if (scheduler_on_impl_thread_)
359 scheduler_on_impl_thread_->SetNeedsCommit();
274 } 360 }
275 361
276 void SingleThreadProxy::PostAnimationEventsToMainThreadOnImplThread( 362 void SingleThreadProxy::PostAnimationEventsToMainThreadOnImplThread(
277 scoped_ptr<AnimationEventsVector> events) { 363 scoped_ptr<AnimationEventsVector> events) {
278 TRACE_EVENT0( 364 TRACE_EVENT0(
279 "cc", "SingleThreadProxy::PostAnimationEventsToMainThreadOnImplThread"); 365 "cc", "SingleThreadProxy::PostAnimationEventsToMainThreadOnImplThread");
280 DCHECK(Proxy::IsImplThread()); 366 DCHECK(Proxy::IsImplThread());
281 DebugScopedSetMainThread main(this); 367 DebugScopedSetMainThread main(this);
282 layer_tree_host_->SetAnimationEvents(events.Pass()); 368 layer_tree_host_->SetAnimationEvents(events.Pass());
283 } 369 }
(...skipping 16 matching lines...) Expand all
300 } 386 }
301 387
302 bool SingleThreadProxy::IsInsideDraw() { return inside_draw_; } 388 bool SingleThreadProxy::IsInsideDraw() { return inside_draw_; }
303 389
304 void SingleThreadProxy::UpdateRendererCapabilitiesOnImplThread() { 390 void SingleThreadProxy::UpdateRendererCapabilitiesOnImplThread() {
305 DCHECK(IsImplThread()); 391 DCHECK(IsImplThread());
306 renderer_capabilities_for_main_thread_ = 392 renderer_capabilities_for_main_thread_ =
307 layer_tree_host_impl_->GetRendererCapabilities().MainThreadCapabilities(); 393 layer_tree_host_impl_->GetRendererCapabilities().MainThreadCapabilities();
308 } 394 }
309 395
396 void SingleThreadProxy::DidManageTiles() {
397 // Impl-side painting only.
398 NOTREACHED();
399 }
400
310 void SingleThreadProxy::DidLoseOutputSurfaceOnImplThread() { 401 void SingleThreadProxy::DidLoseOutputSurfaceOnImplThread() {
311 TRACE_EVENT0("cc", "SingleThreadProxy::DidLoseOutputSurfaceOnImplThread"); 402 TRACE_EVENT0("cc", "SingleThreadProxy::DidLoseOutputSurfaceOnImplThread");
312 // Cause a commit so we can notice the lost context. 403 {
313 SetNeedsCommitOnImplThread(); 404 DebugScopedSetMainThread main(this);
405 // This must happen before we notify the scheduler as it may try to recreate
406 // the output surface if already in BEGIN_IMPL_FRAME_STATE_IDLE.
407 layer_tree_host_->DidLoseOutputSurface();
408 }
314 client_->DidAbortSwapBuffers(); 409 client_->DidAbortSwapBuffers();
410 if (scheduler_on_impl_thread_)
411 scheduler_on_impl_thread_->DidLoseOutputSurface();
315 } 412 }
316 413
317 void SingleThreadProxy::DidSwapBuffersOnImplThread() { 414 void SingleThreadProxy::DidSwapBuffersOnImplThread() {
415 TRACE_EVENT0("cc", "SingleThreadProxy::DidSwapBuffersOnImplThread");
416 if (scheduler_on_impl_thread_)
417 scheduler_on_impl_thread_->DidSwapBuffers();
318 client_->DidPostSwapBuffers(); 418 client_->DidPostSwapBuffers();
319 } 419 }
320 420
321 void SingleThreadProxy::DidSwapBuffersCompleteOnImplThread() { 421 void SingleThreadProxy::DidSwapBuffersCompleteOnImplThread() {
322 TRACE_EVENT0("cc", "SingleThreadProxy::DidSwapBuffersCompleteOnImplThread"); 422 TRACE_EVENT0("cc", "SingleThreadProxy::DidSwapBuffersCompleteOnImplThread");
323 client_->DidCompleteSwapBuffers(); 423 if (scheduler_on_impl_thread_)
424 scheduler_on_impl_thread_->DidSwapBuffersComplete();
425 layer_tree_host_->DidCompleteSwapBuffers();
324 } 426 }
325 427
326 // Called by the legacy scheduling path (e.g. where render_widget does the 428 void SingleThreadProxy::BeginFrame(const BeginFrameArgs& args) {
327 // scheduling) 429 TRACE_EVENT0("cc", "SingleThreadProxy::BeginFrame");
430 if (scheduler_on_impl_thread_)
431 scheduler_on_impl_thread_->BeginImplFrame(args);
432 }
433
328 void SingleThreadProxy::CompositeImmediately(base::TimeTicks frame_begin_time) { 434 void SingleThreadProxy::CompositeImmediately(base::TimeTicks frame_begin_time) {
329 TRACE_EVENT0("cc", "SingleThreadProxy::CompositeImmediately"); 435 TRACE_EVENT0("cc", "SingleThreadProxy::CompositeImmediately");
330 DCHECK(Proxy::IsMainThread()); 436 DCHECK(Proxy::IsMainThread());
331 DCHECK(!layer_tree_host_->output_surface_lost()); 437 DCHECK(!layer_tree_host_->output_surface_lost());
332 438
333 layer_tree_host_->AnimateLayers(frame_begin_time); 439 DoCommit(frame_begin_time);
334
335 if (PrioritizedResourceManager* contents_texture_manager =
336 layer_tree_host_->contents_texture_manager()) {
337 contents_texture_manager->UnlinkAndClearEvictedBackings();
338 contents_texture_manager->SetMaxMemoryLimitBytes(
339 layer_tree_host_impl_->memory_allocation_limit_bytes());
340 contents_texture_manager->SetExternalPriorityCutoff(
341 layer_tree_host_impl_->memory_allocation_priority_cutoff());
342 }
343
344 scoped_ptr<ResourceUpdateQueue> queue =
345 make_scoped_ptr(new ResourceUpdateQueue);
346 layer_tree_host_->UpdateLayers(queue.get());
347 layer_tree_host_->WillCommit();
348 DoCommit(queue.Pass());
349 layer_tree_host_->DidBeginMainFrame();
350 440
351 LayerTreeHostImpl::FrameData frame; 441 LayerTreeHostImpl::FrameData frame;
352 if (DoComposite(frame_begin_time, &frame)) { 442 DoComposite(frame_begin_time, &frame);
353 {
354 DebugScopedSetMainThreadBlocked main_thread_blocked(this);
355 DebugScopedSetImplThread impl(this);
356
357 // This CapturePostTasks should be destroyed before
358 // DidCommitAndDrawFrame() is called since that goes out to the embedder,
359 // and we want the embedder to receive its callbacks before that.
360 // NOTE: This maintains consistent ordering with the ThreadProxy since
361 // the DidCommitAndDrawFrame() must be post-tasked from the impl thread
362 // there as the main thread is not blocked, so any posted tasks inside
363 // the swap buffers will execute first.
364 BlockingTaskRunner::CapturePostTasks blocked;
365
366 layer_tree_host_impl_->SwapBuffers(frame);
367 }
368 DidSwapFrame();
369 }
370 } 443 }
371 444
372 void SingleThreadProxy::AsValueInto(base::debug::TracedValue* state) const { 445 void SingleThreadProxy::AsValueInto(base::debug::TracedValue* state) const {
373 // The following line casts away const modifiers because it is just 446 // The following line casts away const modifiers because it is just
374 // setting debug state. We still want the AsValue() function and its 447 // setting debug state. We still want the AsValue() function and its
375 // call chain to be const throughout. 448 // call chain to be const throughout.
376 DebugScopedSetImplThread impl(const_cast<SingleThreadProxy*>(this)); 449 DebugScopedSetImplThread impl(const_cast<SingleThreadProxy*>(this));
377 450
378 state->BeginDictionary("layer_tree_host_impl"); 451 state->BeginDictionary("layer_tree_host_impl");
379 layer_tree_host_impl_->AsValueInto(state); 452 layer_tree_host_impl_->AsValueInto(state);
(...skipping 19 matching lines...) Expand all
399 return layer_tree_host_impl_->visible() && 472 return layer_tree_host_impl_->visible() &&
400 layer_tree_host_impl_->CanDraw(); 473 layer_tree_host_impl_->CanDraw();
401 } 474 }
402 475
403 void SingleThreadProxy::UpdateBackgroundAnimateTicking() { 476 void SingleThreadProxy::UpdateBackgroundAnimateTicking() {
404 DCHECK(Proxy::IsImplThread()); 477 DCHECK(Proxy::IsImplThread());
405 layer_tree_host_impl_->UpdateBackgroundAnimateTicking( 478 layer_tree_host_impl_->UpdateBackgroundAnimateTicking(
406 !ShouldComposite() && layer_tree_host_impl_->active_tree()->root_layer()); 479 !ShouldComposite() && layer_tree_host_impl_->active_tree()->root_layer());
407 } 480 }
408 481
409 bool SingleThreadProxy::DoComposite( 482 DrawResult SingleThreadProxy::DoComposite(base::TimeTicks frame_begin_time,
410 base::TimeTicks frame_begin_time, 483 LayerTreeHostImpl::FrameData* frame) {
411 LayerTreeHostImpl::FrameData* frame) {
412 TRACE_EVENT0("cc", "SingleThreadProxy::DoComposite"); 484 TRACE_EVENT0("cc", "SingleThreadProxy::DoComposite");
413 DCHECK(!layer_tree_host_->output_surface_lost()); 485 DCHECK(!layer_tree_host_->output_surface_lost());
414 486
415 bool lost_output_surface = false;
416 { 487 {
417 DebugScopedSetImplThread impl(this); 488 DebugScopedSetImplThread impl(this);
418 base::AutoReset<bool> mark_inside(&inside_draw_, true); 489 base::AutoReset<bool> mark_inside(&inside_draw_, true);
419 490
420 // We guard PrepareToDraw() with CanDraw() because it always returns a valid 491 // We guard PrepareToDraw() with CanDraw() because it always returns a valid
421 // frame, so can only be used when such a frame is possible. Since 492 // frame, so can only be used when such a frame is possible. Since
422 // DrawLayers() depends on the result of PrepareToDraw(), it is guarded on 493 // DrawLayers() depends on the result of PrepareToDraw(), it is guarded on
423 // CanDraw() as well. 494 // CanDraw() as well.
424 if (!ShouldComposite()) { 495 if (!ShouldComposite()) {
425 UpdateBackgroundAnimateTicking(); 496 UpdateBackgroundAnimateTicking();
426 return false; 497 return DRAW_ABORTED_CANT_DRAW;
427 } 498 }
428 499
500 timing_history_.DidStartDrawing();
501
429 layer_tree_host_impl_->Animate( 502 layer_tree_host_impl_->Animate(
430 layer_tree_host_impl_->CurrentFrameTimeTicks()); 503 layer_tree_host_impl_->CurrentFrameTimeTicks());
431 UpdateBackgroundAnimateTicking(); 504 UpdateBackgroundAnimateTicking();
432 505
433 if (!layer_tree_host_impl_->IsContextLost()) { 506 if (!layer_tree_host_impl_->IsContextLost()) {
434 layer_tree_host_impl_->PrepareToDraw(frame); 507 layer_tree_host_impl_->PrepareToDraw(frame);
435 layer_tree_host_impl_->DrawLayers(frame, frame_begin_time); 508 layer_tree_host_impl_->DrawLayers(frame, frame_begin_time);
436 layer_tree_host_impl_->DidDrawAllLayers(*frame); 509 layer_tree_host_impl_->DidDrawAllLayers(*frame);
437 } 510 }
438 lost_output_surface = layer_tree_host_impl_->IsContextLost();
439 511
440 bool start_ready_animations = true; 512 bool start_ready_animations = true;
441 layer_tree_host_impl_->UpdateAnimationState(start_ready_animations); 513 layer_tree_host_impl_->UpdateAnimationState(start_ready_animations);
442 514
443 layer_tree_host_impl_->ResetCurrentFrameTimeForNextFrame(); 515 layer_tree_host_impl_->ResetCurrentFrameTimeForNextFrame();
516
517 timing_history_.DidFinishDrawing();
444 } 518 }
445 519
446 if (lost_output_surface) { 520 {
447 layer_tree_host_->DidLoseOutputSurface(); 521 DebugScopedSetImplThread impl(this);
448 return false; 522
523 if (layer_tree_host_impl_->IsContextLost()) {
524 DidLoseOutputSurfaceOnImplThread();
525 } else {
526 // This CapturePostTasks should be destroyed before
527 // DidCommitAndDrawFrame() is called since that goes out to the
528 // embedder,
529 // and we want the embedder to receive its callbacks before that.
530 // NOTE: This maintains consistent ordering with the ThreadProxy since
531 // the DidCommitAndDrawFrame() must be post-tasked from the impl thread
532 // there as the main thread is not blocked, so any posted tasks inside
533 // the swap buffers will execute first.
534 DebugScopedSetMainThreadBlocked main_thread_blocked(this);
535
536 BlockingTaskRunner::CapturePostTasks blocked;
537 layer_tree_host_impl_->SwapBuffers(*frame);
538 }
449 } 539 }
540 DidCommitAndDrawFrame();
450 541
451 return true; 542 return DRAW_SUCCESS;
452 } 543 }
453 544
454 void SingleThreadProxy::DidSwapFrame() { 545 void SingleThreadProxy::DidCommitAndDrawFrame() {
455 if (next_frame_is_newly_committed_frame_) { 546 if (next_frame_is_newly_committed_frame_) {
547 DebugScopedSetMainThread main(this);
456 next_frame_is_newly_committed_frame_ = false; 548 next_frame_is_newly_committed_frame_ = false;
457 layer_tree_host_->DidCommitAndDrawFrame(); 549 layer_tree_host_->DidCommitAndDrawFrame();
458 } 550 }
459 } 551 }
460 552
461 bool SingleThreadProxy::CommitPendingForTesting() { return false; } 553 bool SingleThreadProxy::CommitPendingForTesting() { return false; }
462 554
555 void SingleThreadProxy::SetNeedsBeginFrame(bool enable) {
556 layer_tree_host_impl_->SetNeedsBeginFrame(enable);
557 }
558
559 void SingleThreadProxy::WillBeginImplFrame(const BeginFrameArgs& args) {
560 layer_tree_host_impl_->WillBeginImplFrame(args);
561 }
562
563 void SingleThreadProxy::ScheduledActionSendBeginMainFrame() {
564 TRACE_EVENT0("cc", "SingleThreadProxy::ScheduledActionSendBeginMainFrame");
565 // Although this proxy is single-threaded, it's problematic to synchronously
566 // have BeginMainFrame happen after ScheduledActionSendBeginMainFrame. This
567 // could cause a commit to occur in between a series of SetNeedsCommit calls
568 // (i.e. property modifications) causing some to fall on one frame and some to
569 // fall on the next. Doing it asynchronously instead matches the semantics of
570 // ThreadProxy::SetNeedsCommit where SetNeedsCommit will not cause a
571 // synchronous commit.
572 MainThreadTaskRunner()->PostTask(
573 FROM_HERE,
574 base::Bind(&SingleThreadProxy::BeginMainFrame,
575 weak_factory_.GetWeakPtr()));
576 }
577
578 void SingleThreadProxy::BeginMainFrame() {
579 if (defer_commits_) {
580 DCHECK(!commit_was_deferred_);
581 commit_was_deferred_ = true;
582 layer_tree_host_->DidDeferCommit();
583 return;
584 }
585
586 // This checker assumes NotifyReadyToCommit below causes a synchronous commit.
587 ScopedSwapPromiseChecker swap_promise_checker(layer_tree_host_);
588
589 if (!layer_tree_host_->visible()) {
590 TRACE_EVENT_INSTANT0("cc", "EarlyOut_NotVisible", TRACE_EVENT_SCOPE_THREAD);
591 BeginMainFrameAbortedOnImplThread();
592 return;
593 }
594
595 if (layer_tree_host_->output_surface_lost()) {
enne (OOO) 2014/08/09 00:04:43 Early-outing on the lost output surface here preve
596 TRACE_EVENT_INSTANT0(
597 "cc", "EarlyOut_OutputSurfaceLost", TRACE_EVENT_SCOPE_THREAD);
598 BeginMainFrameAbortedOnImplThread();
599 return;
600 }
601
602 timing_history_.DidBeginMainFrame();
603
604 DCHECK(scheduler_on_impl_thread_);
605 scheduler_on_impl_thread_->NotifyBeginMainFrameStarted();
606 scheduler_on_impl_thread_->NotifyReadyToCommit();
607 }
608
609 void SingleThreadProxy::BeginMainFrameAbortedOnImplThread() {
610 DebugScopedSetImplThread impl(this);
611 DCHECK(scheduler_on_impl_thread_->CommitPending());
612 DCHECK(!layer_tree_host_impl_->pending_tree());
613
614 // TODO(enne): SingleThreadProxy does not support cancelling commits yet so
615 // did_handle is always false.
616 bool did_handle = false;
617 layer_tree_host_impl_->BeginMainFrameAborted(did_handle);
618 scheduler_on_impl_thread_->BeginMainFrameAborted(did_handle);
619 }
620
621 DrawResult SingleThreadProxy::ScheduledActionDrawAndSwapIfPossible() {
622 DebugScopedSetImplThread impl(this);
623 if (layer_tree_host_impl_->IsContextLost()) {
624 DidCommitAndDrawFrame();
625 return DRAW_SUCCESS;
626 }
627
628 LayerTreeHostImpl::FrameData frame;
629 return DoComposite(layer_tree_host_impl_->CurrentFrameTimeTicks(), &frame);
630 }
631
632 DrawResult SingleThreadProxy::ScheduledActionDrawAndSwapForced() {
633 NOTREACHED();
634 return INVALID_RESULT;
635 }
636
637 void SingleThreadProxy::ScheduledActionCommit() {
638 DebugScopedSetMainThread main(this);
639 DoCommit(layer_tree_host_impl_->CurrentFrameTimeTicks());
640 }
641
642 void SingleThreadProxy::ScheduledActionAnimate() {
643 TRACE_EVENT0("cc", "ScheduledActionAnimate");
644 layer_tree_host_impl_->Animate(
645 layer_tree_host_impl_->CurrentFrameTimeTicks());
646 }
647
648 void SingleThreadProxy::ScheduledActionUpdateVisibleTiles() {
649 // Impl-side painting only.
650 NOTREACHED();
651 }
652
653 void SingleThreadProxy::ScheduledActionActivateSyncTree() {
654 }
655
656 void SingleThreadProxy::ScheduledActionBeginOutputSurfaceCreation() {
657 DebugScopedSetMainThread main(this);
658 DCHECK(scheduler_on_impl_thread_);
659 // If possible, create the output surface in a post task. Synchronously
660 // creating the output surface makes tests more awkward since this differs
661 // from the ThreadProxy behavior. However, sometimes there is no
662 // task runner.
663 if (Proxy::MainThreadTaskRunner()) {
664 MainThreadTaskRunner()->PostTask(
665 FROM_HERE,
666 base::Bind(&SingleThreadProxy::CreateAndInitializeOutputSurface,
667 weak_factory_.GetWeakPtr()));
668 } else {
669 CreateAndInitializeOutputSurface();
670 }
671 }
672
673 void SingleThreadProxy::ScheduledActionManageTiles() {
674 // Impl-side painting only.
675 NOTREACHED();
676 }
677
678 void SingleThreadProxy::DidAnticipatedDrawTimeChange(base::TimeTicks time) {
679 }
680
681 base::TimeDelta SingleThreadProxy::DrawDurationEstimate() {
682 return timing_history_.DrawDurationEstimate();
683 }
684
685 base::TimeDelta SingleThreadProxy::BeginMainFrameToCommitDurationEstimate() {
686 return timing_history_.BeginMainFrameToCommitDurationEstimate();
687 }
688
689 base::TimeDelta SingleThreadProxy::CommitToActivateDurationEstimate() {
690 return timing_history_.CommitToActivateDurationEstimate();
691 }
692
693 void SingleThreadProxy::DidBeginImplFrameDeadline() {
694 layer_tree_host_impl_->ResetCurrentFrameTimeForNextFrame();
695 }
696
463 } // namespace cc 697 } // namespace cc
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698