OLD | NEW |
---|---|
1 // Copyright 2012 The Chromium Authors. All rights reserved. | 1 // Copyright 2012 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/tile_manager.h" | 5 #include "cc/tile_manager.h" |
6 | 6 |
7 #include <algorithm> | 7 #include <algorithm> |
8 | 8 |
9 #include "base/bind.h" | 9 #include "base/bind.h" |
10 #include "base/command_line.h" | 10 #include "base/command_line.h" |
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
50 can_be_freed(true), | 50 can_be_freed(true), |
51 resource_is_being_initialized(false), | 51 resource_is_being_initialized(false), |
52 contents_swizzled(false) { | 52 contents_swizzled(false) { |
53 } | 53 } |
54 | 54 |
55 ManagedTileState::~ManagedTileState() { | 55 ManagedTileState::~ManagedTileState() { |
56 DCHECK(!resource); | 56 DCHECK(!resource); |
57 DCHECK(!resource_is_being_initialized); | 57 DCHECK(!resource_is_being_initialized); |
58 } | 58 } |
59 | 59 |
60 PendingSetPixels::PendingSetPixels( | |
nduca
2012/12/04 23:59:26
I think this is overkill. Just do what I told you
reveman
2012/12/05 23:21:19
Done.
| |
61 Tile* tile, scoped_ptr<ResourcePool::Resource> resource) | |
62 : tile_(tile), | |
63 resource_(resource.Pass()) { | |
64 } | |
65 | |
66 PendingSetPixels::~PendingSetPixels() { | |
67 } | |
68 | |
60 TileManager::TileManager( | 69 TileManager::TileManager( |
61 TileManagerClient* client, | 70 TileManagerClient* client, |
62 ResourceProvider* resource_provider, | 71 ResourceProvider* resource_provider, |
63 size_t num_raster_threads) | 72 size_t num_raster_threads) |
64 : client_(client), | 73 : client_(client), |
65 resource_pool_(ResourcePool::Create(resource_provider, | 74 resource_pool_(ResourcePool::Create(resource_provider, |
66 Renderer::ImplPool)), | 75 Renderer::ImplPool)), |
67 manage_tiles_pending_(false), | 76 manage_tiles_pending_(false), |
77 in_prepare_to_draw_(false), | |
68 pending_raster_tasks_(0), | 78 pending_raster_tasks_(0), |
69 num_raster_threads_(num_raster_threads), | 79 num_raster_threads_(num_raster_threads), |
70 worker_pool_(new base::SequencedWorkerPool(num_raster_threads, | 80 worker_pool_(new base::SequencedWorkerPool(num_raster_threads, |
71 kRasterThreadNamePrefix)) { | 81 kRasterThreadNamePrefix)) { |
72 } | 82 } |
73 | 83 |
74 TileManager::~TileManager() { | 84 TileManager::~TileManager() { |
75 // Reset global state and manage. This should cause | 85 // Reset global state and manage. This should cause |
76 // our memory usage to drop to zero. | 86 // our memory usage to drop to zero. |
77 global_state_ = GlobalStateThatImpactsTilePriority(); | 87 global_state_ = GlobalStateThatImpactsTilePriority(); |
(...skipping 137 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
215 // Sort by bin. | 225 // Sort by bin. |
216 std::sort(tiles_.begin(), tiles_.end(), BinComparator()); | 226 std::sort(tiles_.begin(), tiles_.end(), BinComparator()); |
217 | 227 |
218 // Assign gpu memory and determine what tiles need to be rasterized. | 228 // Assign gpu memory and determine what tiles need to be rasterized. |
219 AssignGpuMemoryToTiles(); | 229 AssignGpuMemoryToTiles(); |
220 | 230 |
221 // Finally, kick the rasterizer. | 231 // Finally, kick the rasterizer. |
222 DispatchMoreRasterTasks(); | 232 DispatchMoreRasterTasks(); |
223 } | 233 } |
224 | 234 |
235 void TileManager::PrepareToDraw() { | |
nduca
2012/12/04 23:59:26
Lets call this CheckForCompletedUploads() so its o
reveman
2012/12/05 23:21:19
Done. Now CheckForCompletedSetPixels().
| |
236 in_prepare_to_draw_ = true; | |
237 CheckForPendingSetPixelsCompletion(); | |
238 in_prepare_to_draw_ = false; | |
239 } | |
240 | |
225 void TileManager::renderingStats(RenderingStats* stats) { | 241 void TileManager::renderingStats(RenderingStats* stats) { |
226 stats->totalRasterizeTimeInSeconds = | 242 stats->totalRasterizeTimeInSeconds = |
227 rendering_stats_.totalRasterizeTimeInSeconds; | 243 rendering_stats_.totalRasterizeTimeInSeconds; |
228 stats->totalPixelsRasterized = rendering_stats_.totalPixelsRasterized; | 244 stats->totalPixelsRasterized = rendering_stats_.totalPixelsRasterized; |
229 } | 245 } |
230 | 246 |
231 void TileManager::AssignGpuMemoryToTiles() { | 247 void TileManager::AssignGpuMemoryToTiles() { |
232 TRACE_EVENT0("cc", "TileManager::AssignGpuMemoryToTiles"); | 248 TRACE_EVENT0("cc", "TileManager::AssignGpuMemoryToTiles"); |
233 // Some memory cannot be released. Figure out which. | 249 // Some memory cannot be released. Figure out which. |
234 size_t unreleasable_bytes = 0; | 250 size_t unreleasable_bytes = 0; |
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
287 int max_pending_tasks = kNumPendingRasterTasksPerThread * | 303 int max_pending_tasks = kNumPendingRasterTasksPerThread * |
288 num_raster_threads_; | 304 num_raster_threads_; |
289 | 305 |
290 // Stop dispatching raster tasks when too many are pending. | 306 // Stop dispatching raster tasks when too many are pending. |
291 if (pending_raster_tasks_ >= max_pending_tasks) | 307 if (pending_raster_tasks_ >= max_pending_tasks) |
292 break; | 308 break; |
293 | 309 |
294 DispatchOneRasterTask(tiles_that_need_to_be_rasterized_.back()); | 310 DispatchOneRasterTask(tiles_that_need_to_be_rasterized_.back()); |
295 tiles_that_need_to_be_rasterized_.pop_back(); | 311 tiles_that_need_to_be_rasterized_.pop_back(); |
296 } | 312 } |
313 | |
314 CheckForPendingSetPixelsCompletion(); | |
297 } | 315 } |
298 | 316 |
299 void TileManager::DispatchOneRasterTask(scoped_refptr<Tile> tile) { | 317 void TileManager::DispatchOneRasterTask(scoped_refptr<Tile> tile) { |
300 TRACE_EVENT0("cc", "TileManager::DispatchOneRasterTask"); | 318 TRACE_EVENT0("cc", "TileManager::DispatchOneRasterTask"); |
301 scoped_refptr<PicturePileImpl> cloned_picture_pile = | 319 scoped_refptr<PicturePileImpl> cloned_picture_pile = |
302 tile->picture_pile()->CloneForDrawing(); | 320 tile->picture_pile()->CloneForDrawing(); |
303 | 321 |
304 ManagedTileState& managed_tile_state = tile->managed_state(); | 322 ManagedTileState& managed_tile_state = tile->managed_state(); |
305 DCHECK(managed_tile_state.can_use_gpu_memory); | 323 DCHECK(managed_tile_state.can_use_gpu_memory); |
306 scoped_ptr<ResourcePool::Resource> resource = | 324 scoped_ptr<ResourcePool::Resource> resource = |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
353 // Tile can be freed after the completion of the raster task. Call | 371 // Tile can be freed after the completion of the raster task. Call |
354 // AssignGpuMemoryToTiles() to re-assign gpu memory to highest priority | 372 // AssignGpuMemoryToTiles() to re-assign gpu memory to highest priority |
355 // tiles. The result of this could be that this tile is no longer | 373 // tiles. The result of this could be that this tile is no longer |
356 // allowed to use gpu memory and in that case we need to abort | 374 // allowed to use gpu memory and in that case we need to abort |
357 // initialization and free all associated resources before calling | 375 // initialization and free all associated resources before calling |
358 // DispatchMoreRasterTasks(). | 376 // DispatchMoreRasterTasks(). |
359 AssignGpuMemoryToTiles(); | 377 AssignGpuMemoryToTiles(); |
360 | 378 |
361 // Finish resource initialization if |can_use_gpu_memory| is true. | 379 // Finish resource initialization if |can_use_gpu_memory| is true. |
362 if (managed_tile_state.can_use_gpu_memory) { | 380 if (managed_tile_state.can_use_gpu_memory) { |
363 resource_pool_->resource_provider()->setPixelsFromBuffer(resource->id()); | 381 // The component order may be bgra if we're uploading bgra pixels to rgba |
364 resource_pool_->resource_provider()->releasePixelBuffer(resource->id()); | |
365 | |
366 // The component order may be bgra if we uploaded bgra pixels to rgba | |
367 // texture. Mark contents as swizzled if image component order is | 382 // texture. Mark contents as swizzled if image component order is |
368 // different than texture format. | 383 // different than texture format. |
369 managed_tile_state.contents_swizzled = | 384 managed_tile_state.contents_swizzled = |
370 !PlatformColor::sameComponentOrder(tile->format_); | 385 !PlatformColor::sameComponentOrder(tile->format_); |
371 | 386 |
372 DidFinishTileInitialization(tile, resource.Pass()); | 387 // Tile resources can't be freed until upload has completed. |
388 managed_tile_state.can_be_freed = false; | |
389 | |
390 resource_pool_->resource_provider()->beginSetPixels(resource->id()); | |
391 pending_set_pixels_.append( | |
392 make_scoped_ptr(new PendingSetPixels(tile, resource.Pass()))); | |
373 } else { | 393 } else { |
374 resource_pool_->resource_provider()->releasePixelBuffer(resource->id()); | 394 resource_pool_->resource_provider()->releasePixelBuffer(resource->id()); |
375 resource_pool_->ReleaseResource(resource.Pass()); | 395 resource_pool_->ReleaseResource(resource.Pass()); |
376 managed_tile_state.resource_is_being_initialized = false; | 396 managed_tile_state.resource_is_being_initialized = false; |
377 } | 397 } |
378 | 398 |
379 DispatchMoreRasterTasks(); | 399 DispatchMoreRasterTasks(); |
380 } | 400 } |
381 | 401 |
402 void TileManager::CheckForPendingSetPixelsCompletion() { | |
403 while (!pending_set_pixels_.isEmpty()) { | |
404 // Set pixel tasks complete in the order they are posted. | |
405 if (!resource_pool_->resource_provider()->didSetPixelsComplete( | |
406 pending_set_pixels_.first()->resource()->id())) | |
407 break; | |
408 | |
409 scoped_ptr<PendingSetPixels> set_pixels = pending_set_pixels_.takeFirst(); | |
410 scoped_ptr<ResourcePool::Resource> resource = set_pixels->takeResource(); | |
411 | |
412 // It's now safe to release the pixel buffer. | |
413 resource_pool_->resource_provider()->releasePixelBuffer(resource->id()); | |
414 | |
415 DidFinishTileInitialization(set_pixels->tile(), resource.Pass()); | |
416 } | |
417 } | |
418 | |
382 void TileManager::DidFinishTileInitialization( | 419 void TileManager::DidFinishTileInitialization( |
383 Tile* tile, scoped_ptr<ResourcePool::Resource> resource) { | 420 Tile* tile, scoped_ptr<ResourcePool::Resource> resource) { |
384 ManagedTileState& managed_tile_state = tile->managed_state(); | 421 ManagedTileState& managed_tile_state = tile->managed_state(); |
385 DCHECK(!managed_tile_state.resource); | 422 DCHECK(!managed_tile_state.resource); |
386 managed_tile_state.resource = resource.Pass(); | 423 managed_tile_state.resource = resource.Pass(); |
387 managed_tile_state.resource_is_being_initialized = false; | 424 managed_tile_state.resource_is_being_initialized = false; |
425 managed_tile_state.can_be_freed = true; | |
388 // TODO(qinmin): Make this conditional on managed_tile_state.bin == NOW_BIN. | 426 // TODO(qinmin): Make this conditional on managed_tile_state.bin == NOW_BIN. |
389 client_->ScheduleRedraw(); | 427 if (!in_prepare_to_draw_) |
428 client_->ScheduleRedraw(); | |
390 } | 429 } |
391 | 430 |
392 } | 431 } |
OLD | NEW |