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

Side by Side Diff: sync/notifier/ack_tracker.cc

Issue 11607003: Add a Clock and TickClock interface for mocking out time (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Fix warnings Created 7 years, 10 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
« no previous file with comments | « sync/notifier/ack_tracker.h ('k') | sync/notifier/ack_tracker_unittest.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 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 "sync/notifier/ack_tracker.h" 5 #include "sync/notifier/ack_tracker.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <iterator> 8 #include <iterator>
9 #include <utility> 9 #include <utility>
10 10
11 #include "base/callback.h" 11 #include "base/callback.h"
12 #include "base/stl_util.h" 12 #include "base/stl_util.h"
13 #include "base/time/tick_clock.h"
13 #include "google/cacheinvalidation/include/types.h" 14 #include "google/cacheinvalidation/include/types.h"
14 15
15 namespace syncer { 16 namespace syncer {
16 17
17 namespace { 18 namespace {
18 19
19 // All times are in milliseconds. 20 // All times are in milliseconds.
20 const net::BackoffEntry::Policy kDefaultBackoffPolicy = { 21 const net::BackoffEntry::Policy kDefaultBackoffPolicy = {
21 // Number of initial errors (in sequence) to ignore before applying 22 // Number of initial errors (in sequence) to ignore before applying
22 // exponential back-off rules. 23 // exponential back-off rules.
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after
66 } 67 }
67 68
68 AckTracker::Entry::Entry(scoped_ptr<net::BackoffEntry> backoff, 69 AckTracker::Entry::Entry(scoped_ptr<net::BackoffEntry> backoff,
69 const ObjectIdSet& ids) 70 const ObjectIdSet& ids)
70 : backoff(backoff.Pass()), ids(ids) { 71 : backoff(backoff.Pass()), ids(ids) {
71 } 72 }
72 73
73 AckTracker::Entry::~Entry() { 74 AckTracker::Entry::~Entry() {
74 } 75 }
75 76
76 AckTracker::AckTracker(Delegate* delegate) 77 AckTracker::AckTracker(base::TickClock* tick_clock, Delegate* delegate)
77 : now_callback_(base::Bind(&base::TimeTicks::Now)), 78 : create_backoff_entry_callback_(base::Bind(&CreateDefaultBackoffEntry)),
78 create_backoff_entry_callback_(base::Bind(&CreateDefaultBackoffEntry)), 79 tick_clock_(tick_clock),
79 delegate_(delegate) { 80 delegate_(delegate) {
81 DCHECK(tick_clock_);
80 DCHECK(delegate_); 82 DCHECK(delegate_);
81 } 83 }
82 84
83 AckTracker::~AckTracker() { 85 AckTracker::~AckTracker() {
84 DCHECK(thread_checker_.CalledOnValidThread()); 86 DCHECK(thread_checker_.CalledOnValidThread());
85 87
86 Clear(); 88 Clear();
87 } 89 }
88 90
89 void AckTracker::Clear() { 91 void AckTracker::Clear() {
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after
132 NudgeTimer(); 134 NudgeTimer();
133 } 135 }
134 136
135 void AckTracker::NudgeTimer() { 137 void AckTracker::NudgeTimer() {
136 DCHECK(thread_checker_.CalledOnValidThread()); 138 DCHECK(thread_checker_.CalledOnValidThread());
137 139
138 if (queue_.empty()) { 140 if (queue_.empty()) {
139 return; 141 return;
140 } 142 }
141 143
142 const base::TimeTicks now = now_callback_.Run(); 144 const base::TimeTicks now = tick_clock_->NowTicks();
143 // There are two cases when the timer needs to be started: 145 // There are two cases when the timer needs to be started:
144 // 1. |desired_run_time_| is in the past. By definition, the timer has already 146 // 1. |desired_run_time_| is in the past. By definition, the timer has already
145 // fired at this point. Since the queue is non-empty, we need to set the 147 // fired at this point. Since the queue is non-empty, we need to set the
146 // timer to fire again. 148 // timer to fire again.
147 // 2. The timer is already running but we need it to fire sooner if the first 149 // 2. The timer is already running but we need it to fire sooner if the first
148 // entry's timeout occurs before |desired_run_time_|. 150 // entry's timeout occurs before |desired_run_time_|.
149 if (desired_run_time_ <= now || queue_.begin()->first < desired_run_time_) { 151 if (desired_run_time_ <= now || queue_.begin()->first < desired_run_time_) {
150 base::TimeDelta delay = queue_.begin()->first - now; 152 base::TimeDelta delay = queue_.begin()->first - now;
151 if (delay < base::TimeDelta()) { 153 if (delay < base::TimeDelta()) {
152 delay = base::TimeDelta(); 154 delay = base::TimeDelta();
153 } 155 }
154 timer_.Start(FROM_HERE, delay, this, &AckTracker::OnTimeout); 156 timer_.Start(FROM_HERE, delay, this, &AckTracker::OnTimeout);
155 desired_run_time_ = queue_.begin()->first; 157 desired_run_time_ = queue_.begin()->first;
156 } 158 }
157 } 159 }
158 160
159 void AckTracker::OnTimeout() { 161 void AckTracker::OnTimeout() {
160 DCHECK(thread_checker_.CalledOnValidThread()); 162 DCHECK(thread_checker_.CalledOnValidThread());
161 163
162 OnTimeoutAt(now_callback_.Run()); 164 OnTimeoutAt(tick_clock_->NowTicks());
163 } 165 }
164 166
165 void AckTracker::OnTimeoutAt(base::TimeTicks now) { 167 void AckTracker::OnTimeoutAt(base::TimeTicks now) {
166 DCHECK(thread_checker_.CalledOnValidThread()); 168 DCHECK(thread_checker_.CalledOnValidThread());
167 169
168 if (queue_.empty()) 170 if (queue_.empty())
169 return; 171 return;
170 172
171 ObjectIdSet expired_ids; 173 ObjectIdSet expired_ids;
172 std::multimap<base::TimeTicks, Entry*>::iterator end = 174 std::multimap<base::TimeTicks, Entry*>::iterator end =
173 queue_.upper_bound(now); 175 queue_.upper_bound(now);
174 std::vector<Entry*> expired_entries; 176 std::vector<Entry*> expired_entries;
175 for (std::multimap<base::TimeTicks, Entry*>::iterator it = queue_.begin(); 177 for (std::multimap<base::TimeTicks, Entry*>::iterator it = queue_.begin();
176 it != end; ++it) { 178 it != end; ++it) {
177 expired_ids.insert(it->second->ids.begin(), it->second->ids.end()); 179 expired_ids.insert(it->second->ids.begin(), it->second->ids.end());
178 it->second->backoff->InformOfRequest(false /* succeeded */); 180 it->second->backoff->InformOfRequest(false /* succeeded */);
179 expired_entries.push_back(it->second); 181 expired_entries.push_back(it->second);
180 } 182 }
181 queue_.erase(queue_.begin(), end); 183 queue_.erase(queue_.begin(), end);
182 for (std::vector<Entry*>::const_iterator it = expired_entries.begin(); 184 for (std::vector<Entry*>::const_iterator it = expired_entries.begin();
183 it != expired_entries.end(); ++it) { 185 it != expired_entries.end(); ++it) {
184 queue_.insert(std::make_pair((*it)->backoff->GetReleaseTime(), *it)); 186 queue_.insert(std::make_pair((*it)->backoff->GetReleaseTime(), *it));
185 } 187 }
186 delegate_->OnTimeout(expired_ids); 188 delegate_->OnTimeout(expired_ids);
187 NudgeTimer(); 189 NudgeTimer();
188 } 190 }
189 191
190 // Testing helpers. 192 // Testing helpers.
191 void AckTracker::SetNowCallbackForTest(
192 const NowCallback& now_callback) {
193 DCHECK(thread_checker_.CalledOnValidThread());
194
195 now_callback_ = now_callback;
196 }
197
198 void AckTracker::SetCreateBackoffEntryCallbackForTest( 193 void AckTracker::SetCreateBackoffEntryCallbackForTest(
199 const CreateBackoffEntryCallback& create_backoff_entry_callback) { 194 const CreateBackoffEntryCallback& create_backoff_entry_callback) {
200 DCHECK(thread_checker_.CalledOnValidThread()); 195 DCHECK(thread_checker_.CalledOnValidThread());
201 196
202 create_backoff_entry_callback_ = create_backoff_entry_callback; 197 create_backoff_entry_callback_ = create_backoff_entry_callback;
203 } 198 }
204 199
205 bool AckTracker::TriggerTimeoutAtForTest(base::TimeTicks now) { 200 bool AckTracker::TriggerTimeoutAtForTest(base::TimeTicks now) {
206 DCHECK(thread_checker_.CalledOnValidThread()); 201 DCHECK(thread_checker_.CalledOnValidThread());
207 202
208 bool no_timeouts_before_now = (queue_.lower_bound(now) == queue_.begin()); 203 bool no_timeouts_before_now = (queue_.lower_bound(now) == queue_.begin());
209 OnTimeoutAt(now); 204 OnTimeoutAt(now);
210 return no_timeouts_before_now; 205 return no_timeouts_before_now;
211 } 206 }
212 207
213 bool AckTracker::IsQueueEmptyForTest() const { 208 bool AckTracker::IsQueueEmptyForTest() const {
214 DCHECK(thread_checker_.CalledOnValidThread()); 209 DCHECK(thread_checker_.CalledOnValidThread());
215 210
216 return queue_.empty(); 211 return queue_.empty();
217 } 212 }
218 213
219 const base::Timer& AckTracker::GetTimerForTest() const { 214 const base::Timer& AckTracker::GetTimerForTest() const {
220 DCHECK(thread_checker_.CalledOnValidThread()); 215 DCHECK(thread_checker_.CalledOnValidThread());
221 216
222 return timer_; 217 return timer_;
223 } 218 }
224 219
225 } // namespace syncer 220 } // namespace syncer
OLDNEW
« no previous file with comments | « sync/notifier/ack_tracker.h ('k') | sync/notifier/ack_tracker_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698