blob: 9f7f5c1cd0d49f844aa790ca8c88ca5442a22060 [file] [log] [blame]
Jay Srinivasan6f6ea002012-12-14 11:26:28 -08001// Copyright (c) 2012 The Chromium OS 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#include <glib.h>
6
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -08007#include "base/stringprintf.h"
Jay Srinivasan6f6ea002012-12-14 11:26:28 -08008#include "gmock/gmock.h"
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -08009#include "gtest/gtest.h"
10
Jay Srinivasand29695d2013-04-08 15:08:05 -070011#include "update_engine/constants.h"
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080012#include "update_engine/omaha_request_action.h"
13#include "update_engine/payload_state.h"
14#include "update_engine/prefs_mock.h"
15#include "update_engine/test_utils.h"
16#include "update_engine/utils.h"
17
Jay Srinivasan08262882012-12-28 19:29:43 -080018using base::Time;
19using base::TimeDelta;
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080020using std::string;
21using testing::_;
22using testing::NiceMock;
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080023using testing::Return;
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080024using testing::SetArgumentPointee;
25
26namespace chromeos_update_engine {
27
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080028static void SetupPayloadStateWith2Urls(string hash,
29 PayloadState* payload_state,
30 OmahaResponse* response) {
31 response->payload_urls.clear();
32 response->payload_urls.push_back("http://test");
33 response->payload_urls.push_back("https://test");
34 response->size = 523456789;
35 response->hash = hash;
36 response->metadata_size = 558123;
37 response->metadata_signature = "metasign";
38 response->max_failure_count_per_url = 3;
39 payload_state->SetResponse(*response);
Jay Srinivasan08262882012-12-28 19:29:43 -080040 string stored_response_sign = payload_state->GetResponseSignature();
41 string expected_response_sign = StringPrintf(
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080042 "NumURLs = 2\n"
43 "Url0 = http://test\n"
44 "Url1 = https://test\n"
45 "Payload Size = 523456789\n"
46 "Payload Sha256 Hash = %s\n"
47 "Metadata Size = 558123\n"
Jay Srinivasan08262882012-12-28 19:29:43 -080048 "Metadata Signature = metasign\n"
49 "Is Delta Payload = %d\n"
50 "Max Failure Count Per Url = %d\n"
51 "Disable Payload Backoff = %d\n",
52 hash.c_str(),
53 response->is_delta_payload,
54 response->max_failure_count_per_url,
55 response->disable_payload_backoff);
56 EXPECT_EQ(expected_response_sign, stored_response_sign);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080057}
58
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080059class PayloadStateTest : public ::testing::Test { };
60
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080061TEST(PayloadStateTest, DidYouAddANewActionExitCode) {
Jay Srinivasan1c0fe792013-03-28 16:45:25 -070062 if (kActionCodeUmaReportedMax != 43) {
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080063 LOG(ERROR) << "The following failure is intentional. If you added a new "
64 << "ActionExitCode enum value, make sure to add it to the "
65 << "PayloadState::UpdateFailed method and then update this test "
66 << "to the new value of kActionCodeUmaReportedMax, which is "
67 << kActionCodeUmaReportedMax;
68 EXPECT_FALSE("Please see the log line above");
69 }
70}
71
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080072TEST(PayloadStateTest, SetResponseWorksWithEmptyResponse) {
73 OmahaResponse response;
74 NiceMock<PrefsMock> prefs;
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080075 EXPECT_CALL(prefs, SetInt64(kPrefsPayloadAttemptNumber, 0));
Jay Srinivasan08262882012-12-28 19:29:43 -080076 EXPECT_CALL(prefs, SetInt64(kPrefsBackoffExpiryTime, 0));
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080077 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlIndex, 0));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080078 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0));
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080079 PayloadState payload_state;
80 EXPECT_TRUE(payload_state.Initialize(&prefs));
81 payload_state.SetResponse(response);
Jay Srinivasan08262882012-12-28 19:29:43 -080082 string stored_response_sign = payload_state.GetResponseSignature();
83 string expected_response_sign = "NumURLs = 0\n"
84 "Payload Size = 0\n"
85 "Payload Sha256 Hash = \n"
86 "Metadata Size = 0\n"
87 "Metadata Signature = \n"
88 "Is Delta Payload = 0\n"
89 "Max Failure Count Per Url = 0\n"
90 "Disable Payload Backoff = 0\n";
91 EXPECT_EQ(expected_response_sign, stored_response_sign);
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080092 EXPECT_EQ(0, payload_state.GetUrlIndex());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080093 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080094}
95
96TEST(PayloadStateTest, SetResponseWorksWithSingleUrl) {
97 OmahaResponse response;
98 response.payload_urls.push_back("http://single.url.test");
99 response.size = 123456789;
100 response.hash = "hash";
101 response.metadata_size = 58123;
102 response.metadata_signature = "msign";
103 NiceMock<PrefsMock> prefs;
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800104 EXPECT_CALL(prefs, SetInt64(kPrefsPayloadAttemptNumber, 0));
Jay Srinivasan08262882012-12-28 19:29:43 -0800105 EXPECT_CALL(prefs, SetInt64(kPrefsBackoffExpiryTime, 0));
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800106 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlIndex, 0));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800107 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0));
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800108 PayloadState payload_state;
109 EXPECT_TRUE(payload_state.Initialize(&prefs));
110 payload_state.SetResponse(response);
Jay Srinivasan08262882012-12-28 19:29:43 -0800111 string stored_response_sign = payload_state.GetResponseSignature();
112 string expected_response_sign = "NumURLs = 1\n"
113 "Url0 = http://single.url.test\n"
114 "Payload Size = 123456789\n"
115 "Payload Sha256 Hash = hash\n"
116 "Metadata Size = 58123\n"
117 "Metadata Signature = msign\n"
118 "Is Delta Payload = 0\n"
119 "Max Failure Count Per Url = 0\n"
120 "Disable Payload Backoff = 0\n";
121 EXPECT_EQ(expected_response_sign, stored_response_sign);
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800122 EXPECT_EQ(0, payload_state.GetUrlIndex());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800123 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800124}
125
126TEST(PayloadStateTest, SetResponseWorksWithMultipleUrls) {
127 OmahaResponse response;
128 response.payload_urls.push_back("http://multiple.url.test");
129 response.payload_urls.push_back("https://multiple.url.test");
130 response.size = 523456789;
131 response.hash = "rhash";
132 response.metadata_size = 558123;
133 response.metadata_signature = "metasign";
134 NiceMock<PrefsMock> prefs;
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800135 EXPECT_CALL(prefs, SetInt64(kPrefsPayloadAttemptNumber, 0));
Jay Srinivasan08262882012-12-28 19:29:43 -0800136 EXPECT_CALL(prefs, SetInt64(kPrefsBackoffExpiryTime, 0));
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800137 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlIndex, 0));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800138 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0));
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800139 PayloadState payload_state;
140 EXPECT_TRUE(payload_state.Initialize(&prefs));
141 payload_state.SetResponse(response);
Jay Srinivasan08262882012-12-28 19:29:43 -0800142 string stored_response_sign = payload_state.GetResponseSignature();
143 string expected_response_sign = "NumURLs = 2\n"
144 "Url0 = http://multiple.url.test\n"
145 "Url1 = https://multiple.url.test\n"
146 "Payload Size = 523456789\n"
147 "Payload Sha256 Hash = rhash\n"
148 "Metadata Size = 558123\n"
149 "Metadata Signature = metasign\n"
150 "Is Delta Payload = 0\n"
151 "Max Failure Count Per Url = 0\n"
152 "Disable Payload Backoff = 0\n";
153 EXPECT_EQ(expected_response_sign, stored_response_sign);
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800154 EXPECT_EQ(0, payload_state.GetUrlIndex());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800155 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800156}
157
158TEST(PayloadStateTest, CanAdvanceUrlIndexCorrectly) {
159 OmahaResponse response;
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800160 NiceMock<PrefsMock> prefs;
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800161 PayloadState payload_state;
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800162
163 // Payload attempt should start with 0 and then advance to 1.
164 EXPECT_CALL(prefs, SetInt64(kPrefsPayloadAttemptNumber, 0)).Times(1);
165 EXPECT_CALL(prefs, SetInt64(kPrefsPayloadAttemptNumber, 1)).Times(1);
Jay Srinivasan08262882012-12-28 19:29:43 -0800166 EXPECT_CALL(prefs, SetInt64(kPrefsBackoffExpiryTime, _)).Times(2);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800167
168 // Url index should go from 0 to 1 twice.
169 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlIndex, 0)).Times(2);
170 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlIndex, 1)).Times(2);
171
172 // Failure count should be called each times url index is set, so that's
173 // 4 times for this test.
174 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0)).Times(4);
175
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800176 EXPECT_TRUE(payload_state.Initialize(&prefs));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800177
178 // This does a SetResponse which causes all the states to be set to 0 for
179 // the first time.
180 SetupPayloadStateWith2Urls("Hash1235", &payload_state, &response);
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800181 EXPECT_EQ(0, payload_state.GetUrlIndex());
182
183 // Verify that on the first error, the URL index advances to 1.
184 ActionExitCode error = kActionCodeDownloadMetadataSignatureMismatch;
185 payload_state.UpdateFailed(error);
186 EXPECT_EQ(1, payload_state.GetUrlIndex());
187
188 // Verify that on the next error, the URL index wraps around to 0.
189 payload_state.UpdateFailed(error);
190 EXPECT_EQ(0, payload_state.GetUrlIndex());
191
192 // Verify that on the next error, it again advances to 1.
193 payload_state.UpdateFailed(error);
194 EXPECT_EQ(1, payload_state.GetUrlIndex());
195}
196
197TEST(PayloadStateTest, NewResponseResetsPayloadState) {
198 OmahaResponse response;
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800199 NiceMock<PrefsMock> prefs;
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800200 PayloadState payload_state;
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800201
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800202 EXPECT_TRUE(payload_state.Initialize(&prefs));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800203
204 // Set the first response.
205 SetupPayloadStateWith2Urls("Hash5823", &payload_state, &response);
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800206
207 // Advance the URL index to 1 by faking an error.
208 ActionExitCode error = kActionCodeDownloadMetadataSignatureMismatch;
209 payload_state.UpdateFailed(error);
210 EXPECT_EQ(1, payload_state.GetUrlIndex());
211
212 // Now, slightly change the response and set it again.
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800213 SetupPayloadStateWith2Urls("Hash8225", &payload_state, &response);
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800214
215 // Make sure the url index was reset to 0 because of the new response.
216 EXPECT_EQ(0, payload_state.GetUrlIndex());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800217 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800218}
219
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800220TEST(PayloadStateTest, AllCountersGetUpdatedProperlyOnErrorCodesAndEvents) {
221 OmahaResponse response;
222 PayloadState payload_state;
223 NiceMock<PrefsMock> prefs;
224
225 EXPECT_CALL(prefs, SetInt64(kPrefsPayloadAttemptNumber, 0)).Times(2);
226 EXPECT_CALL(prefs, SetInt64(kPrefsPayloadAttemptNumber, 1)).Times(1);
227 EXPECT_CALL(prefs, SetInt64(kPrefsPayloadAttemptNumber, 2)).Times(1);
228
Jay Srinivasan08262882012-12-28 19:29:43 -0800229 EXPECT_CALL(prefs, SetInt64(kPrefsBackoffExpiryTime, _)).Times(4);
230
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800231 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlIndex, 0)).Times(4);
232 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlIndex, 1)).Times(2);
233
234 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0)).Times(7);
235 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlFailureCount, 1)).Times(2);
236 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlFailureCount, 2)).Times(1);
237
238 EXPECT_TRUE(payload_state.Initialize(&prefs));
239
240 SetupPayloadStateWith2Urls("Hash5873", &payload_state, &response);
241
242 // This should advance the URL index.
243 payload_state.UpdateFailed(kActionCodeDownloadMetadataSignatureMismatch);
244 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
245 EXPECT_EQ(1, payload_state.GetUrlIndex());
246 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
247
248 // This should advance the failure count only.
249 payload_state.UpdateFailed(kActionCodeDownloadTransferError);
250 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
251 EXPECT_EQ(1, payload_state.GetUrlIndex());
252 EXPECT_EQ(1, payload_state.GetUrlFailureCount());
253
254 // This should advance the failure count only.
255 payload_state.UpdateFailed(kActionCodeDownloadTransferError);
256 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
257 EXPECT_EQ(1, payload_state.GetUrlIndex());
258 EXPECT_EQ(2, payload_state.GetUrlFailureCount());
259
260 // This should advance the URL index as we've reached the
261 // max failure count and reset the failure count for the new URL index.
262 // This should also wrap around the URL index and thus cause the payload
263 // attempt number to be incremented.
264 payload_state.UpdateFailed(kActionCodeDownloadTransferError);
265 EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
266 EXPECT_EQ(0, payload_state.GetUrlIndex());
267 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
Jay Srinivasan08262882012-12-28 19:29:43 -0800268 EXPECT_TRUE(payload_state.ShouldBackoffDownload());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800269
270 // This should advance the URL index.
271 payload_state.UpdateFailed(kActionCodePayloadHashMismatchError);
272 EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
273 EXPECT_EQ(1, payload_state.GetUrlIndex());
274 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
Jay Srinivasan08262882012-12-28 19:29:43 -0800275 EXPECT_TRUE(payload_state.ShouldBackoffDownload());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800276
277 // This should advance the URL index and payload attempt number due to
278 // wrap-around of URL index.
279 payload_state.UpdateFailed(kActionCodeDownloadMetadataSignatureMissingError);
280 EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
281 EXPECT_EQ(0, payload_state.GetUrlIndex());
282 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
Jay Srinivasan08262882012-12-28 19:29:43 -0800283 EXPECT_TRUE(payload_state.ShouldBackoffDownload());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800284
285 // This HTTP error code should only increase the failure count.
286 payload_state.UpdateFailed(static_cast<ActionExitCode>(
287 kActionCodeOmahaRequestHTTPResponseBase + 404));
288 EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
289 EXPECT_EQ(0, payload_state.GetUrlIndex());
290 EXPECT_EQ(1, payload_state.GetUrlFailureCount());
Jay Srinivasan08262882012-12-28 19:29:43 -0800291 EXPECT_TRUE(payload_state.ShouldBackoffDownload());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800292
293 // And that failure count should be reset when we download some bytes
294 // afterwards.
295 payload_state.DownloadProgress(100);
296 EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
297 EXPECT_EQ(0, payload_state.GetUrlIndex());
298 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
Jay Srinivasan08262882012-12-28 19:29:43 -0800299 EXPECT_TRUE(payload_state.ShouldBackoffDownload());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800300
301 // Now, slightly change the response and set it again.
302 SetupPayloadStateWith2Urls("Hash8532", &payload_state, &response);
303
304 // Make sure the url index was reset to 0 because of the new response.
305 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
306 EXPECT_EQ(0, payload_state.GetUrlIndex());
307 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
Jay Srinivasan08262882012-12-28 19:29:43 -0800308 EXPECT_FALSE(payload_state.ShouldBackoffDownload());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800309}
310
311TEST(PayloadStateTest, PayloadAttemptNumberIncreasesOnSuccessfulDownload) {
312 OmahaResponse response;
313 PayloadState payload_state;
314 NiceMock<PrefsMock> prefs;
315
316 EXPECT_CALL(prefs, SetInt64(kPrefsPayloadAttemptNumber, 0)).Times(1);
317 EXPECT_CALL(prefs, SetInt64(kPrefsPayloadAttemptNumber, 1)).Times(1);
318
Jay Srinivasan08262882012-12-28 19:29:43 -0800319 EXPECT_CALL(prefs, SetInt64(kPrefsBackoffExpiryTime, _)).Times(2);
320
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800321 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlIndex, 0)).Times(1);
322 EXPECT_CALL(prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0)).Times(1);
323
324 EXPECT_TRUE(payload_state.Initialize(&prefs));
325
326 SetupPayloadStateWith2Urls("Hash8593", &payload_state, &response);
327
328 // This should just advance the payload attempt number;
329 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
330 payload_state.DownloadComplete();
331 EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
332 EXPECT_EQ(0, payload_state.GetUrlIndex());
333 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
334}
335
336TEST(PayloadStateTest, SetResponseResetsInvalidUrlIndex) {
337 OmahaResponse response;
338 PayloadState payload_state;
339 NiceMock<PrefsMock> prefs;
340
341 EXPECT_TRUE(payload_state.Initialize(&prefs));
342 SetupPayloadStateWith2Urls("Hash4427", &payload_state, &response);
343
344 // Generate enough events to advance URL index, failure count and
345 // payload attempt number all to 1.
346 payload_state.DownloadComplete();
347 payload_state.UpdateFailed(kActionCodeDownloadMetadataSignatureMismatch);
348 payload_state.UpdateFailed(kActionCodeDownloadTransferError);
349 EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
350 EXPECT_EQ(1, payload_state.GetUrlIndex());
351 EXPECT_EQ(1, payload_state.GetUrlFailureCount());
352
353 // Now, simulate a corrupted url index on persisted store which gets
354 // loaded when update_engine restarts. Using a different prefs object
355 // so as to not bother accounting for the uninteresting calls above.
356 NiceMock<PrefsMock> prefs2;
357 EXPECT_CALL(prefs2, Exists(_)).WillRepeatedly(Return(true));
358 EXPECT_CALL(prefs2, GetInt64(kPrefsPayloadAttemptNumber, _));
Jay Srinivasan08262882012-12-28 19:29:43 -0800359 EXPECT_CALL(prefs2, GetInt64(kPrefsBackoffExpiryTime, _));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800360 EXPECT_CALL(prefs2, GetInt64(kPrefsCurrentUrlIndex, _))
361 .WillOnce(DoAll(SetArgumentPointee<1>(2), Return(true)));
362 EXPECT_CALL(prefs2, GetInt64(kPrefsCurrentUrlFailureCount, _));
363
364 // Note: This will be a different payload object, but the response should
365 // have the same hash as before so as to not trivially reset because the
366 // response was different. We want to specifically test that even if the
367 // response is same, we should reset the state if we find it corrupted.
368 EXPECT_TRUE(payload_state.Initialize(&prefs2));
369 SetupPayloadStateWith2Urls("Hash4427", &payload_state, &response);
370
371 // Make sure all counters get reset to 0 because of the corrupted URL index
372 // we supplied above.
373 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
374 EXPECT_EQ(0, payload_state.GetUrlIndex());
375 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
376}
Jay Srinivasan08262882012-12-28 19:29:43 -0800377
378TEST(PayloadStateTest, NoBackoffForDeltaPayloads) {
379 OmahaResponse response;
380 response.is_delta_payload = true;
381 PayloadState payload_state;
382 NiceMock<PrefsMock> prefs;
383
384 EXPECT_TRUE(payload_state.Initialize(&prefs));
385 SetupPayloadStateWith2Urls("Hash6437", &payload_state, &response);
386
387 // Simulate a successful download and see that we're ready to download
388 // again without any backoff as this is a delta payload.
389 payload_state.DownloadComplete();
390 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
391 EXPECT_FALSE(payload_state.ShouldBackoffDownload());
392
393 // Simulate two failures (enough to cause payload backoff) and check
394 // again that we're ready to re-download without any backoff as this is
395 // a delta payload.
396 payload_state.UpdateFailed(kActionCodeDownloadMetadataSignatureMismatch);
397 payload_state.UpdateFailed(kActionCodeDownloadMetadataSignatureMismatch);
398 EXPECT_EQ(0, payload_state.GetUrlIndex());
399 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
400 EXPECT_FALSE(payload_state.ShouldBackoffDownload());
401}
402
403static void CheckPayloadBackoffState(PayloadState* payload_state,
404 int expected_attempt_number,
405 TimeDelta expected_days) {
406 payload_state->DownloadComplete();
407 EXPECT_EQ(expected_attempt_number, payload_state->GetPayloadAttemptNumber());
408 EXPECT_TRUE(payload_state->ShouldBackoffDownload());
409 Time backoff_expiry_time = payload_state->GetBackoffExpiryTime();
410 // Add 1 hour extra to the 6 hour fuzz check to tolerate edge cases.
411 TimeDelta max_fuzz_delta = TimeDelta::FromHours(7);
412 Time expected_min_time = Time::Now() + expected_days - max_fuzz_delta;
413 Time expected_max_time = Time::Now() + expected_days + max_fuzz_delta;
414 EXPECT_LT(expected_min_time.ToInternalValue(),
415 backoff_expiry_time.ToInternalValue());
416 EXPECT_GT(expected_max_time.ToInternalValue(),
417 backoff_expiry_time.ToInternalValue());
418}
419
420TEST(PayloadStateTest, BackoffPeriodsAreInCorrectRange) {
421 OmahaResponse response;
422 response.is_delta_payload = false;
423 PayloadState payload_state;
424 NiceMock<PrefsMock> prefs;
425
426 EXPECT_TRUE(payload_state.Initialize(&prefs));
427 SetupPayloadStateWith2Urls("Hash8939", &payload_state, &response);
428
429 CheckPayloadBackoffState(&payload_state, 1, TimeDelta::FromDays(1));
430 CheckPayloadBackoffState(&payload_state, 2, TimeDelta::FromDays(2));
431 CheckPayloadBackoffState(&payload_state, 3, TimeDelta::FromDays(4));
432 CheckPayloadBackoffState(&payload_state, 4, TimeDelta::FromDays(8));
433 CheckPayloadBackoffState(&payload_state, 5, TimeDelta::FromDays(16));
434 CheckPayloadBackoffState(&payload_state, 6, TimeDelta::FromDays(16));
435 CheckPayloadBackoffState(&payload_state, 7, TimeDelta::FromDays(16));
436 CheckPayloadBackoffState(&payload_state, 8, TimeDelta::FromDays(16));
437 CheckPayloadBackoffState(&payload_state, 9, TimeDelta::FromDays(16));
438 CheckPayloadBackoffState(&payload_state, 10, TimeDelta::FromDays(16));
439}
440
441TEST(PayloadStateTest, BackoffLogicCanBeDisabled) {
442 OmahaResponse response;
443 response.disable_payload_backoff = true;
444 PayloadState payload_state;
445 NiceMock<PrefsMock> prefs;
446
447 EXPECT_TRUE(payload_state.Initialize(&prefs));
448 SetupPayloadStateWith2Urls("Hash8939", &payload_state, &response);
449
450 // Simulate a successful download and see that we are ready to download
451 // again without any backoff.
452 payload_state.DownloadComplete();
453 EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
454 EXPECT_FALSE(payload_state.ShouldBackoffDownload());
455
456 // Test again, this time by simulating two errors that would cause
457 // the payload attempt number to increment due to wrap around. And
458 // check that we are still ready to re-download without any backoff.
459 payload_state.UpdateFailed(kActionCodeDownloadMetadataSignatureMismatch);
460 payload_state.UpdateFailed(kActionCodeDownloadMetadataSignatureMismatch);
461 EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
462 EXPECT_FALSE(payload_state.ShouldBackoffDownload());
463}
464
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800465}