blob: f94b75609d3ab00cd991be34a2f0561db1ee6746 [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
Chris Sosabe45bef2013-04-09 18:25:12 -07007#include "base/file_path.h"
8#include "base/file_util.h"
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -08009#include "base/stringprintf.h"
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080010#include "gmock/gmock.h"
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080011#include "gtest/gtest.h"
12
Jay Srinivasand29695d2013-04-08 15:08:05 -070013#include "update_engine/constants.h"
David Zeuthenf413fe52013-04-22 14:04:39 -070014#include "update_engine/fake_clock.h"
Jay Srinivasan19409b72013-04-12 19:23:36 -070015#include "update_engine/mock_system_state.h"
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080016#include "update_engine/omaha_request_action.h"
17#include "update_engine/payload_state.h"
David Zeuthenf413fe52013-04-22 14:04:39 -070018#include "update_engine/prefs.h"
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080019#include "update_engine/prefs_mock.h"
20#include "update_engine/test_utils.h"
21#include "update_engine/utils.h"
22
Jay Srinivasan08262882012-12-28 19:29:43 -080023using base::Time;
24using base::TimeDelta;
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080025using std::string;
26using testing::_;
27using testing::NiceMock;
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080028using testing::Return;
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080029using testing::SetArgumentPointee;
David Zeuthen9a017f22013-04-11 16:10:26 -070030using testing::AtLeast;
Jay Srinivasandbd9ea22013-04-22 17:45:19 -070031using testing::AnyNumber;
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080032
33namespace chromeos_update_engine {
34
Jay Srinivasan19409b72013-04-12 19:23:36 -070035const char* kCurrentBytesDownloadedFromHttps =
36 "current-bytes-downloaded-from-HttpsServer";
37const char* kTotalBytesDownloadedFromHttps =
38 "total-bytes-downloaded-from-HttpsServer";
39const char* kCurrentBytesDownloadedFromHttp =
40 "current-bytes-downloaded-from-HttpServer";
41const char* kTotalBytesDownloadedFromHttp =
42 "total-bytes-downloaded-from-HttpServer";
43
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080044static void SetupPayloadStateWith2Urls(string hash,
Jay Srinivasan53173b92013-05-17 17:13:01 -070045 bool http_enabled,
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080046 PayloadState* payload_state,
47 OmahaResponse* response) {
48 response->payload_urls.clear();
49 response->payload_urls.push_back("http://test");
50 response->payload_urls.push_back("https://test");
51 response->size = 523456789;
52 response->hash = hash;
53 response->metadata_size = 558123;
54 response->metadata_signature = "metasign";
55 response->max_failure_count_per_url = 3;
56 payload_state->SetResponse(*response);
Jay Srinivasan08262882012-12-28 19:29:43 -080057 string stored_response_sign = payload_state->GetResponseSignature();
Jay Srinivasan53173b92013-05-17 17:13:01 -070058
59 string expected_url_https_only =
60 "NumURLs = 1\n"
61 "Candidate Url0 = https://test\n";
62
63 string expected_urls_both =
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080064 "NumURLs = 2\n"
Jay Srinivasan53173b92013-05-17 17:13:01 -070065 "Candidate Url0 = http://test\n"
66 "Candidate Url1 = https://test\n";
67
68 string expected_response_sign =
69 (http_enabled ? expected_urls_both : expected_url_https_only) +
70 StringPrintf("Payload Size = 523456789\n"
71 "Payload Sha256 Hash = %s\n"
72 "Metadata Size = 558123\n"
73 "Metadata Signature = metasign\n"
74 "Is Delta Payload = %d\n"
75 "Max Failure Count Per Url = %d\n"
76 "Disable Payload Backoff = %d\n",
77 hash.c_str(),
78 response->is_delta_payload,
79 response->max_failure_count_per_url,
80 response->disable_payload_backoff);
Jay Srinivasan08262882012-12-28 19:29:43 -080081 EXPECT_EQ(expected_response_sign, stored_response_sign);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080082}
83
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080084class PayloadStateTest : public ::testing::Test { };
85
David Zeuthena99981f2013-04-29 13:42:47 -070086TEST(PayloadStateTest, DidYouAddANewErrorCode) {
87 if (kErrorCodeUmaReportedMax != 43) {
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080088 LOG(ERROR) << "The following failure is intentional. If you added a new "
David Zeuthena99981f2013-04-29 13:42:47 -070089 << "ErrorCode enum value, make sure to add it to the "
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080090 << "PayloadState::UpdateFailed method and then update this test "
David Zeuthena99981f2013-04-29 13:42:47 -070091 << "to the new value of kErrorCodeUmaReportedMax, which is "
92 << kErrorCodeUmaReportedMax;
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -080093 EXPECT_FALSE("Please see the log line above");
94 }
95}
96
Jay Srinivasan6f6ea002012-12-14 11:26:28 -080097TEST(PayloadStateTest, SetResponseWorksWithEmptyResponse) {
98 OmahaResponse response;
Jay Srinivasan19409b72013-04-12 19:23:36 -070099 MockSystemState mock_system_state;
100 NiceMock<PrefsMock>* prefs = mock_system_state.mock_prefs();
Jay Srinivasandbd9ea22013-04-22 17:45:19 -0700101 EXPECT_CALL(*prefs, SetInt64(_,_)).Times(AnyNumber());
Jay Srinivasan19409b72013-04-12 19:23:36 -0700102 EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
103 .Times(AtLeast(1));
Alex Deymo820cc702013-06-28 15:43:46 -0700104 EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
105 .Times(AtLeast(1));
Jay Srinivasan19409b72013-04-12 19:23:36 -0700106 EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, 0)).Times(AtLeast(1));
107 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0)).Times(AtLeast(1));
108 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
109 .Times(AtLeast(1));
110 EXPECT_CALL(*prefs, SetInt64(kPrefsUpdateTimestampStart, _))
111 .Times(AtLeast(1));
112 EXPECT_CALL(*prefs, SetInt64(kPrefsUpdateDurationUptime, _))
113 .Times(AtLeast(1));
114 EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttps, 0))
115 .Times(AtLeast(1));
116 EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttp, 0))
117 .Times(AtLeast(1));
Chris Sosabe45bef2013-04-09 18:25:12 -0700118 EXPECT_CALL(*prefs, SetInt64(kPrefsNumReboots, 0)).Times(AtLeast(1));
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800119 PayloadState payload_state;
Jay Srinivasan19409b72013-04-12 19:23:36 -0700120 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800121 payload_state.SetResponse(response);
Jay Srinivasan08262882012-12-28 19:29:43 -0800122 string stored_response_sign = payload_state.GetResponseSignature();
123 string expected_response_sign = "NumURLs = 0\n"
124 "Payload Size = 0\n"
125 "Payload Sha256 Hash = \n"
126 "Metadata Size = 0\n"
127 "Metadata Signature = \n"
128 "Is Delta Payload = 0\n"
129 "Max Failure Count Per Url = 0\n"
130 "Disable Payload Backoff = 0\n";
131 EXPECT_EQ(expected_response_sign, stored_response_sign);
Jay Srinivasan53173b92013-05-17 17:13:01 -0700132 EXPECT_EQ("", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800133 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700134 EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
David Zeuthena573d6f2013-06-14 16:13:36 -0700135 EXPECT_EQ(1, payload_state.GetNumResponsesSeen());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800136}
137
138TEST(PayloadStateTest, SetResponseWorksWithSingleUrl) {
139 OmahaResponse response;
Jay Srinivasan53173b92013-05-17 17:13:01 -0700140 response.payload_urls.push_back("https://single.url.test");
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800141 response.size = 123456789;
142 response.hash = "hash";
143 response.metadata_size = 58123;
144 response.metadata_signature = "msign";
Jay Srinivasan19409b72013-04-12 19:23:36 -0700145 MockSystemState mock_system_state;
146 NiceMock<PrefsMock>* prefs = mock_system_state.mock_prefs();
Jay Srinivasandbd9ea22013-04-22 17:45:19 -0700147 EXPECT_CALL(*prefs, SetInt64(_,_)).Times(AnyNumber());
Jay Srinivasan19409b72013-04-12 19:23:36 -0700148 EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
149 .Times(AtLeast(1));
Alex Deymo820cc702013-06-28 15:43:46 -0700150 EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
151 .Times(AtLeast(1));
Jay Srinivasan19409b72013-04-12 19:23:36 -0700152 EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, 0))
153 .Times(AtLeast(1));
154 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0))
155 .Times(AtLeast(1));
156 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
157 .Times(AtLeast(1));
158 EXPECT_CALL(*prefs, SetInt64(kPrefsUpdateTimestampStart, _))
159 .Times(AtLeast(1));
160 EXPECT_CALL(*prefs, SetInt64(kPrefsUpdateDurationUptime, _))
161 .Times(AtLeast(1));
162 EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttps, 0))
163 .Times(AtLeast(1));
164 EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttp, 0))
165 .Times(AtLeast(1));
Chris Sosabe45bef2013-04-09 18:25:12 -0700166 EXPECT_CALL(*prefs, SetInt64(kPrefsNumReboots, 0))
167 .Times(AtLeast(1));
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800168 PayloadState payload_state;
Jay Srinivasan19409b72013-04-12 19:23:36 -0700169 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800170 payload_state.SetResponse(response);
Jay Srinivasan08262882012-12-28 19:29:43 -0800171 string stored_response_sign = payload_state.GetResponseSignature();
172 string expected_response_sign = "NumURLs = 1\n"
Jay Srinivasan53173b92013-05-17 17:13:01 -0700173 "Candidate Url0 = https://single.url.test\n"
Jay Srinivasan08262882012-12-28 19:29:43 -0800174 "Payload Size = 123456789\n"
175 "Payload Sha256 Hash = hash\n"
176 "Metadata Size = 58123\n"
177 "Metadata Signature = msign\n"
178 "Is Delta Payload = 0\n"
179 "Max Failure Count Per Url = 0\n"
180 "Disable Payload Backoff = 0\n";
181 EXPECT_EQ(expected_response_sign, stored_response_sign);
Jay Srinivasan53173b92013-05-17 17:13:01 -0700182 EXPECT_EQ("https://single.url.test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800183 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700184 EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
David Zeuthena573d6f2013-06-14 16:13:36 -0700185 EXPECT_EQ(1, payload_state.GetNumResponsesSeen());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800186}
187
188TEST(PayloadStateTest, SetResponseWorksWithMultipleUrls) {
189 OmahaResponse response;
190 response.payload_urls.push_back("http://multiple.url.test");
191 response.payload_urls.push_back("https://multiple.url.test");
192 response.size = 523456789;
193 response.hash = "rhash";
194 response.metadata_size = 558123;
195 response.metadata_signature = "metasign";
Jay Srinivasan19409b72013-04-12 19:23:36 -0700196 MockSystemState mock_system_state;
197 NiceMock<PrefsMock>* prefs = mock_system_state.mock_prefs();
Jay Srinivasandbd9ea22013-04-22 17:45:19 -0700198 EXPECT_CALL(*prefs, SetInt64(_,_)).Times(AnyNumber());
Jay Srinivasan19409b72013-04-12 19:23:36 -0700199 EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
200 .Times(AtLeast(1));
Alex Deymo820cc702013-06-28 15:43:46 -0700201 EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
202 .Times(AtLeast(1));
Jay Srinivasan19409b72013-04-12 19:23:36 -0700203 EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, 0))
204 .Times(AtLeast(1));
205 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0))
206 .Times(AtLeast(1));
207 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
208 .Times(AtLeast(1));
209 EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttps, 0))
210 .Times(AtLeast(1));
211 EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttp, 0))
212 .Times(AtLeast(1));
Chris Sosabe45bef2013-04-09 18:25:12 -0700213 EXPECT_CALL(*prefs, SetInt64(kPrefsNumReboots, 0))
214 .Times(AtLeast(1));
Jay Srinivasan53173b92013-05-17 17:13:01 -0700215
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800216 PayloadState payload_state;
Jay Srinivasan19409b72013-04-12 19:23:36 -0700217 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800218 payload_state.SetResponse(response);
Jay Srinivasan08262882012-12-28 19:29:43 -0800219 string stored_response_sign = payload_state.GetResponseSignature();
220 string expected_response_sign = "NumURLs = 2\n"
Jay Srinivasan53173b92013-05-17 17:13:01 -0700221 "Candidate Url0 = http://multiple.url.test\n"
222 "Candidate Url1 = https://multiple.url.test\n"
Jay Srinivasan08262882012-12-28 19:29:43 -0800223 "Payload Size = 523456789\n"
224 "Payload Sha256 Hash = rhash\n"
225 "Metadata Size = 558123\n"
226 "Metadata Signature = metasign\n"
227 "Is Delta Payload = 0\n"
228 "Max Failure Count Per Url = 0\n"
229 "Disable Payload Backoff = 0\n";
230 EXPECT_EQ(expected_response_sign, stored_response_sign);
Jay Srinivasan53173b92013-05-17 17:13:01 -0700231 EXPECT_EQ("http://multiple.url.test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800232 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700233 EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
David Zeuthena573d6f2013-06-14 16:13:36 -0700234 EXPECT_EQ(1, payload_state.GetNumResponsesSeen());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800235}
236
237TEST(PayloadStateTest, CanAdvanceUrlIndexCorrectly) {
238 OmahaResponse response;
Jay Srinivasan19409b72013-04-12 19:23:36 -0700239 MockSystemState mock_system_state;
240 NiceMock<PrefsMock>* prefs = mock_system_state.mock_prefs();
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800241 PayloadState payload_state;
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800242
Jay Srinivasandbd9ea22013-04-22 17:45:19 -0700243 EXPECT_CALL(*prefs, SetInt64(_,_)).Times(AnyNumber());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800244 // Payload attempt should start with 0 and then advance to 1.
Jay Srinivasan19409b72013-04-12 19:23:36 -0700245 EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
246 .Times(AtLeast(1));
247 EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 1))
248 .Times(AtLeast(1));
Alex Deymo820cc702013-06-28 15:43:46 -0700249 EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
250 .Times(AtLeast(1));
251 EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 1))
252 .Times(AtLeast(1));
Jay Srinivasan19409b72013-04-12 19:23:36 -0700253 EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, _)).Times(AtLeast(2));
David Zeuthen9a017f22013-04-11 16:10:26 -0700254
Chris Sosabe45bef2013-04-09 18:25:12 -0700255 // Reboots will be set
256 EXPECT_CALL(*prefs, SetInt64(kPrefsNumReboots, _)).Times(AtLeast(1));
257
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800258 // Url index should go from 0 to 1 twice.
Jay Srinivasan19409b72013-04-12 19:23:36 -0700259 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0)).Times(AtLeast(1));
260 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 1)).Times(AtLeast(1));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800261
262 // Failure count should be called each times url index is set, so that's
263 // 4 times for this test.
Jay Srinivasan19409b72013-04-12 19:23:36 -0700264 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
265 .Times(AtLeast(4));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800266
Jay Srinivasan19409b72013-04-12 19:23:36 -0700267 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800268
269 // This does a SetResponse which causes all the states to be set to 0 for
270 // the first time.
Jay Srinivasan53173b92013-05-17 17:13:01 -0700271 SetupPayloadStateWith2Urls("Hash1235", true, &payload_state, &response);
272 EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800273
274 // Verify that on the first error, the URL index advances to 1.
David Zeuthena99981f2013-04-29 13:42:47 -0700275 ErrorCode error = kErrorCodeDownloadMetadataSignatureMismatch;
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800276 payload_state.UpdateFailed(error);
Jay Srinivasan53173b92013-05-17 17:13:01 -0700277 EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800278
279 // Verify that on the next error, the URL index wraps around to 0.
280 payload_state.UpdateFailed(error);
Jay Srinivasan53173b92013-05-17 17:13:01 -0700281 EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800282
283 // Verify that on the next error, it again advances to 1.
284 payload_state.UpdateFailed(error);
Jay Srinivasan53173b92013-05-17 17:13:01 -0700285 EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
David Zeuthencc6f9962013-04-18 11:57:24 -0700286
287 // Verify that we switched URLs three times
288 EXPECT_EQ(3, payload_state.GetUrlSwitchCount());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800289}
290
291TEST(PayloadStateTest, NewResponseResetsPayloadState) {
292 OmahaResponse response;
Jay Srinivasan19409b72013-04-12 19:23:36 -0700293 MockSystemState mock_system_state;
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800294 PayloadState payload_state;
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800295
Jay Srinivasan19409b72013-04-12 19:23:36 -0700296 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800297
298 // Set the first response.
Jay Srinivasan53173b92013-05-17 17:13:01 -0700299 SetupPayloadStateWith2Urls("Hash5823", true, &payload_state, &response);
David Zeuthena573d6f2013-06-14 16:13:36 -0700300 EXPECT_EQ(1, payload_state.GetNumResponsesSeen());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800301
302 // Advance the URL index to 1 by faking an error.
David Zeuthena99981f2013-04-29 13:42:47 -0700303 ErrorCode error = kErrorCodeDownloadMetadataSignatureMismatch;
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800304 payload_state.UpdateFailed(error);
Jay Srinivasan53173b92013-05-17 17:13:01 -0700305 EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
David Zeuthencc6f9962013-04-18 11:57:24 -0700306 EXPECT_EQ(1, payload_state.GetUrlSwitchCount());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800307
308 // Now, slightly change the response and set it again.
Jay Srinivasan53173b92013-05-17 17:13:01 -0700309 SetupPayloadStateWith2Urls("Hash8225", true, &payload_state, &response);
David Zeuthena573d6f2013-06-14 16:13:36 -0700310 EXPECT_EQ(2, payload_state.GetNumResponsesSeen());
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800311
312 // Make sure the url index was reset to 0 because of the new response.
Jay Srinivasan53173b92013-05-17 17:13:01 -0700313 EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800314 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700315 EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
Jay Srinivasan19409b72013-04-12 19:23:36 -0700316 EXPECT_EQ(0,
317 payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
318 EXPECT_EQ(0,
319 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
320 EXPECT_EQ(0, payload_state.GetCurrentBytesDownloaded(
321 kDownloadSourceHttpsServer));
322 EXPECT_EQ(0,
323 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpsServer));
Jay Srinivasan6f6ea002012-12-14 11:26:28 -0800324}
325
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800326TEST(PayloadStateTest, AllCountersGetUpdatedProperlyOnErrorCodesAndEvents) {
327 OmahaResponse response;
328 PayloadState payload_state;
Jay Srinivasan19409b72013-04-12 19:23:36 -0700329 MockSystemState mock_system_state;
330 int progress_bytes = 100;
331 NiceMock<PrefsMock>* prefs = mock_system_state.mock_prefs();
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800332
Jay Srinivasandbd9ea22013-04-22 17:45:19 -0700333 EXPECT_CALL(*prefs, SetInt64(_,_)).Times(AnyNumber());
Jay Srinivasan19409b72013-04-12 19:23:36 -0700334 EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
335 .Times(AtLeast(2));
336 EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 1))
337 .Times(AtLeast(1));
338 EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 2))
339 .Times(AtLeast(1));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800340
Alex Deymo820cc702013-06-28 15:43:46 -0700341 EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
342 .Times(AtLeast(2));
343 EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 1))
344 .Times(AtLeast(1));
345 EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 2))
346 .Times(AtLeast(1));
347
Jay Srinivasan19409b72013-04-12 19:23:36 -0700348 EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, _)).Times(AtLeast(4));
Jay Srinivasan08262882012-12-28 19:29:43 -0800349
Jay Srinivasan19409b72013-04-12 19:23:36 -0700350 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0)).Times(AtLeast(4));
351 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 1)).Times(AtLeast(2));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800352
Jay Srinivasan19409b72013-04-12 19:23:36 -0700353 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
354 .Times(AtLeast(7));
355 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 1))
356 .Times(AtLeast(2));
357 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 2))
358 .Times(AtLeast(1));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800359
Jay Srinivasan19409b72013-04-12 19:23:36 -0700360 EXPECT_CALL(*prefs, SetInt64(kPrefsUpdateTimestampStart, _))
361 .Times(AtLeast(1));
362 EXPECT_CALL(*prefs, SetInt64(kPrefsUpdateDurationUptime, _))
363 .Times(AtLeast(1));
David Zeuthen9a017f22013-04-11 16:10:26 -0700364
Jay Srinivasan19409b72013-04-12 19:23:36 -0700365 EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttps, 0))
366 .Times(AtLeast(1));
367 EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttp, 0))
368 .Times(AtLeast(1));
369 EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttp, progress_bytes))
370 .Times(AtLeast(1));
371 EXPECT_CALL(*prefs, SetInt64(kTotalBytesDownloadedFromHttp, progress_bytes))
372 .Times(AtLeast(1));
Chris Sosabe45bef2013-04-09 18:25:12 -0700373 EXPECT_CALL(*prefs, SetInt64(kPrefsNumReboots, 0))
374 .Times(AtLeast(1));
Jay Srinivasan19409b72013-04-12 19:23:36 -0700375
376 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800377
Jay Srinivasan53173b92013-05-17 17:13:01 -0700378 SetupPayloadStateWith2Urls("Hash5873", true, &payload_state, &response);
David Zeuthena573d6f2013-06-14 16:13:36 -0700379 EXPECT_EQ(1, payload_state.GetNumResponsesSeen());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800380
381 // This should advance the URL index.
David Zeuthena99981f2013-04-29 13:42:47 -0700382 payload_state.UpdateFailed(kErrorCodeDownloadMetadataSignatureMismatch);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800383 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700384 EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan53173b92013-05-17 17:13:01 -0700385 EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800386 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700387 EXPECT_EQ(1, payload_state.GetUrlSwitchCount());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800388
389 // This should advance the failure count only.
David Zeuthena99981f2013-04-29 13:42:47 -0700390 payload_state.UpdateFailed(kErrorCodeDownloadTransferError);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800391 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700392 EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan53173b92013-05-17 17:13:01 -0700393 EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800394 EXPECT_EQ(1, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700395 EXPECT_EQ(1, payload_state.GetUrlSwitchCount());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800396
397 // This should advance the failure count only.
David Zeuthena99981f2013-04-29 13:42:47 -0700398 payload_state.UpdateFailed(kErrorCodeDownloadTransferError);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800399 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700400 EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan53173b92013-05-17 17:13:01 -0700401 EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800402 EXPECT_EQ(2, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700403 EXPECT_EQ(1, payload_state.GetUrlSwitchCount());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800404
405 // This should advance the URL index as we've reached the
406 // max failure count and reset the failure count for the new URL index.
407 // This should also wrap around the URL index and thus cause the payload
408 // attempt number to be incremented.
David Zeuthena99981f2013-04-29 13:42:47 -0700409 payload_state.UpdateFailed(kErrorCodeDownloadTransferError);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800410 EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700411 EXPECT_EQ(1, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan53173b92013-05-17 17:13:01 -0700412 EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800413 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700414 EXPECT_EQ(2, payload_state.GetUrlSwitchCount());
Jay Srinivasan08262882012-12-28 19:29:43 -0800415 EXPECT_TRUE(payload_state.ShouldBackoffDownload());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800416
417 // This should advance the URL index.
David Zeuthena99981f2013-04-29 13:42:47 -0700418 payload_state.UpdateFailed(kErrorCodePayloadHashMismatchError);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800419 EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700420 EXPECT_EQ(1, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan53173b92013-05-17 17:13:01 -0700421 EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800422 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700423 EXPECT_EQ(3, payload_state.GetUrlSwitchCount());
Jay Srinivasan08262882012-12-28 19:29:43 -0800424 EXPECT_TRUE(payload_state.ShouldBackoffDownload());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800425
426 // This should advance the URL index and payload attempt number due to
427 // wrap-around of URL index.
David Zeuthena99981f2013-04-29 13:42:47 -0700428 payload_state.UpdateFailed(kErrorCodeDownloadMetadataSignatureMissingError);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800429 EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700430 EXPECT_EQ(2, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan53173b92013-05-17 17:13:01 -0700431 EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800432 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700433 EXPECT_EQ(4, payload_state.GetUrlSwitchCount());
Jay Srinivasan08262882012-12-28 19:29:43 -0800434 EXPECT_TRUE(payload_state.ShouldBackoffDownload());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800435
436 // This HTTP error code should only increase the failure count.
David Zeuthena99981f2013-04-29 13:42:47 -0700437 payload_state.UpdateFailed(static_cast<ErrorCode>(
438 kErrorCodeOmahaRequestHTTPResponseBase + 404));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800439 EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700440 EXPECT_EQ(2, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan53173b92013-05-17 17:13:01 -0700441 EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800442 EXPECT_EQ(1, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700443 EXPECT_EQ(4, payload_state.GetUrlSwitchCount());
Jay Srinivasan08262882012-12-28 19:29:43 -0800444 EXPECT_TRUE(payload_state.ShouldBackoffDownload());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800445
446 // And that failure count should be reset when we download some bytes
447 // afterwards.
Jay Srinivasan19409b72013-04-12 19:23:36 -0700448 payload_state.DownloadProgress(progress_bytes);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800449 EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700450 EXPECT_EQ(2, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan53173b92013-05-17 17:13:01 -0700451 EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800452 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700453 EXPECT_EQ(4, payload_state.GetUrlSwitchCount());
Jay Srinivasan08262882012-12-28 19:29:43 -0800454 EXPECT_TRUE(payload_state.ShouldBackoffDownload());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800455
456 // Now, slightly change the response and set it again.
Jay Srinivasan53173b92013-05-17 17:13:01 -0700457 SetupPayloadStateWith2Urls("Hash8532", true, &payload_state, &response);
David Zeuthena573d6f2013-06-14 16:13:36 -0700458 EXPECT_EQ(2, payload_state.GetNumResponsesSeen());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800459
460 // Make sure the url index was reset to 0 because of the new response.
461 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700462 EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan53173b92013-05-17 17:13:01 -0700463 EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800464 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700465 EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
Jay Srinivasan08262882012-12-28 19:29:43 -0800466 EXPECT_FALSE(payload_state.ShouldBackoffDownload());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800467}
468
Alex Deymo820cc702013-06-28 15:43:46 -0700469TEST(PayloadStateTest, PayloadAttemptNumberIncreasesOnSuccessfulFullDownload) {
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800470 OmahaResponse response;
Alex Deymo820cc702013-06-28 15:43:46 -0700471 response.is_delta_payload = false;
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800472 PayloadState payload_state;
Jay Srinivasan19409b72013-04-12 19:23:36 -0700473 MockSystemState mock_system_state;
474 NiceMock<PrefsMock>* prefs = mock_system_state.mock_prefs();
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800475
Jay Srinivasandbd9ea22013-04-22 17:45:19 -0700476 EXPECT_CALL(*prefs, SetInt64(_,_)).Times(AnyNumber());
Jay Srinivasan19409b72013-04-12 19:23:36 -0700477 EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
478 .Times(AtLeast(1));
479 EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 1))
480 .Times(AtLeast(1));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800481
Alex Deymo820cc702013-06-28 15:43:46 -0700482 EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
483 .Times(AtLeast(1));
484 EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 1))
485 .Times(AtLeast(1));
486
Jay Srinivasan19409b72013-04-12 19:23:36 -0700487 EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, _))
488 .Times(AtLeast(2));
Jay Srinivasan08262882012-12-28 19:29:43 -0800489
Jay Srinivasan19409b72013-04-12 19:23:36 -0700490 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0))
491 .Times(AtLeast(1));
492 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
493 .Times(AtLeast(1));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800494
Jay Srinivasan19409b72013-04-12 19:23:36 -0700495 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800496
Jay Srinivasan53173b92013-05-17 17:13:01 -0700497 SetupPayloadStateWith2Urls("Hash8593", true, &payload_state, &response);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800498
499 // This should just advance the payload attempt number;
500 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700501 EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800502 payload_state.DownloadComplete();
503 EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700504 EXPECT_EQ(1, payload_state.GetFullPayloadAttemptNumber());
505 EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
506 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
507 EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
508}
509
510TEST(PayloadStateTest, PayloadAttemptNumberIncreasesOnSuccessfulDeltaDownload) {
511 OmahaResponse response;
512 response.is_delta_payload = true;
513 PayloadState payload_state;
514 MockSystemState mock_system_state;
515 NiceMock<PrefsMock>* prefs = mock_system_state.mock_prefs();
516
517 EXPECT_CALL(*prefs, SetInt64(_,_)).Times(AnyNumber());
518 EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
519 .Times(AtLeast(1));
520 EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 1))
521 .Times(AtLeast(1));
522
523 // kPrefsFullPayloadAttemptNumber is not incremented for delta payloads.
524 EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
525 .Times(AtLeast(1));
526
527 EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, _))
528 .Times(1);
529
530 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0))
531 .Times(AtLeast(1));
532 EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
533 .Times(AtLeast(1));
534
535 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
536
537 SetupPayloadStateWith2Urls("Hash8593", true, &payload_state, &response);
538
539 // This should just advance the payload attempt number;
540 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
541 EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
542 payload_state.DownloadComplete();
543 EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
544 EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan53173b92013-05-17 17:13:01 -0700545 EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800546 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700547 EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800548}
549
550TEST(PayloadStateTest, SetResponseResetsInvalidUrlIndex) {
551 OmahaResponse response;
552 PayloadState payload_state;
Jay Srinivasan19409b72013-04-12 19:23:36 -0700553 MockSystemState mock_system_state;
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800554
Jay Srinivasan19409b72013-04-12 19:23:36 -0700555 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
Jay Srinivasan53173b92013-05-17 17:13:01 -0700556 SetupPayloadStateWith2Urls("Hash4427", true, &payload_state, &response);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800557
558 // Generate enough events to advance URL index, failure count and
559 // payload attempt number all to 1.
560 payload_state.DownloadComplete();
David Zeuthena99981f2013-04-29 13:42:47 -0700561 payload_state.UpdateFailed(kErrorCodeDownloadMetadataSignatureMismatch);
562 payload_state.UpdateFailed(kErrorCodeDownloadTransferError);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800563 EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700564 EXPECT_EQ(1, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan53173b92013-05-17 17:13:01 -0700565 EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800566 EXPECT_EQ(1, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700567 EXPECT_EQ(1, payload_state.GetUrlSwitchCount());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800568
569 // Now, simulate a corrupted url index on persisted store which gets
570 // loaded when update_engine restarts. Using a different prefs object
571 // so as to not bother accounting for the uninteresting calls above.
Jay Srinivasan19409b72013-04-12 19:23:36 -0700572 MockSystemState mock_system_state2;
573 NiceMock<PrefsMock>* prefs2 = mock_system_state2.mock_prefs();
574 EXPECT_CALL(*prefs2, Exists(_)).WillRepeatedly(Return(true));
575 EXPECT_CALL(*prefs2, GetInt64(_,_)).Times(AtLeast(1));
576 EXPECT_CALL(*prefs2, GetInt64(kPrefsPayloadAttemptNumber, _))
577 .Times(AtLeast(1));
Alex Deymo820cc702013-06-28 15:43:46 -0700578 EXPECT_CALL(*prefs2, GetInt64(kPrefsFullPayloadAttemptNumber, _))
579 .Times(AtLeast(1));
Jay Srinivasan19409b72013-04-12 19:23:36 -0700580 EXPECT_CALL(*prefs2, GetInt64(kPrefsCurrentUrlIndex, _))
581 .WillRepeatedly(DoAll(SetArgumentPointee<1>(2), Return(true)));
582 EXPECT_CALL(*prefs2, GetInt64(kPrefsCurrentUrlFailureCount, _))
583 .Times(AtLeast(1));
David Zeuthencc6f9962013-04-18 11:57:24 -0700584 EXPECT_CALL(*prefs2, GetInt64(kPrefsUrlSwitchCount, _))
585 .Times(AtLeast(1));
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800586
587 // Note: This will be a different payload object, but the response should
588 // have the same hash as before so as to not trivially reset because the
589 // response was different. We want to specifically test that even if the
590 // response is same, we should reset the state if we find it corrupted.
Jay Srinivasan19409b72013-04-12 19:23:36 -0700591 EXPECT_TRUE(payload_state.Initialize(&mock_system_state2));
Jay Srinivasan53173b92013-05-17 17:13:01 -0700592 SetupPayloadStateWith2Urls("Hash4427", true, &payload_state, &response);
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800593
594 // Make sure all counters get reset to 0 because of the corrupted URL index
595 // we supplied above.
596 EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700597 EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan53173b92013-05-17 17:13:01 -0700598 EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800599 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
David Zeuthencc6f9962013-04-18 11:57:24 -0700600 EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
Jay Srinivasan2b5a0f02012-12-19 17:25:56 -0800601}
Jay Srinivasan08262882012-12-28 19:29:43 -0800602
603TEST(PayloadStateTest, NoBackoffForDeltaPayloads) {
604 OmahaResponse response;
605 response.is_delta_payload = true;
606 PayloadState payload_state;
Jay Srinivasan19409b72013-04-12 19:23:36 -0700607 MockSystemState mock_system_state;
Jay Srinivasan08262882012-12-28 19:29:43 -0800608
Jay Srinivasan19409b72013-04-12 19:23:36 -0700609 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
Jay Srinivasan53173b92013-05-17 17:13:01 -0700610 SetupPayloadStateWith2Urls("Hash6437", true, &payload_state, &response);
Jay Srinivasan08262882012-12-28 19:29:43 -0800611
612 // Simulate a successful download and see that we're ready to download
613 // again without any backoff as this is a delta payload.
614 payload_state.DownloadComplete();
Alex Deymo820cc702013-06-28 15:43:46 -0700615 EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
616 EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan08262882012-12-28 19:29:43 -0800617 EXPECT_FALSE(payload_state.ShouldBackoffDownload());
618
619 // Simulate two failures (enough to cause payload backoff) and check
620 // again that we're ready to re-download without any backoff as this is
621 // a delta payload.
David Zeuthena99981f2013-04-29 13:42:47 -0700622 payload_state.UpdateFailed(kErrorCodeDownloadMetadataSignatureMismatch);
623 payload_state.UpdateFailed(kErrorCodeDownloadMetadataSignatureMismatch);
Jay Srinivasan53173b92013-05-17 17:13:01 -0700624 EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
Alex Deymo820cc702013-06-28 15:43:46 -0700625 EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
626 EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan08262882012-12-28 19:29:43 -0800627 EXPECT_FALSE(payload_state.ShouldBackoffDownload());
628}
629
630static void CheckPayloadBackoffState(PayloadState* payload_state,
631 int expected_attempt_number,
632 TimeDelta expected_days) {
633 payload_state->DownloadComplete();
Alex Deymo820cc702013-06-28 15:43:46 -0700634 EXPECT_EQ(expected_attempt_number,
635 payload_state->GetFullPayloadAttemptNumber());
Jay Srinivasan08262882012-12-28 19:29:43 -0800636 EXPECT_TRUE(payload_state->ShouldBackoffDownload());
637 Time backoff_expiry_time = payload_state->GetBackoffExpiryTime();
638 // Add 1 hour extra to the 6 hour fuzz check to tolerate edge cases.
639 TimeDelta max_fuzz_delta = TimeDelta::FromHours(7);
640 Time expected_min_time = Time::Now() + expected_days - max_fuzz_delta;
641 Time expected_max_time = Time::Now() + expected_days + max_fuzz_delta;
642 EXPECT_LT(expected_min_time.ToInternalValue(),
643 backoff_expiry_time.ToInternalValue());
644 EXPECT_GT(expected_max_time.ToInternalValue(),
645 backoff_expiry_time.ToInternalValue());
646}
647
648TEST(PayloadStateTest, BackoffPeriodsAreInCorrectRange) {
649 OmahaResponse response;
650 response.is_delta_payload = false;
651 PayloadState payload_state;
Jay Srinivasan19409b72013-04-12 19:23:36 -0700652 MockSystemState mock_system_state;
Jay Srinivasan08262882012-12-28 19:29:43 -0800653
Jay Srinivasan19409b72013-04-12 19:23:36 -0700654 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
Jay Srinivasan53173b92013-05-17 17:13:01 -0700655 SetupPayloadStateWith2Urls("Hash8939", true, &payload_state, &response);
Jay Srinivasan08262882012-12-28 19:29:43 -0800656
657 CheckPayloadBackoffState(&payload_state, 1, TimeDelta::FromDays(1));
658 CheckPayloadBackoffState(&payload_state, 2, TimeDelta::FromDays(2));
659 CheckPayloadBackoffState(&payload_state, 3, TimeDelta::FromDays(4));
660 CheckPayloadBackoffState(&payload_state, 4, TimeDelta::FromDays(8));
661 CheckPayloadBackoffState(&payload_state, 5, TimeDelta::FromDays(16));
662 CheckPayloadBackoffState(&payload_state, 6, TimeDelta::FromDays(16));
663 CheckPayloadBackoffState(&payload_state, 7, TimeDelta::FromDays(16));
664 CheckPayloadBackoffState(&payload_state, 8, TimeDelta::FromDays(16));
665 CheckPayloadBackoffState(&payload_state, 9, TimeDelta::FromDays(16));
666 CheckPayloadBackoffState(&payload_state, 10, TimeDelta::FromDays(16));
667}
668
669TEST(PayloadStateTest, BackoffLogicCanBeDisabled) {
670 OmahaResponse response;
671 response.disable_payload_backoff = true;
672 PayloadState payload_state;
Jay Srinivasan19409b72013-04-12 19:23:36 -0700673 MockSystemState mock_system_state;
Jay Srinivasan08262882012-12-28 19:29:43 -0800674
Jay Srinivasan19409b72013-04-12 19:23:36 -0700675 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
Jay Srinivasan53173b92013-05-17 17:13:01 -0700676 SetupPayloadStateWith2Urls("Hash8939", true, &payload_state, &response);
Jay Srinivasan08262882012-12-28 19:29:43 -0800677
678 // Simulate a successful download and see that we are ready to download
679 // again without any backoff.
680 payload_state.DownloadComplete();
681 EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700682 EXPECT_EQ(1, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan08262882012-12-28 19:29:43 -0800683 EXPECT_FALSE(payload_state.ShouldBackoffDownload());
684
685 // Test again, this time by simulating two errors that would cause
686 // the payload attempt number to increment due to wrap around. And
687 // check that we are still ready to re-download without any backoff.
David Zeuthena99981f2013-04-29 13:42:47 -0700688 payload_state.UpdateFailed(kErrorCodeDownloadMetadataSignatureMismatch);
689 payload_state.UpdateFailed(kErrorCodeDownloadMetadataSignatureMismatch);
Jay Srinivasan08262882012-12-28 19:29:43 -0800690 EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
Alex Deymo820cc702013-06-28 15:43:46 -0700691 EXPECT_EQ(2, payload_state.GetFullPayloadAttemptNumber());
Jay Srinivasan08262882012-12-28 19:29:43 -0800692 EXPECT_FALSE(payload_state.ShouldBackoffDownload());
693}
694
Jay Srinivasan19409b72013-04-12 19:23:36 -0700695TEST(PayloadStateTest, BytesDownloadedMetricsGetAddedToCorrectSources) {
696 OmahaResponse response;
697 response.disable_payload_backoff = true;
698 PayloadState payload_state;
699 MockSystemState mock_system_state;
700 int https_total = 0;
701 int http_total = 0;
702
703 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
Jay Srinivasan53173b92013-05-17 17:13:01 -0700704 SetupPayloadStateWith2Urls("Hash3286", true, &payload_state, &response);
David Zeuthena573d6f2013-06-14 16:13:36 -0700705 EXPECT_EQ(1, payload_state.GetNumResponsesSeen());
Jay Srinivasan19409b72013-04-12 19:23:36 -0700706
Jay Srinivasandbd9ea22013-04-22 17:45:19 -0700707 // Simulate a previous attempt with in order to set an initial non-zero value
708 // for the total bytes downloaded for HTTP.
709 int prev_chunk = 323456789;
710 http_total += prev_chunk;
711 payload_state.DownloadProgress(prev_chunk);
712
713 // Ensure that the initial values for HTTP reflect this attempt.
714 EXPECT_EQ(prev_chunk,
715 payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
716 EXPECT_EQ(http_total,
717 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
718
719 // Change the response hash so as to simulate a new response which will
720 // reset the current bytes downloaded, but not the total bytes downloaded.
Jay Srinivasan53173b92013-05-17 17:13:01 -0700721 SetupPayloadStateWith2Urls("Hash9904", true, &payload_state, &response);
David Zeuthena573d6f2013-06-14 16:13:36 -0700722 EXPECT_EQ(2, payload_state.GetNumResponsesSeen());
Jay Srinivasandbd9ea22013-04-22 17:45:19 -0700723
724 // First, simulate successful download of a few bytes over HTTP.
Jay Srinivasan19409b72013-04-12 19:23:36 -0700725 int first_chunk = 5000000;
726 http_total += first_chunk;
727 payload_state.DownloadProgress(first_chunk);
Jay Srinivasan53173b92013-05-17 17:13:01 -0700728 // Test that first all progress is made on HTTP and none on HTTPS.
Jay Srinivasan19409b72013-04-12 19:23:36 -0700729 EXPECT_EQ(first_chunk,
730 payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
731 EXPECT_EQ(http_total,
732 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
733 EXPECT_EQ(0, payload_state.GetCurrentBytesDownloaded(
734 kDownloadSourceHttpsServer));
735 EXPECT_EQ(https_total,
736 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpsServer));
737
738 // Simulate an error that'll cause the url index to point to https.
David Zeuthena99981f2013-04-29 13:42:47 -0700739 ErrorCode error = kErrorCodeDownloadMetadataSignatureMismatch;
Jay Srinivasan19409b72013-04-12 19:23:36 -0700740 payload_state.UpdateFailed(error);
741
Jay Srinivasan53173b92013-05-17 17:13:01 -0700742 // Test that no new progress is made on HTTP and new progress is on HTTPS.
Jay Srinivasan19409b72013-04-12 19:23:36 -0700743 int second_chunk = 23456789;
744 https_total += second_chunk;
745 payload_state.DownloadProgress(second_chunk);
746 EXPECT_EQ(first_chunk,
747 payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
748 EXPECT_EQ(http_total,
749 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
750 EXPECT_EQ(second_chunk, payload_state.GetCurrentBytesDownloaded(
751 kDownloadSourceHttpsServer));
752 EXPECT_EQ(https_total,
753 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpsServer));
754
755 // Simulate error to go back to http.
756 payload_state.UpdateFailed(error);
757 int third_chunk = 32345678;
758 int http_chunk = first_chunk + third_chunk;
759 http_total += third_chunk;
760 int https_chunk = second_chunk;
761 payload_state.DownloadProgress(third_chunk);
762
763 // Test that third chunk is again back on HTTP. HTTPS remains on second chunk.
764 EXPECT_EQ(http_chunk,
765 payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
Jay Srinivasandbd9ea22013-04-22 17:45:19 -0700766 EXPECT_EQ(http_total,
Jay Srinivasan19409b72013-04-12 19:23:36 -0700767 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
768 EXPECT_EQ(second_chunk, payload_state.GetCurrentBytesDownloaded(
769 kDownloadSourceHttpsServer));
770 EXPECT_EQ(https_total,
771 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpsServer));
772
Jay Srinivasandbd9ea22013-04-22 17:45:19 -0700773 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendToUMA(_, _, _, _, _))
774 .Times(AnyNumber());
Jay Srinivasan19409b72013-04-12 19:23:36 -0700775 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendToUMA(
776 "Installer.SuccessfulMBsDownloadedFromHttpServer",
777 http_chunk / kNumBytesInOneMiB, _, _, _));
778 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendToUMA(
779 "Installer.TotalMBsDownloadedFromHttpServer",
780 http_total / kNumBytesInOneMiB, _, _, _));
781 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendToUMA(
782 "Installer.SuccessfulMBsDownloadedFromHttpsServer",
783 https_chunk / kNumBytesInOneMiB, _, _, _));
784 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendToUMA(
785 "Installer.TotalMBsDownloadedFromHttpsServer",
786 https_total / kNumBytesInOneMiB, _, _, _));
David Zeuthencc6f9962013-04-18 11:57:24 -0700787 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendToUMA(
788 "Installer.UpdateURLSwitches",
789 2, _, _, _));
David Zeuthen674c3182013-04-18 14:05:20 -0700790 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendToUMA(
791 "Installer.UpdateDurationMinutes",
792 _, _, _, _));
793 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendToUMA(
794 "Installer.UpdateDurationUptimeMinutes",
795 _, _, _, _));
Jay Srinivasandbd9ea22013-04-22 17:45:19 -0700796 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendToUMA(
797 "Installer.DownloadSourcesUsed", 3, _, _, _));
798 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendToUMA(
799 "Installer.DownloadOverheadPercentage", 542, _, _, _));
Alex Deymo1c656c42013-06-28 11:02:14 -0700800 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendEnumToUMA(
801 "Installer.PayloadFormat", kPayloadTypeFull, kNumPayloadTypes));
Alex Deymo820cc702013-06-28 15:43:46 -0700802 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendToUMA(
803 "Installer.AttemptsCount.Total", 1, _, _, _));
Jay Srinivasan19409b72013-04-12 19:23:36 -0700804
805 payload_state.UpdateSucceeded();
806
807 // Make sure the metrics are reset after a successful update.
808 EXPECT_EQ(0,
809 payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
810 EXPECT_EQ(0,
811 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
812 EXPECT_EQ(0, payload_state.GetCurrentBytesDownloaded(
813 kDownloadSourceHttpsServer));
814 EXPECT_EQ(0,
815 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpsServer));
David Zeuthena573d6f2013-06-14 16:13:36 -0700816 EXPECT_EQ(0, payload_state.GetNumResponsesSeen());
Jay Srinivasan19409b72013-04-12 19:23:36 -0700817}
818
819TEST(PayloadStateTest, RestartingUpdateResetsMetrics) {
820 OmahaResponse response;
821 MockSystemState mock_system_state;
822 PayloadState payload_state;
823
824 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
825
826 // Set the first response.
Jay Srinivasan53173b92013-05-17 17:13:01 -0700827 SetupPayloadStateWith2Urls("Hash5823", true, &payload_state, &response);
Jay Srinivasan19409b72013-04-12 19:23:36 -0700828
829 int num_bytes = 10000;
830 payload_state.DownloadProgress(num_bytes);
831 EXPECT_EQ(num_bytes,
832 payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
833 EXPECT_EQ(num_bytes,
834 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
835 EXPECT_EQ(0, payload_state.GetCurrentBytesDownloaded(
836 kDownloadSourceHttpsServer));
837 EXPECT_EQ(0,
838 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpsServer));
839
840 payload_state.UpdateRestarted();
841 // Make sure the current bytes downloaded is reset, but not the total bytes.
842 EXPECT_EQ(0,
843 payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
844 EXPECT_EQ(num_bytes,
845 payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
846}
847
Chris Sosabe45bef2013-04-09 18:25:12 -0700848TEST(PayloadStateTest, NumRebootsIncrementsCorrectly) {
849 MockSystemState mock_system_state;
850 PayloadState payload_state;
Jay Srinivasan19409b72013-04-12 19:23:36 -0700851
Chris Sosabe45bef2013-04-09 18:25:12 -0700852 NiceMock<PrefsMock>* prefs = mock_system_state.mock_prefs();
853 EXPECT_CALL(*prefs, SetInt64(_,_)).Times(AtLeast(0));
854 EXPECT_CALL(*prefs, SetInt64(kPrefsNumReboots, 1)).Times(AtLeast(1));
855
856 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
857
858 payload_state.UpdateRestarted();
859 EXPECT_EQ(0, payload_state.GetNumReboots());
860
861 EXPECT_CALL(mock_system_state, system_rebooted()).WillOnce(Return(true));
862 payload_state.UpdateResumed();
863 // Num reboots should be incremented because system rebooted detected.
864 EXPECT_EQ(1, payload_state.GetNumReboots());
865
866 EXPECT_CALL(mock_system_state, system_rebooted()).WillOnce(Return(false));
867 payload_state.UpdateResumed();
868 // Num reboots should now be 1 as reboot was not detected.
869 EXPECT_EQ(1, payload_state.GetNumReboots());
870
871 // Restart the update again to verify we set the num of reboots back to 0.
872 payload_state.UpdateRestarted();
873 EXPECT_EQ(0, payload_state.GetNumReboots());
874}
Jay Srinivasan19409b72013-04-12 19:23:36 -0700875
Chris Sosaaa18e162013-06-20 13:20:30 -0700876TEST(PayloadStateTest, RollbackVersion) {
877 MockSystemState mock_system_state;
878 PayloadState payload_state;
879
880 NiceMock<PrefsMock>* mock_powerwash_safe_prefs =
881 mock_system_state.mock_powerwash_safe_prefs();
882 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
883
884 // Verify pre-conditions are good.
885 EXPECT_TRUE(payload_state.GetRollbackVersion().empty());
886
887 // Mock out the os version and make sure it's blacklisted correctly.
888 string rollback_version = "2345.0.0";
889 OmahaRequestParams params(&mock_system_state);
890 params.Init(rollback_version, "", false);
891 mock_system_state.set_request_params(&params);
892
893 EXPECT_CALL(*mock_powerwash_safe_prefs, SetString(kPrefsRollbackVersion,
894 rollback_version));
895 payload_state.Rollback();
896
897 EXPECT_EQ(rollback_version, payload_state.GetRollbackVersion());
898}
899
David Zeuthenf413fe52013-04-22 14:04:39 -0700900TEST(PayloadStateTest, DurationsAreCorrect) {
901 OmahaResponse response;
902 PayloadState payload_state;
903 MockSystemState mock_system_state;
904 FakeClock fake_clock;
905 Prefs prefs;
906 string temp_dir;
907
908 // Set the clock to a well-known time - 1 second on the wall-clock
909 // and 2 seconds on the monotonic clock
910 fake_clock.SetWallclockTime(Time::FromInternalValue(1000000));
911 fake_clock.SetMonotonicTime(Time::FromInternalValue(2000000));
912
913 // We need persistent preferences for this test
914 EXPECT_TRUE(utils::MakeTempDirectory("/tmp/PayloadStateDurationTests.XXXXXX",
915 &temp_dir));
916 prefs.Init(FilePath(temp_dir));
917
918 mock_system_state.set_clock(&fake_clock);
919 mock_system_state.set_prefs(&prefs);
920 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
921
922 // Check that durations are correct for a successful update where
923 // time has advanced 7 seconds on the wall clock and 4 seconds on
924 // the monotonic clock.
Jay Srinivasan53173b92013-05-17 17:13:01 -0700925 SetupPayloadStateWith2Urls("Hash8593", true, &payload_state, &response);
David Zeuthenf413fe52013-04-22 14:04:39 -0700926 fake_clock.SetWallclockTime(Time::FromInternalValue(8000000));
927 fake_clock.SetMonotonicTime(Time::FromInternalValue(6000000));
928 payload_state.UpdateSucceeded();
929 EXPECT_EQ(payload_state.GetUpdateDuration().InMicroseconds(), 7000000);
930 EXPECT_EQ(payload_state.GetUpdateDurationUptime().InMicroseconds(), 4000000);
931
932 // Check that durations are reset when a new response comes in.
Jay Srinivasan53173b92013-05-17 17:13:01 -0700933 SetupPayloadStateWith2Urls("Hash8594", true, &payload_state, &response);
David Zeuthenf413fe52013-04-22 14:04:39 -0700934 EXPECT_EQ(payload_state.GetUpdateDuration().InMicroseconds(), 0);
935 EXPECT_EQ(payload_state.GetUpdateDurationUptime().InMicroseconds(), 0);
936
937 // Advance time a bit (10 secs), simulate download progress and
938 // check that durations are updated.
939 fake_clock.SetWallclockTime(Time::FromInternalValue(18000000));
940 fake_clock.SetMonotonicTime(Time::FromInternalValue(16000000));
941 payload_state.DownloadProgress(10);
942 EXPECT_EQ(payload_state.GetUpdateDuration().InMicroseconds(), 10000000);
943 EXPECT_EQ(payload_state.GetUpdateDurationUptime().InMicroseconds(), 10000000);
944
945 // Now simulate a reboot by resetting monotonic time (to 5000) and
946 // creating a new PayloadState object and check that we load the
947 // durations correctly (e.g. they are the same as before).
948 fake_clock.SetMonotonicTime(Time::FromInternalValue(5000));
949 PayloadState payload_state2;
950 EXPECT_TRUE(payload_state2.Initialize(&mock_system_state));
951 EXPECT_EQ(payload_state2.GetUpdateDuration().InMicroseconds(), 10000000);
952 EXPECT_EQ(payload_state2.GetUpdateDurationUptime().InMicroseconds(),10000000);
953
954 // Advance wall-clock by 7 seconds and monotonic clock by 6 seconds
955 // and check that the durations are increased accordingly.
956 fake_clock.SetWallclockTime(Time::FromInternalValue(25000000));
957 fake_clock.SetMonotonicTime(Time::FromInternalValue(6005000));
958 payload_state2.UpdateSucceeded();
959 EXPECT_EQ(payload_state2.GetUpdateDuration().InMicroseconds(), 17000000);
960 EXPECT_EQ(payload_state2.GetUpdateDurationUptime().InMicroseconds(),16000000);
961
962 EXPECT_TRUE(utils::RecursiveUnlinkDir(temp_dir));
963}
964
David Zeuthene4c58bf2013-06-18 17:26:50 -0700965TEST(PayloadStateTest, RebootAfterSuccessfulUpdateTest) {
966 OmahaResponse response;
967 PayloadState payload_state;
968 MockSystemState mock_system_state;
969 FakeClock fake_clock;
970 Prefs prefs;
971 string temp_dir;
972
973 // Set the clock to a well-known time (t = 30 seconds).
974 fake_clock.SetWallclockTime(Time::FromInternalValue(
975 30 * Time::kMicrosecondsPerSecond));
976
977 // We need persistent preferences for this test
978 EXPECT_TRUE(utils::MakeTempDirectory(
979 "/tmp/RebootAfterSuccessfulUpdateTest.XXXXXX", &temp_dir));
980 prefs.Init(FilePath(temp_dir));
981
982 mock_system_state.set_clock(&fake_clock);
983 mock_system_state.set_prefs(&prefs);
984 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
985
986 // Make the update succeed.
987 SetupPayloadStateWith2Urls("Hash8593", true, &payload_state, &response);
988 payload_state.UpdateSucceeded();
989
990 // Check that the marker was written.
991 EXPECT_TRUE(prefs.Exists(kPrefsSystemUpdatedMarker));
992
993 // Now simulate a reboot and set the wallclock time to a later point
994 // (t = 500 seconds). We do this by using a new PayloadState object
995 // and checking that it emits the right UMA metric with the right
996 // value.
997 fake_clock.SetWallclockTime(Time::FromInternalValue(
998 500 * Time::kMicrosecondsPerSecond));
999 PayloadState payload_state2;
1000 EXPECT_TRUE(payload_state2.Initialize(&mock_system_state));
1001
1002 // Expect 500 - 30 seconds = 470 seconds ~= 7 min 50 sec
1003 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendToUMA(
1004 "Installer.TimeToRebootMinutes",
1005 7, _, _, _));
1006
1007 payload_state2.UpdateEngineStarted();
1008
1009 // Check that the marker was nuked.
1010 EXPECT_FALSE(prefs.Exists(kPrefsSystemUpdatedMarker));
1011
1012 EXPECT_TRUE(utils::RecursiveUnlinkDir(temp_dir));
1013}
1014
Jay Srinivasan53173b92013-05-17 17:13:01 -07001015TEST(PayloadStateTest, CandidateUrlsComputedCorrectly) {
1016 OmahaResponse response;
1017 MockSystemState mock_system_state;
1018 PayloadState payload_state;
1019
1020 // Pretend that this is an offical build so that the HTTP download policy
1021 // is honored.
1022 EXPECT_CALL(mock_system_state, IsOfficialBuild())
1023 .WillRepeatedly(Return(true));
1024
1025 policy::MockDevicePolicy disable_http_policy;
1026 EXPECT_CALL(mock_system_state, device_policy())
1027 .WillRepeatedly(Return(&disable_http_policy));
1028 EXPECT_CALL(disable_http_policy, GetHttpDownloadsEnabled(_))
1029 .WillRepeatedly(DoAll(SetArgumentPointee<0>(false), Return(true)));
1030
1031 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
1032
1033 // Set the first response.
1034 SetupPayloadStateWith2Urls("Hash8433", false, &payload_state, &response);
1035
1036 // Check that we skip the HTTP URL and use only the HTTPS url.
1037 EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
1038
1039 // Advance the URL index to 1 by faking an error.
1040 ErrorCode error = kErrorCodeDownloadMetadataSignatureMismatch;
1041 payload_state.UpdateFailed(error);
1042
1043 // Check that we still skip the HTTP URL and use only the HTTPS url.
1044 EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
1045 EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
1046
1047 // Now, slightly change the response and set it again.
1048 SetupPayloadStateWith2Urls("Hash2399", false, &payload_state, &response);
1049
1050 // Check that we still skip the HTTP URL and use only the HTTPS url.
1051 EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
1052
1053 // Now, pretend that the HTTP policy is turned on. We want to make sure
1054 // the new policy is honored.
1055 policy::MockDevicePolicy enable_http_policy;
1056 EXPECT_CALL(mock_system_state, device_policy())
1057 .WillRepeatedly(Return(&enable_http_policy));
1058 EXPECT_CALL(enable_http_policy, GetHttpDownloadsEnabled(_))
1059 .WillRepeatedly(DoAll(SetArgumentPointee<0>(true), Return(true)));
1060
1061 // Now, set the same response using the same hash
1062 // so that we can test that the state is reset not because of the
1063 // hash but because of the policy change which results in candidate url
1064 // list change.
1065 SetupPayloadStateWith2Urls("Hash2399", true, &payload_state, &response);
1066
1067 // Check that we use the HTTP URL now and the failure count is reset.
1068 EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
1069 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
1070
1071 // Fake a failure and see if we're moving over to the HTTPS url and update
1072 // the URL switch count properly.
1073 payload_state.UpdateFailed(error);
1074 EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
1075 EXPECT_EQ(1, payload_state.GetUrlSwitchCount());
1076 EXPECT_EQ(0, payload_state.GetUrlFailureCount());
1077}
1078
Alex Deymo1c656c42013-06-28 11:02:14 -07001079TEST(PayloadStateTest, PayloadTypeMetricWhenTypeIsDelta) {
1080 OmahaResponse response;
1081 response.is_delta_payload = true;
1082 PayloadState payload_state;
1083 MockSystemState mock_system_state;
1084
1085 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
1086 SetupPayloadStateWith2Urls("Hash6437", true, &payload_state, &response);
1087
1088 // Simulate a successful download and update.
1089 payload_state.DownloadComplete();
1090
1091 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendEnumToUMA(
1092 "Installer.PayloadFormat", kPayloadTypeDelta, kNumPayloadTypes));
1093 payload_state.UpdateSucceeded();
1094
1095 // Mock the request to a request where the delta was disabled but Omaha sends
1096 // a delta anyway and test again.
1097 OmahaRequestParams params(&mock_system_state);
1098 params.set_delta_okay(false);
1099 mock_system_state.set_request_params(&params);
1100
1101 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
1102 SetupPayloadStateWith2Urls("Hash6437", true, &payload_state, &response);
1103
1104 payload_state.DownloadComplete();
1105
1106 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendEnumToUMA(
1107 "Installer.PayloadFormat", kPayloadTypeDelta, kNumPayloadTypes));
1108 payload_state.UpdateSucceeded();
1109}
1110
1111TEST(PayloadStateTest, PayloadTypeMetricWhenTypeIsForcedFull) {
1112 OmahaResponse response;
1113 response.is_delta_payload = false;
1114 PayloadState payload_state;
1115 MockSystemState mock_system_state;
1116
1117 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
1118 SetupPayloadStateWith2Urls("Hash6437", true, &payload_state, &response);
1119
1120 // Mock the request to a request where the delta was disabled.
1121 OmahaRequestParams params(&mock_system_state);
1122 params.set_delta_okay(false);
1123 mock_system_state.set_request_params(&params);
1124
1125 // Simulate a successful download and update.
1126 payload_state.DownloadComplete();
1127
1128 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendEnumToUMA(
1129 "Installer.PayloadFormat", kPayloadTypeForcedFull, kNumPayloadTypes));
1130 payload_state.UpdateSucceeded();
1131}
1132
1133TEST(PayloadStateTest, PayloadTypeMetricWhenTypeIsFull) {
1134 OmahaResponse response;
1135 response.is_delta_payload = false;
1136 PayloadState payload_state;
1137 MockSystemState mock_system_state;
1138
1139 EXPECT_TRUE(payload_state.Initialize(&mock_system_state));
1140 SetupPayloadStateWith2Urls("Hash6437", true, &payload_state, &response);
1141
Alex Deymo820cc702013-06-28 15:43:46 -07001142 // Mock the request to a request where the delta is enabled, although the
1143 // result is full.
Alex Deymo1c656c42013-06-28 11:02:14 -07001144 OmahaRequestParams params(&mock_system_state);
1145 params.set_delta_okay(true);
1146 mock_system_state.set_request_params(&params);
1147
1148 // Simulate a successful download and update.
1149 payload_state.DownloadComplete();
1150
1151 EXPECT_CALL(*mock_system_state.mock_metrics_lib(), SendEnumToUMA(
1152 "Installer.PayloadFormat", kPayloadTypeFull, kNumPayloadTypes));
1153 payload_state.UpdateSucceeded();
1154}
1155
Jay Srinivasan6f6ea002012-12-14 11:26:28 -08001156}