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

Side by Side Diff: cc/tiles/checker_image_tracker.cc

Issue 2726343004: cc: Optimize decode scheduling for checker-images. (Closed)
Patch Set: .. Created 3 years, 9 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
OLDNEW
1 // Copyright 2017 The Chromium Authors. All rights reserved. 1 // Copyright 2017 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/tiles/checker_image_tracker.h" 5 #include "cc/tiles/checker_image_tracker.h"
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "base/trace_event/trace_event.h" 8 #include "base/trace_event/trace_event.h"
9 9
10 namespace cc { 10 namespace cc {
(...skipping 17 matching lines...) Expand all
28 client_(client), 28 client_(client),
29 enable_checker_imaging_(enable_checker_imaging), 29 enable_checker_imaging_(enable_checker_imaging),
30 weak_factory_(this) {} 30 weak_factory_(this) {}
31 31
32 CheckerImageTracker::~CheckerImageTracker() { 32 CheckerImageTracker::~CheckerImageTracker() {
33 // Unlock all images pending decode requests. 33 // Unlock all images pending decode requests.
34 for (auto it : image_id_to_decode_request_id_) 34 for (auto it : image_id_to_decode_request_id_)
35 image_controller_->UnlockImageDecode(it.second); 35 image_controller_->UnlockImageDecode(it.second);
36 } 36 }
37 37
38 void CheckerImageTracker::FilterImagesForCheckeringForTile( 38 void CheckerImageTracker::SetImageDecodeQueue(
39 std::vector<DrawImage>* images, 39 ImageDecodeQueue image_decode_queue) {
40 ImageIdFlatSet* checkered_images, 40 image_decode_queue_ = std::move(image_decode_queue);
41 WhichTree tree) { 41 next_image_to_decode_ = 0;
42 DCHECK(checkered_images->empty()); 42 ScheduleNextImageDecode();
43
44 auto images_to_checker = std::remove_if(
45 images->begin(), images->end(),
46 [this, tree, &checkered_images](const DrawImage& draw_image) {
47 const sk_sp<const SkImage>& image = draw_image.image();
48 DCHECK(image->isLazyGenerated());
49 if (ShouldCheckerImage(image, tree)) {
50 ScheduleImageDecodeIfNecessary(image);
51 checkered_images->insert(image->uniqueID());
52 return true;
53 }
54 return false;
55 });
56 images->erase(images_to_checker, images->end());
57 } 43 }
58 44
59 const ImageIdFlatSet& CheckerImageTracker::TakeImagesToInvalidateOnSyncTree() { 45 const ImageIdFlatSet& CheckerImageTracker::TakeImagesToInvalidateOnSyncTree() {
60 DCHECK_EQ(invalidated_images_on_current_sync_tree_.size(), 0u) 46 DCHECK_EQ(invalidated_images_on_current_sync_tree_.size(), 0u)
61 << "Sync tree can not be invalidated more than once"; 47 << "Sync tree can not be invalidated more than once";
62 48
63 invalidated_images_on_current_sync_tree_.swap(images_pending_invalidation_); 49 invalidated_images_on_current_sync_tree_.swap(images_pending_invalidation_);
64 images_pending_invalidation_.clear(); 50 images_pending_invalidation_.clear();
65 return invalidated_images_on_current_sync_tree_; 51 return invalidated_images_on_current_sync_tree_;
66 } 52 }
67 53
68 void CheckerImageTracker::DidActivateSyncTree() { 54 void CheckerImageTracker::DidActivateSyncTree() {
69 for (auto image_id : invalidated_images_on_current_sync_tree_) { 55 for (auto image_id : invalidated_images_on_current_sync_tree_) {
70 auto it = image_id_to_decode_request_id_.find(image_id); 56 auto it = image_id_to_decode_request_id_.find(image_id);
71 image_controller_->UnlockImageDecode(it->second); 57 image_controller_->UnlockImageDecode(it->second);
72 image_id_to_decode_request_id_.erase(it); 58 image_id_to_decode_request_id_.erase(it);
73 } 59 }
74 60
75 invalidated_images_on_current_sync_tree_.clear(); 61 invalidated_images_on_current_sync_tree_.clear();
76 } 62 }
77 63
78 void CheckerImageTracker::DidFinishImageDecode( 64 void CheckerImageTracker::DidFinishImageDecode(
79 ImageId image_id, 65 ImageId image_id,
80 ImageController::ImageDecodeRequestId request_id, 66 ImageController::ImageDecodeRequestId request_id,
81 ImageController::ImageDecodeResult result) { 67 ImageController::ImageDecodeResult result) {
82 TRACE_EVENT_ASYNC_END0("cc", "CheckerImageTracker::DeferImageDecode", 68 TRACE_EVENT_ASYNC_END0("cc", "CheckerImageTracker::DeferImageDecode",
83 image_id); 69 image_id);
84 70
85 DCHECK_NE(result, ImageController::ImageDecodeResult::DECODE_NOT_REQUIRED); 71 DCHECK_NE(ImageController::ImageDecodeResult::DECODE_NOT_REQUIRED, result);
86 DCHECK_NE(pending_image_decodes_.count(image_id), 0u); 72 DCHECK_EQ(outstanding_image_decode_->uniqueID(), image_id);
87 pending_image_decodes_.erase(image_id); 73 outstanding_image_decode_ = nullptr;
88
89 images_decoded_once_.insert(image_id); 74 images_decoded_once_.insert(image_id);
90 images_pending_invalidation_.insert(image_id); 75 images_pending_invalidation_.insert(image_id);
76
77 ScheduleNextImageDecode();
91 client_->NeedsInvalidationForCheckerImagedTiles(); 78 client_->NeedsInvalidationForCheckerImagedTiles();
92 } 79 }
93 80
94 bool CheckerImageTracker::ShouldCheckerImage(const sk_sp<const SkImage>& image, 81 bool CheckerImageTracker::ShouldCheckerImage(const sk_sp<const SkImage>& image,
95 WhichTree tree) const { 82 WhichTree tree) const {
96 TRACE_EVENT1("cc", "CheckerImageTracker::ShouldCheckerImage", "image_id", 83 TRACE_EVENT1("cc", "CheckerImageTracker::ShouldCheckerImage", "image_id",
97 image->uniqueID()); 84 image->uniqueID());
98 85
99 if (!enable_checker_imaging_) 86 if (!enable_checker_imaging_)
100 return false; 87 return false;
101 88
102 // If the image was invalidated on the current sync tree and the tile is 89 // If the image was invalidated on the current sync tree and the tile is
103 // for the active tree, continue checkering it on the active tree to ensure 90 // for the active tree, continue checkering it on the active tree to ensure
104 // the image update is atomic for the frame. 91 // the image update is atomic for the frame.
105 if (invalidated_images_on_current_sync_tree_.count(image->uniqueID()) != 0 && 92 if (invalidated_images_on_current_sync_tree_.count(image->uniqueID()) != 0 &&
106 tree == WhichTree::ACTIVE_TREE) { 93 tree == WhichTree::ACTIVE_TREE) {
107 return true; 94 return true;
108 } 95 }
109 96
110 // If a decode request is pending for this image, continue checkering it.
111 if (pending_image_decodes_.find(image->uniqueID()) !=
112 pending_image_decodes_.end()) {
113 return true;
114 }
115
116 // If the image is pending invalidation, continue checkering it. All tiles 97 // If the image is pending invalidation, continue checkering it. All tiles
117 // for these images will be invalidated on the next pending tree. 98 // for these images will be invalidated on the next pending tree.
118 if (images_pending_invalidation_.find(image->uniqueID()) != 99 if (images_pending_invalidation_.find(image->uniqueID()) !=
119 images_pending_invalidation_.end()) { 100 images_pending_invalidation_.end()) {
120 return true; 101 return true;
121 } 102 }
122 103
123 // If the image has been decoded once before, don't checker it again. 104 // If the image has been decoded once before, don't checker it again.
124 if (images_decoded_once_.find(image->uniqueID()) != 105 if (images_decoded_once_.find(image->uniqueID()) !=
125 images_decoded_once_.end()) { 106 images_decoded_once_.end()) {
126 return false; 107 return false;
127 } 108 }
128 109
129 return SafeSizeOfImage(image.get()) >= kMinImageSizeToCheckerBytes; 110 return SafeSizeOfImage(image.get()) >= kMinImageSizeToCheckerBytes;
130 } 111 }
131 112
132 void CheckerImageTracker::ScheduleImageDecodeIfNecessary( 113 void CheckerImageTracker::ScheduleNextImageDecode() {
133 const sk_sp<const SkImage>& image) { 114 if (image_decode_queue_.empty())
134 ImageId image_id = image->uniqueID(); 115 return;
135 116
136 // If the image has already been decoded, or a decode request is pending, we 117 if (outstanding_image_decode_)
vmpstr 2017/03/17 18:32:13 Leave a comment here explaining that if we have so
Khushal 2017/03/27 13:57:32 Done.
137 // don't need to schedule another decode.
138 if (images_decoded_once_.count(image_id) != 0 ||
139 pending_image_decodes_.count(image_id) != 0) {
140 return; 118 return;
119
120 DCHECK_GE(next_image_to_decode_, 0u);
121 DCHECK_LT(next_image_to_decode_, image_decode_queue_.size());
122 while (next_image_to_decode_ != image_decode_queue_.size()) {
123 outstanding_image_decode_ =
124 std::move(image_decode_queue_[next_image_to_decode_++]);
125
126 // The image may have already been decoded. Proceed to the next image in the
vmpstr 2017/03/17 18:32:13 Can you rephrase this comment to match the code? T
Khushal 2017/03/27 13:57:32 Done.
127 // queue in that case.
128 ImageId image_id = outstanding_image_decode_->uniqueID();
129 if (images_decoded_once_.count(image_id) == 0)
130 break;
131 outstanding_image_decode_ = nullptr;
141 } 132 }
142 133
134 if (next_image_to_decode_ == image_decode_queue_.size()) {
vmpstr 2017/03/17 18:32:13 Comment here
Khushal 2017/03/27 13:57:32 Done.
135 next_image_to_decode_ = 0;
136 image_decode_queue_.clear();
137 }
138
139 if (!outstanding_image_decode_)
140 return;
141
142 ImageId image_id = outstanding_image_decode_->uniqueID();
143 DCHECK_EQ(image_id_to_decode_request_id_.count(image_id), 0u);
143 TRACE_EVENT_ASYNC_BEGIN0("cc", "CheckerImageTracker::DeferImageDecode", 144 TRACE_EVENT_ASYNC_BEGIN0("cc", "CheckerImageTracker::DeferImageDecode",
144 image_id); 145 image_id);
145 DCHECK_EQ(image_id_to_decode_request_id_.count(image_id), 0U);
146
147 image_id_to_decode_request_id_[image_id] = 146 image_id_to_decode_request_id_[image_id] =
148 image_controller_->QueueImageDecode( 147 image_controller_->QueueImageDecode(
149 image, base::Bind(&CheckerImageTracker::DidFinishImageDecode, 148 outstanding_image_decode_,
150 weak_factory_.GetWeakPtr(), image_id)); 149 base::Bind(&CheckerImageTracker::DidFinishImageDecode,
151 pending_image_decodes_.insert(image_id); 150 weak_factory_.GetWeakPtr(), image_id));
152 } 151 }
153 152
154 } // namespace cc 153 } // namespace cc
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698