google_update_settings_unittest.cc revision eb525c5499e34cc9c4b825d6d9e75bb07cc06ace
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
3// found in the LICENSE file.
4
5#include <windows.h>
6#include <shlwapi.h>  // For SHDeleteKey.
7
8#include "base/memory/scoped_ptr.h"
9#include "base/strings/utf_string_conversions.h"
10#include "base/test/test_reg_util_win.h"
11#include "base/win/registry.h"
12#include "chrome/common/chrome_constants.h"
13#include "chrome/installer/util/browser_distribution.h"
14#include "chrome/installer/util/channel_info.h"
15#include "chrome/installer/util/fake_installation_state.h"
16#include "chrome/installer/util/google_update_constants.h"
17#include "chrome/installer/util/google_update_settings.h"
18#include "chrome/installer/util/util_constants.h"
19#include "chrome/installer/util/work_item_list.h"
20#include "testing/gtest/include/gtest/gtest.h"
21
22using base::win::RegKey;
23using installer::ChannelInfo;
24
25namespace {
26
27const wchar_t kGoogleUpdatePoliciesKey[] =
28    L"SOFTWARE\\Policies\\Google\\Update";
29const wchar_t kGoogleUpdateUpdateDefault[] = L"UpdateDefault";
30const wchar_t kGoogleUpdateUpdatePrefix[] = L"Update";
31const GoogleUpdateSettings::UpdatePolicy kDefaultUpdatePolicy =
32#if defined(GOOGLE_CHROME_BUILD)
33    GoogleUpdateSettings::AUTOMATIC_UPDATES;
34#else
35    GoogleUpdateSettings::UPDATES_DISABLED;
36#endif
37
38const wchar_t kTestProductGuid[] = L"{89F1B351-B15D-48D4-8F10-1298721CF13D}";
39const wchar_t kTestExperimentLabel[] = L"test_label_value";
40
41// This test fixture redirects the HKLM and HKCU registry hives for
42// the duration of the test to make it independent of the machine
43// and user settings.
44class GoogleUpdateSettingsTest : public testing::Test {
45 protected:
46  virtual void SetUp() OVERRIDE {
47    registry_overrides_.OverrideRegistry(HKEY_LOCAL_MACHINE, L"HKLM_pit");
48    registry_overrides_.OverrideRegistry(HKEY_CURRENT_USER, L"HKCU_pit");
49  }
50
51  enum SystemUserInstall {
52    SYSTEM_INSTALL,
53    USER_INSTALL,
54  };
55
56  void SetApField(SystemUserInstall is_system, const wchar_t* value) {
57    HKEY root = is_system == SYSTEM_INSTALL ?
58        HKEY_LOCAL_MACHINE : HKEY_CURRENT_USER;
59
60    RegKey update_key;
61    BrowserDistribution* dist = BrowserDistribution::GetDistribution();
62    std::wstring path = dist->GetStateKey();
63    ASSERT_EQ(ERROR_SUCCESS, update_key.Create(root, path.c_str(), KEY_WRITE));
64    ASSERT_EQ(ERROR_SUCCESS, update_key.WriteValue(L"ap", value));
65  }
66
67  // Tests setting the ap= value to various combinations of values with
68  // prefixes and suffixes, while asserting on the correct channel value.
69  // Note that any non-empty ap= value that doesn't match ".*-{dev|beta}.*"
70  // will return the "unknown" channel.
71  void TestCurrentChromeChannelWithVariousApValues(SystemUserInstall install) {
72    static struct Expectations {
73      const wchar_t* ap_value;
74      const wchar_t* channel;
75    } expectations[] = {
76      { L"dev", installer::kChromeChannelDev },
77      { L"-dev", installer::kChromeChannelDev },
78      { L"-developer", installer::kChromeChannelDev },
79      { L"beta", installer::kChromeChannelBeta },
80      { L"-beta", installer::kChromeChannelBeta },
81      { L"-betamax", installer::kChromeChannelBeta },
82    };
83    bool is_system = install == SYSTEM_INSTALL;
84    const wchar_t* prefixes[] = {
85      L"",
86      L"prefix",
87      L"prefix-with-dash",
88    };
89    const wchar_t* suffixes[] = {
90      L"",
91      L"suffix",
92      L"suffix-with-dash",
93    };
94
95    for (size_t i = 0; i < arraysize(prefixes); ++i) {
96      for (size_t j = 0; j < arraysize(expectations); ++j) {
97        for (size_t k = 0; k < arraysize(suffixes); ++k) {
98          std::wstring ap = prefixes[i];
99          ap += expectations[j].ap_value;
100          ap += suffixes[k];
101          const wchar_t* channel = expectations[j].channel;
102
103          SetApField(install, ap.c_str());
104          string16 ret_channel;
105
106          EXPECT_TRUE(GoogleUpdateSettings::GetChromeChannelAndModifiers(
107              is_system, &ret_channel));
108          EXPECT_STREQ(channel, ret_channel.c_str())
109              << "Expecting channel \"" << channel
110              << "\" for ap=\"" << ap << "\"";
111        }
112      }
113    }
114  }
115
116  // Test the writing and deleting functionality of the experiments label
117  // helper.
118  void TestExperimentsLabelHelper(SystemUserInstall install) {
119    BrowserDistribution* chrome =
120        BrowserDistribution::GetSpecificDistribution(
121            BrowserDistribution::CHROME_BROWSER);
122    std::wstring value;
123#if defined(GOOGLE_CHROME_BUILD)
124    EXPECT_TRUE(chrome->ShouldSetExperimentLabels());
125
126    // Before anything is set, ReadExperimentLabels should succeed but return
127    // an empty string.
128    EXPECT_TRUE(GoogleUpdateSettings::ReadExperimentLabels(
129        install == SYSTEM_INSTALL, &value));
130    EXPECT_EQ(string16(), value);
131
132    EXPECT_TRUE(GoogleUpdateSettings::SetExperimentLabels(
133        install == SYSTEM_INSTALL, kTestExperimentLabel));
134
135    // Validate that something is written. Only worry about the label itself.
136    RegKey key;
137    HKEY root = install == SYSTEM_INSTALL ?
138        HKEY_LOCAL_MACHINE : HKEY_CURRENT_USER;
139    string16 state_key = install == SYSTEM_INSTALL ?
140        chrome->GetStateMediumKey() : chrome->GetStateKey();
141
142    EXPECT_EQ(ERROR_SUCCESS,
143              key.Open(root, state_key.c_str(), KEY_QUERY_VALUE));
144    EXPECT_EQ(ERROR_SUCCESS,
145        key.ReadValue(google_update::kExperimentLabels, &value));
146    EXPECT_EQ(kTestExperimentLabel, value);
147    EXPECT_TRUE(GoogleUpdateSettings::ReadExperimentLabels(
148        install == SYSTEM_INSTALL, &value));
149    EXPECT_EQ(kTestExperimentLabel, value);
150    key.Close();
151
152    // Now that the label is set, test the delete functionality. An empty label
153    // should result in deleting the value.
154    EXPECT_TRUE(GoogleUpdateSettings::SetExperimentLabels(
155        install == SYSTEM_INSTALL, string16()));
156    EXPECT_EQ(ERROR_SUCCESS,
157              key.Open(root, state_key.c_str(), KEY_QUERY_VALUE));
158    EXPECT_EQ(ERROR_FILE_NOT_FOUND,
159        key.ReadValue(google_update::kExperimentLabels, &value));
160    EXPECT_TRUE(GoogleUpdateSettings::ReadExperimentLabels(
161        install == SYSTEM_INSTALL, &value));
162    EXPECT_EQ(string16(), value);
163    key.Close();
164#else
165    EXPECT_FALSE(chrome->ShouldSetExperimentLabels());
166    EXPECT_FALSE(GoogleUpdateSettings::ReadExperimentLabels(
167        install == SYSTEM_INSTALL, &value));
168#endif  // GOOGLE_CHROME_BUILD
169  }
170
171  // Creates "ap" key with the value given as parameter. Also adds work
172  // items to work_item_list given so that they can be rolled back later.
173  bool CreateApKey(WorkItemList* work_item_list, const std::wstring& value) {
174    HKEY reg_root = HKEY_CURRENT_USER;
175    std::wstring reg_key = GetApKeyPath();
176    work_item_list->AddCreateRegKeyWorkItem(reg_root, reg_key);
177    work_item_list->AddSetRegValueWorkItem(reg_root, reg_key,
178        google_update::kRegApField, value.c_str(), true);
179    if (!work_item_list->Do()) {
180      work_item_list->Rollback();
181      return false;
182    }
183    return true;
184  }
185
186  // Returns the key path of "ap" key, e.g.:
187  // Google\Update\ClientState\<kTestProductGuid>
188  std::wstring GetApKeyPath() {
189    std::wstring reg_key(google_update::kRegPathClientState);
190    reg_key.append(L"\\");
191    reg_key.append(kTestProductGuid);
192    return reg_key;
193  }
194
195  // Utility method to read "ap" key value
196  std::wstring ReadApKeyValue() {
197    RegKey key;
198    std::wstring ap_key_value;
199    std::wstring reg_key = GetApKeyPath();
200    if (key.Open(HKEY_CURRENT_USER, reg_key.c_str(), KEY_ALL_ACCESS) ==
201        ERROR_SUCCESS) {
202      key.ReadValue(google_update::kRegApField, &ap_key_value);
203    }
204
205    return ap_key_value;
206  }
207
208  registry_util::RegistryOverrideManager registry_overrides_;
209};
210
211}  // namespace
212
213// Verify that we return success on no registration (which means stable),
214// whether per-system or per-user install.
215TEST_F(GoogleUpdateSettingsTest, CurrentChromeChannelAbsent) {
216  // Per-system first.
217  string16 channel;
218  EXPECT_TRUE(GoogleUpdateSettings::GetChromeChannelAndModifiers(true,
219                                                                 &channel));
220  EXPECT_STREQ(L"", channel.c_str());
221
222  // Then per-user.
223  EXPECT_TRUE(GoogleUpdateSettings::GetChromeChannelAndModifiers(false,
224                                                                 &channel));
225  EXPECT_STREQ(L"", channel.c_str());
226}
227
228// Test an empty Ap key for system and user.
229TEST_F(GoogleUpdateSettingsTest, CurrentChromeChannelEmptySystem) {
230  SetApField(SYSTEM_INSTALL, L"");
231  string16 channel;
232  EXPECT_TRUE(GoogleUpdateSettings::GetChromeChannelAndModifiers(true,
233                                                                 &channel));
234  EXPECT_STREQ(L"", channel.c_str());
235
236  // Per-user lookups still succeed and return empty string.
237  EXPECT_TRUE(GoogleUpdateSettings::GetChromeChannelAndModifiers(false,
238                                                                 &channel));
239  EXPECT_STREQ(L"", channel.c_str());
240}
241
242TEST_F(GoogleUpdateSettingsTest, CurrentChromeChannelEmptyUser) {
243  SetApField(USER_INSTALL, L"");
244  // Per-system lookups still succeed and return empty string.
245  string16 channel;
246  EXPECT_TRUE(GoogleUpdateSettings::GetChromeChannelAndModifiers(true,
247                                                                 &channel));
248  EXPECT_STREQ(L"", channel.c_str());
249
250  // Per-user lookup should succeed.
251  EXPECT_TRUE(GoogleUpdateSettings::GetChromeChannelAndModifiers(false,
252                                                                 &channel));
253  EXPECT_STREQ(L"", channel.c_str());
254}
255
256TEST_F(GoogleUpdateSettingsTest, CurrentChromeChannelVariousApValuesSystem) {
257  TestCurrentChromeChannelWithVariousApValues(SYSTEM_INSTALL);
258}
259
260TEST_F(GoogleUpdateSettingsTest, CurrentChromeChannelVariousApValuesUser) {
261  TestCurrentChromeChannelWithVariousApValues(USER_INSTALL);
262}
263
264// Run through all combinations of diff vs. full install, single vs. multi
265// install, success and failure results, and a fistful of initial "ap" values
266// checking that the expected final "ap" value is generated by
267// GoogleUpdateSettings::UpdateGoogleUpdateApKey.
268TEST_F(GoogleUpdateSettingsTest, UpdateGoogleUpdateApKey) {
269  const installer::ArchiveType archive_types[] = {
270    installer::UNKNOWN_ARCHIVE_TYPE,
271    installer::FULL_ARCHIVE_TYPE,
272    installer::INCREMENTAL_ARCHIVE_TYPE
273  };
274  const int results[] = {
275    installer::FIRST_INSTALL_SUCCESS,
276    installer::INSTALL_FAILED
277  };
278  const wchar_t* const plain[] = {
279    L"",
280    L"1.1",
281    L"1.1-dev"
282  };
283  const wchar_t* const full[] = {
284    L"-full",
285    L"1.1-full",
286    L"1.1-dev-full"
287  };
288  COMPILE_ASSERT(arraysize(full) == arraysize(plain), bad_full_array_size);
289  const wchar_t* const multifail[] = {
290    L"-multifail",
291    L"1.1-multifail",
292    L"1.1-dev-multifail"
293  };
294  COMPILE_ASSERT(arraysize(multifail) == arraysize(plain),
295                 bad_multifail_array_size);
296  const wchar_t* const multifail_full[] = {
297    L"-multifail-full",
298    L"1.1-multifail-full",
299    L"1.1-dev-multifail-full"
300  };
301  COMPILE_ASSERT(arraysize(multifail_full) == arraysize(plain),
302                 bad_multifail_full_array_size);
303  const wchar_t* const* input_arrays[] = {
304    plain,
305    full,
306    multifail,
307    multifail_full
308  };
309  ChannelInfo v;
310  for (int type_idx = 0; type_idx < arraysize(archive_types); ++type_idx) {
311    const installer::ArchiveType archive_type = archive_types[type_idx];
312    for (int result_idx = 0; result_idx < arraysize(results); ++result_idx) {
313      const int result = results[result_idx];
314      // The archive type will/must always be known on install success.
315      if (archive_type == installer::UNKNOWN_ARCHIVE_TYPE &&
316          result == installer::FIRST_INSTALL_SUCCESS) {
317        continue;
318      }
319      const wchar_t* const* outputs = NULL;
320      if (result == installer::FIRST_INSTALL_SUCCESS ||
321          archive_type == installer::FULL_ARCHIVE_TYPE) {
322        outputs = plain;
323      } else if (archive_type == installer::INCREMENTAL_ARCHIVE_TYPE) {
324        outputs = full;
325      }  // else if (archive_type == UNKNOWN) see below
326
327      for (int inputs_idx = 0; inputs_idx < arraysize(input_arrays);
328           ++inputs_idx) {
329        const wchar_t* const* inputs = input_arrays[inputs_idx];
330        if (archive_type == installer::UNKNOWN_ARCHIVE_TYPE) {
331          // "-full" is untouched if the archive type is unknown.
332          // "-multifail" is unconditionally removed.
333          if (inputs == full || inputs == multifail_full)
334            outputs = full;
335          else
336            outputs = plain;
337        }
338        for (int input_idx = 0; input_idx < arraysize(plain); ++input_idx) {
339          const wchar_t* input = inputs[input_idx];
340          const wchar_t* output = outputs[input_idx];
341
342          v.set_value(input);
343          if (output == v.value()) {
344            EXPECT_FALSE(GoogleUpdateSettings::UpdateGoogleUpdateApKey(
345                archive_type, result, &v))
346                << "archive_type: " << archive_type
347                << ", result: " << result
348                << ", input ap value: " << input;
349          } else {
350            EXPECT_TRUE(GoogleUpdateSettings::UpdateGoogleUpdateApKey(
351                archive_type, result, &v))
352                << "archive_type: " << archive_type
353                << ", result: " << result
354                << ", input ap value: " << input;
355          }
356          EXPECT_EQ(output, v.value())
357              << "archive_type: " << archive_type
358              << ", result: " << result
359              << ", input ap value: " << input;
360        }
361      }
362    }
363  }
364}
365
366TEST_F(GoogleUpdateSettingsTest, UpdateInstallStatusTest) {
367  scoped_ptr<WorkItemList> work_item_list(WorkItem::CreateWorkItemList());
368  // Test incremental install failure
369  ASSERT_TRUE(CreateApKey(work_item_list.get(), L""))
370      << "Failed to create ap key.";
371  GoogleUpdateSettings::UpdateInstallStatus(false,
372                                            installer::INCREMENTAL_ARCHIVE_TYPE,
373                                            installer::INSTALL_FAILED,
374                                            kTestProductGuid);
375  EXPECT_STREQ(ReadApKeyValue().c_str(), L"-full");
376  work_item_list->Rollback();
377
378  work_item_list.reset(WorkItem::CreateWorkItemList());
379  // Test incremental install success
380  ASSERT_TRUE(CreateApKey(work_item_list.get(), L""))
381      << "Failed to create ap key.";
382  GoogleUpdateSettings::UpdateInstallStatus(false,
383                                            installer::INCREMENTAL_ARCHIVE_TYPE,
384                                            installer::FIRST_INSTALL_SUCCESS,
385                                            kTestProductGuid);
386  EXPECT_STREQ(ReadApKeyValue().c_str(), L"");
387  work_item_list->Rollback();
388
389  work_item_list.reset(WorkItem::CreateWorkItemList());
390  // Test full install failure
391  ASSERT_TRUE(CreateApKey(work_item_list.get(), L"-full"))
392      << "Failed to create ap key.";
393  GoogleUpdateSettings::UpdateInstallStatus(false, installer::FULL_ARCHIVE_TYPE,
394                                            installer::INSTALL_FAILED,
395                                            kTestProductGuid);
396  EXPECT_STREQ(ReadApKeyValue().c_str(), L"");
397  work_item_list->Rollback();
398
399  work_item_list.reset(WorkItem::CreateWorkItemList());
400  // Test full install success
401  ASSERT_TRUE(CreateApKey(work_item_list.get(), L"-full"))
402      << "Failed to create ap key.";
403  GoogleUpdateSettings::UpdateInstallStatus(false, installer::FULL_ARCHIVE_TYPE,
404                                            installer::FIRST_INSTALL_SUCCESS,
405                                            kTestProductGuid);
406  EXPECT_STREQ(ReadApKeyValue().c_str(), L"");
407  work_item_list->Rollback();
408
409  work_item_list.reset(WorkItem::CreateWorkItemList());
410  // Test the case of when "ap" key doesnt exist at all
411  std::wstring ap_key_value = ReadApKeyValue();
412  std::wstring reg_key = GetApKeyPath();
413  HKEY reg_root = HKEY_CURRENT_USER;
414  bool ap_key_deleted = false;
415  RegKey key;
416  if (key.Open(HKEY_CURRENT_USER, reg_key.c_str(), KEY_ALL_ACCESS) !=
417      ERROR_SUCCESS) {
418    work_item_list->AddCreateRegKeyWorkItem(reg_root, reg_key);
419    ASSERT_TRUE(work_item_list->Do()) << "Failed to create ClientState key.";
420  } else if (key.DeleteValue(google_update::kRegApField) == ERROR_SUCCESS) {
421    ap_key_deleted = true;
422  }
423  // try differential installer
424  GoogleUpdateSettings::UpdateInstallStatus(false,
425                                            installer::INCREMENTAL_ARCHIVE_TYPE,
426                                            installer::INSTALL_FAILED,
427                                            kTestProductGuid);
428  EXPECT_STREQ(ReadApKeyValue().c_str(), L"-full");
429  // try full installer now
430  GoogleUpdateSettings::UpdateInstallStatus(false, installer::FULL_ARCHIVE_TYPE,
431                                            installer::INSTALL_FAILED,
432                                            kTestProductGuid);
433  EXPECT_STREQ(ReadApKeyValue().c_str(), L"");
434  // Now cleanup to leave the system in unchanged state.
435  // - Diff installer creates an ap key if it didnt exist, so delete this ap key
436  // - If we created any reg key path for ap, roll it back
437  // - Finally restore the original value of ap key.
438  key.Open(HKEY_CURRENT_USER, reg_key.c_str(), KEY_ALL_ACCESS);
439  key.DeleteValue(google_update::kRegApField);
440  work_item_list->Rollback();
441  if (ap_key_deleted) {
442    work_item_list.reset(WorkItem::CreateWorkItemList());
443    ASSERT_TRUE(CreateApKey(work_item_list.get(), ap_key_value))
444        << "Failed to restore ap key.";
445  }
446}
447
448TEST_F(GoogleUpdateSettingsTest, SetEULAConsent) {
449  using installer::FakeInstallationState;
450
451  const bool multi_install = true;
452  const bool system_level = true;
453  FakeInstallationState machine_state;
454
455  // Chrome is installed.
456  machine_state.AddChrome(system_level, multi_install,
457      new Version(chrome::kChromeVersion));
458
459  RegKey key;
460  DWORD value;
461  BrowserDistribution* binaries =
462      BrowserDistribution::GetSpecificDistribution(
463          BrowserDistribution::CHROME_BINARIES);
464  BrowserDistribution* chrome =
465      BrowserDistribution::GetSpecificDistribution(
466          BrowserDistribution::CHROME_BROWSER);
467
468  // eulaconsent is set on both the product and the binaries.
469  EXPECT_TRUE(GoogleUpdateSettings::SetEULAConsent(machine_state, chrome,
470                                                   true));
471  EXPECT_EQ(ERROR_SUCCESS,
472      key.Open(HKEY_LOCAL_MACHINE, binaries->GetStateMediumKey().c_str(),
473               KEY_QUERY_VALUE));
474  EXPECT_EQ(ERROR_SUCCESS,
475      key.ReadValueDW(google_update::kRegEULAAceptedField, &value));
476  EXPECT_EQ(1U, value);
477  EXPECT_EQ(ERROR_SUCCESS,
478      key.Open(HKEY_LOCAL_MACHINE, chrome->GetStateMediumKey().c_str(),
479               KEY_QUERY_VALUE));
480  EXPECT_EQ(ERROR_SUCCESS,
481      key.ReadValueDW(google_update::kRegEULAAceptedField, &value));
482  EXPECT_EQ(1U, value);
483}
484
485// Test that the appropriate default is returned if no update override is
486// present.
487TEST_F(GoogleUpdateSettingsTest, GetAppUpdatePolicyNoOverride) {
488  // There are no policies at all.
489  EXPECT_EQ(ERROR_FILE_NOT_FOUND,
490            RegKey().Open(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
491                          KEY_QUERY_VALUE));
492  bool is_overridden = true;
493  EXPECT_EQ(kDefaultUpdatePolicy,
494            GoogleUpdateSettings::GetAppUpdatePolicy(kTestProductGuid,
495                                                     &is_overridden));
496  EXPECT_FALSE(is_overridden);
497
498  // The policy key exists, but there are no values of interest present.
499  EXPECT_EQ(ERROR_SUCCESS,
500            RegKey().Create(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
501                            KEY_SET_VALUE));
502  EXPECT_EQ(ERROR_SUCCESS,
503            RegKey().Open(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
504                          KEY_QUERY_VALUE));
505  is_overridden = true;
506  EXPECT_EQ(kDefaultUpdatePolicy,
507            GoogleUpdateSettings::GetAppUpdatePolicy(kTestProductGuid,
508                                                     &is_overridden));
509  EXPECT_FALSE(is_overridden);
510}
511
512#if defined(GOOGLE_CHROME_BUILD)
513
514// Test that the default override is returned if no app-specific override is
515// present.
516TEST_F(GoogleUpdateSettingsTest, GetAppUpdatePolicyDefaultOverride) {
517  EXPECT_EQ(ERROR_SUCCESS,
518            RegKey(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
519                   KEY_SET_VALUE).WriteValue(kGoogleUpdateUpdateDefault,
520                                             static_cast<DWORD>(0)));
521  bool is_overridden = true;
522  EXPECT_EQ(GoogleUpdateSettings::UPDATES_DISABLED,
523            GoogleUpdateSettings::GetAppUpdatePolicy(kTestProductGuid,
524                                                     &is_overridden));
525  EXPECT_FALSE(is_overridden);
526
527  EXPECT_EQ(ERROR_SUCCESS,
528            RegKey(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
529                   KEY_SET_VALUE).WriteValue(kGoogleUpdateUpdateDefault,
530                                             static_cast<DWORD>(1)));
531  is_overridden = true;
532  EXPECT_EQ(GoogleUpdateSettings::AUTOMATIC_UPDATES,
533            GoogleUpdateSettings::GetAppUpdatePolicy(kTestProductGuid,
534                                                     &is_overridden));
535  EXPECT_FALSE(is_overridden);
536
537  EXPECT_EQ(ERROR_SUCCESS,
538            RegKey(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
539                   KEY_SET_VALUE).WriteValue(kGoogleUpdateUpdateDefault,
540                                             static_cast<DWORD>(2)));
541  is_overridden = true;
542  EXPECT_EQ(GoogleUpdateSettings::MANUAL_UPDATES_ONLY,
543            GoogleUpdateSettings::GetAppUpdatePolicy(kTestProductGuid,
544                                                     &is_overridden));
545  EXPECT_FALSE(is_overridden);
546
547  EXPECT_EQ(ERROR_SUCCESS,
548            RegKey(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
549                   KEY_SET_VALUE).WriteValue(kGoogleUpdateUpdateDefault,
550                                             static_cast<DWORD>(3)));
551  is_overridden = true;
552  EXPECT_EQ(GoogleUpdateSettings::AUTO_UPDATES_ONLY,
553            GoogleUpdateSettings::GetAppUpdatePolicy(kTestProductGuid,
554                                                     &is_overridden));
555  EXPECT_FALSE(is_overridden);
556
557  // The default policy should be in force for bogus values.
558  EXPECT_EQ(ERROR_SUCCESS,
559            RegKey(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
560                   KEY_SET_VALUE).WriteValue(kGoogleUpdateUpdateDefault,
561                                             static_cast<DWORD>(4)));
562  is_overridden = true;
563  EXPECT_EQ(kDefaultUpdatePolicy,
564            GoogleUpdateSettings::GetAppUpdatePolicy(kTestProductGuid,
565                                                     &is_overridden));
566  EXPECT_FALSE(is_overridden);
567}
568
569// Test that an app-specific override is used if present.
570TEST_F(GoogleUpdateSettingsTest, GetAppUpdatePolicyAppOverride) {
571  std::wstring app_policy_value(kGoogleUpdateUpdatePrefix);
572  app_policy_value.append(kTestProductGuid);
573
574  EXPECT_EQ(ERROR_SUCCESS,
575            RegKey(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
576                   KEY_SET_VALUE).WriteValue(kGoogleUpdateUpdateDefault,
577                                             static_cast<DWORD>(1)));
578  EXPECT_EQ(ERROR_SUCCESS,
579            RegKey(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
580                   KEY_SET_VALUE).WriteValue(app_policy_value.c_str(),
581                                             static_cast<DWORD>(0)));
582  bool is_overridden = false;
583  EXPECT_EQ(GoogleUpdateSettings::UPDATES_DISABLED,
584            GoogleUpdateSettings::GetAppUpdatePolicy(kTestProductGuid,
585                                                     &is_overridden));
586  EXPECT_TRUE(is_overridden);
587
588  EXPECT_EQ(ERROR_SUCCESS,
589            RegKey(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
590                   KEY_SET_VALUE).WriteValue(kGoogleUpdateUpdateDefault,
591                                             static_cast<DWORD>(0)));
592  EXPECT_EQ(ERROR_SUCCESS,
593            RegKey(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
594                   KEY_SET_VALUE).WriteValue(app_policy_value.c_str(),
595                                             static_cast<DWORD>(1)));
596  is_overridden = false;
597  EXPECT_EQ(GoogleUpdateSettings::AUTOMATIC_UPDATES,
598            GoogleUpdateSettings::GetAppUpdatePolicy(kTestProductGuid,
599                                                     &is_overridden));
600  EXPECT_TRUE(is_overridden);
601
602  EXPECT_EQ(ERROR_SUCCESS,
603            RegKey(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
604                   KEY_SET_VALUE).WriteValue(app_policy_value.c_str(),
605                                             static_cast<DWORD>(2)));
606  is_overridden = false;
607  EXPECT_EQ(GoogleUpdateSettings::MANUAL_UPDATES_ONLY,
608            GoogleUpdateSettings::GetAppUpdatePolicy(kTestProductGuid,
609                                                     &is_overridden));
610  EXPECT_TRUE(is_overridden);
611
612  EXPECT_EQ(ERROR_SUCCESS,
613            RegKey(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
614                   KEY_SET_VALUE).WriteValue(app_policy_value.c_str(),
615                                             static_cast<DWORD>(3)));
616  is_overridden = false;
617  EXPECT_EQ(GoogleUpdateSettings::AUTO_UPDATES_ONLY,
618            GoogleUpdateSettings::GetAppUpdatePolicy(kTestProductGuid,
619                                                     &is_overridden));
620  EXPECT_TRUE(is_overridden);
621
622  // The default policy should be in force for bogus values.
623  EXPECT_EQ(ERROR_SUCCESS,
624            RegKey(HKEY_LOCAL_MACHINE, kGoogleUpdatePoliciesKey,
625                   KEY_SET_VALUE).WriteValue(app_policy_value.c_str(),
626                                             static_cast<DWORD>(4)));
627  is_overridden = true;
628  EXPECT_EQ(GoogleUpdateSettings::UPDATES_DISABLED,
629            GoogleUpdateSettings::GetAppUpdatePolicy(kTestProductGuid,
630                                                     &is_overridden));
631  EXPECT_FALSE(is_overridden);
632}
633
634TEST_F(GoogleUpdateSettingsTest, ExperimentsLabelHelperSystem) {
635  TestExperimentsLabelHelper(SYSTEM_INSTALL);
636}
637
638TEST_F(GoogleUpdateSettingsTest, ExperimentsLabelHelperUser) {
639  TestExperimentsLabelHelper(USER_INSTALL);
640}
641
642#endif  // defined(GOOGLE_CHROME_BUILD)
643
644// Test GoogleUpdateSettings::GetUninstallCommandLine at system- or user-level,
645// according to the param.
646class GetUninstallCommandLine : public GoogleUpdateSettingsTest,
647                                public testing::WithParamInterface<bool> {
648 protected:
649  static const wchar_t kDummyCommand[];
650
651  virtual void SetUp() OVERRIDE {
652    GoogleUpdateSettingsTest::SetUp();
653    system_install_ = GetParam();
654    root_key_ = system_install_ ? HKEY_LOCAL_MACHINE : HKEY_CURRENT_USER;
655  }
656
657  HKEY root_key_;
658  bool system_install_;
659};
660
661const wchar_t GetUninstallCommandLine::kDummyCommand[] =
662    L"\"goopdate.exe\" /spam";
663
664// Tests that GetUninstallCommandLine returns an empty string if there's no
665// Software\Google\Update key.
666TEST_P(GetUninstallCommandLine, TestNoKey) {
667  EXPECT_EQ(string16(),
668            GoogleUpdateSettings::GetUninstallCommandLine(system_install_));
669}
670
671// Tests that GetUninstallCommandLine returns an empty string if there's no
672// UninstallCmdLine value in the Software\Google\Update key.
673TEST_P(GetUninstallCommandLine, TestNoValue) {
674  RegKey(root_key_, google_update::kRegPathGoogleUpdate, KEY_SET_VALUE);
675  EXPECT_EQ(string16(),
676            GoogleUpdateSettings::GetUninstallCommandLine(system_install_));
677}
678
679// Tests that GetUninstallCommandLine returns an empty string if there's an
680// empty UninstallCmdLine value in the Software\Google\Update key.
681TEST_P(GetUninstallCommandLine, TestEmptyValue) {
682  RegKey(root_key_, google_update::kRegPathGoogleUpdate, KEY_SET_VALUE)
683    .WriteValue(google_update::kRegUninstallCmdLine, L"");
684  EXPECT_EQ(string16(),
685            GoogleUpdateSettings::GetUninstallCommandLine(system_install_));
686}
687
688// Tests that GetUninstallCommandLine returns the correct string if there's an
689// UninstallCmdLine value in the Software\Google\Update key.
690TEST_P(GetUninstallCommandLine, TestRealValue) {
691  RegKey(root_key_, google_update::kRegPathGoogleUpdate, KEY_SET_VALUE)
692      .WriteValue(google_update::kRegUninstallCmdLine, kDummyCommand);
693  EXPECT_EQ(string16(kDummyCommand),
694            GoogleUpdateSettings::GetUninstallCommandLine(system_install_));
695  // Make sure that there's no value in the other level (user or system).
696  EXPECT_EQ(string16(),
697            GoogleUpdateSettings::GetUninstallCommandLine(!system_install_));
698}
699
700INSTANTIATE_TEST_CASE_P(GetUninstallCommandLineAtLevel, GetUninstallCommandLine,
701                        testing::Bool());
702
703// Test GoogleUpdateSettings::GetGoogleUpdateVersion at system- or user-level,
704// according to the param.
705class GetGoogleUpdateVersion : public GoogleUpdateSettingsTest,
706                               public testing::WithParamInterface<bool> {
707 protected:
708  static const wchar_t kDummyVersion[];
709
710  virtual void SetUp() OVERRIDE {
711    GoogleUpdateSettingsTest::SetUp();
712    system_install_ = GetParam();
713    root_key_ = system_install_ ? HKEY_LOCAL_MACHINE : HKEY_CURRENT_USER;
714  }
715
716  HKEY root_key_;
717  bool system_install_;
718};
719
720const wchar_t GetGoogleUpdateVersion::kDummyVersion[] = L"1.2.3.4";
721
722// Tests that GetGoogleUpdateVersion returns an empty string if there's no
723// Software\Google\Update key.
724TEST_P(GetGoogleUpdateVersion, TestNoKey) {
725  EXPECT_FALSE(
726      GoogleUpdateSettings::GetGoogleUpdateVersion(system_install_).IsValid());
727}
728
729// Tests that GetGoogleUpdateVersion returns an empty string if there's no
730// version value in the Software\Google\Update key.
731TEST_P(GetGoogleUpdateVersion, TestNoValue) {
732  RegKey(root_key_, google_update::kRegPathGoogleUpdate, KEY_SET_VALUE);
733  EXPECT_FALSE(
734      GoogleUpdateSettings::GetGoogleUpdateVersion(system_install_).IsValid());
735}
736
737// Tests that GetGoogleUpdateVersion returns an empty string if there's an
738// empty version value in the Software\Google\Update key.
739TEST_P(GetGoogleUpdateVersion, TestEmptyValue) {
740  RegKey(root_key_, google_update::kRegPathGoogleUpdate, KEY_SET_VALUE)
741      .WriteValue(google_update::kRegGoogleUpdateVersion, L"");
742  EXPECT_FALSE(
743      GoogleUpdateSettings::GetGoogleUpdateVersion(system_install_).IsValid());
744}
745
746// Tests that GetGoogleUpdateVersion returns the correct string if there's a
747// version value in the Software\Google\Update key.
748TEST_P(GetGoogleUpdateVersion, TestRealValue) {
749  RegKey(root_key_, google_update::kRegPathGoogleUpdate, KEY_SET_VALUE)
750      .WriteValue(google_update::kRegGoogleUpdateVersion, kDummyVersion);
751  Version expected(UTF16ToUTF8(kDummyVersion));
752  EXPECT_TRUE(expected.Equals(
753      GoogleUpdateSettings::GetGoogleUpdateVersion(system_install_)));
754  // Make sure that there's no value in the other level (user or system).
755  EXPECT_FALSE(
756      GoogleUpdateSettings::GetGoogleUpdateVersion(!system_install_)
757          .IsValid());
758}
759
760INSTANTIATE_TEST_CASE_P(GetGoogleUpdateVersionAtLevel, GetGoogleUpdateVersion,
761                        testing::Bool());
762
763// Test values for use by the CollectStatsConsent test fixture.
764class StatsState {
765 public:
766  enum InstallType {
767    SINGLE_INSTALL,
768    MULTI_INSTALL,
769  };
770  enum StateSetting {
771    NO_SETTING,
772    FALSE_SETTING,
773    TRUE_SETTING,
774  };
775  struct UserLevelState {};
776  struct SystemLevelState {};
777  static const UserLevelState kUserLevel;
778  static const SystemLevelState kSystemLevel;
779
780  StatsState(const UserLevelState&,
781             InstallType install_type,
782             StateSetting state_value)
783      : system_level_(false),
784        multi_install_(install_type == MULTI_INSTALL),
785        state_value_(state_value),
786        state_medium_value_(NO_SETTING) {
787  }
788  StatsState(const SystemLevelState&,
789             InstallType install_type,
790             StateSetting state_value,
791             StateSetting state_medium_value)
792      : system_level_(true),
793        multi_install_(install_type == MULTI_INSTALL),
794        state_value_(state_value),
795        state_medium_value_(state_medium_value) {
796  }
797  bool system_level() const { return system_level_; }
798  bool multi_install() const { return multi_install_; }
799  HKEY root_key() const {
800    return system_level_ ? HKEY_LOCAL_MACHINE : HKEY_CURRENT_USER;
801  }
802  StateSetting state_value() const { return state_value_; }
803  StateSetting state_medium_value() const {
804    return state_medium_value_;
805  }
806  bool is_consent_granted() const {
807    return (system_level_ && state_medium_value_ != NO_SETTING) ?
808        (state_medium_value_ == TRUE_SETTING) :
809        (state_value_ == TRUE_SETTING);
810  }
811 private:
812  bool system_level_;
813  bool multi_install_;
814  StateSetting state_value_;
815  StateSetting state_medium_value_;
816};
817
818const StatsState::UserLevelState StatsState::kUserLevel;
819const StatsState::SystemLevelState StatsState::kSystemLevel;
820
821// A value parameterized test for testing the stats collection consent setting.
822class CollectStatsConsent : public ::testing::TestWithParam<StatsState> {
823 public:
824  static void SetUpTestCase();
825  static void TearDownTestCase();
826 protected:
827  virtual void SetUp() OVERRIDE;
828  static void MakeChromeMultiInstall(HKEY root_key);
829  static void ApplySetting(StatsState::StateSetting setting,
830                           HKEY root_key,
831                           const std::wstring& reg_key);
832
833  static std::wstring* chrome_version_key_;
834  static std::wstring* chrome_state_key_;
835  static std::wstring* chrome_state_medium_key_;
836  static std::wstring* binaries_state_key_;
837  static std::wstring* binaries_state_medium_key_;
838  registry_util::RegistryOverrideManager override_manager_;
839};
840
841std::wstring* CollectStatsConsent::chrome_version_key_;
842std::wstring* CollectStatsConsent::chrome_state_key_;
843std::wstring* CollectStatsConsent::chrome_state_medium_key_;
844std::wstring* CollectStatsConsent::binaries_state_key_;
845std::wstring* CollectStatsConsent::binaries_state_medium_key_;
846
847void CollectStatsConsent::SetUpTestCase() {
848  BrowserDistribution* dist =
849      BrowserDistribution::GetSpecificDistribution(
850          BrowserDistribution::CHROME_BROWSER);
851  chrome_version_key_ = new std::wstring(dist->GetVersionKey());
852  chrome_state_key_ = new std::wstring(dist->GetStateKey());
853  chrome_state_medium_key_ = new std::wstring(dist->GetStateMediumKey());
854
855  dist = BrowserDistribution::GetSpecificDistribution(
856      BrowserDistribution::CHROME_BINARIES);
857  binaries_state_key_ = new std::wstring(dist->GetStateKey());
858  binaries_state_medium_key_ = new std::wstring(dist->GetStateMediumKey());
859}
860
861void CollectStatsConsent::TearDownTestCase() {
862  delete chrome_version_key_;
863  delete chrome_state_key_;
864  delete chrome_state_medium_key_;
865  delete binaries_state_key_;
866  delete binaries_state_medium_key_;
867}
868
869// Install the registry override and apply the settings to the registry.
870void CollectStatsConsent::SetUp() {
871  const StatsState& stats_state = GetParam();
872  const HKEY root_key = stats_state.root_key();
873  std::wstring reg_temp_name(stats_state.system_level() ? L"HKLM_" : L"HKCU_");
874  reg_temp_name += L"CollectStatsConsent";
875  override_manager_.OverrideRegistry(root_key, reg_temp_name);
876
877  if (stats_state.multi_install()) {
878    MakeChromeMultiInstall(root_key);
879    ApplySetting(stats_state.state_value(), root_key, *binaries_state_key_);
880    ApplySetting(stats_state.state_medium_value(), root_key,
881                 *binaries_state_medium_key_);
882  } else {
883    ApplySetting(stats_state.state_value(), root_key, *chrome_state_key_);
884    ApplySetting(stats_state.state_medium_value(), root_key,
885                 *chrome_state_medium_key_);
886  }
887}
888
889// Write values into the registry so that Chrome is considered to be installed
890// as multi-install.
891void CollectStatsConsent::MakeChromeMultiInstall(HKEY root_key) {
892  ASSERT_EQ(
893      ERROR_SUCCESS,
894      RegKey(root_key, chrome_version_key_->c_str(),
895             KEY_SET_VALUE).WriteValue(google_update::kRegVersionField,
896                                       L"1.2.3.4"));
897  ASSERT_EQ(
898      ERROR_SUCCESS,
899      RegKey(root_key, chrome_state_key_->c_str(),
900             KEY_SET_VALUE).WriteValue(installer::kUninstallArgumentsField,
901                                       L"--multi-install"));
902}
903
904// Write the correct value to represent |setting| in the registry.
905void CollectStatsConsent::ApplySetting(StatsState::StateSetting setting,
906                                       HKEY root_key,
907                                       const std::wstring& reg_key) {
908  if (setting != StatsState::NO_SETTING) {
909    DWORD value = setting != StatsState::FALSE_SETTING ? 1 : 0;
910    ASSERT_EQ(
911        ERROR_SUCCESS,
912        RegKey(root_key, reg_key.c_str(),
913               KEY_SET_VALUE).WriteValue(google_update::kRegUsageStatsField,
914                                         value));
915  }
916}
917
918// Test that stats consent can be read.
919TEST_P(CollectStatsConsent, GetCollectStatsConsentAtLevel) {
920  if (GetParam().is_consent_granted()) {
921    EXPECT_TRUE(GoogleUpdateSettings::GetCollectStatsConsentAtLevel(
922                    GetParam().system_level()));
923  } else {
924    EXPECT_FALSE(GoogleUpdateSettings::GetCollectStatsConsentAtLevel(
925                     GetParam().system_level()));
926  }
927}
928
929// Test that stats consent can be flipped to the opposite setting, that the new
930// setting takes affect, and that the correct registry location is modified.
931TEST_P(CollectStatsConsent, SetCollectStatsConsentAtLevel) {
932  EXPECT_TRUE(GoogleUpdateSettings::SetCollectStatsConsentAtLevel(
933                  GetParam().system_level(),
934                  !GetParam().is_consent_granted()));
935  const std::wstring* const reg_keys[] = {
936    chrome_state_key_,
937    chrome_state_medium_key_,
938    binaries_state_key_,
939    binaries_state_medium_key_,
940  };
941  int key_index = ((GetParam().system_level() ? 1 : 0) +
942                   (GetParam().multi_install() ? 2 : 0));
943  const std::wstring& reg_key = *reg_keys[key_index];
944  DWORD value = 0;
945  EXPECT_EQ(
946      ERROR_SUCCESS,
947      RegKey(GetParam().root_key(), reg_key.c_str(),
948             KEY_QUERY_VALUE).ReadValueDW(google_update::kRegUsageStatsField,
949                                          &value));
950  if (GetParam().is_consent_granted()) {
951    EXPECT_FALSE(GoogleUpdateSettings::GetCollectStatsConsentAtLevel(
952                     GetParam().system_level()));
953    EXPECT_EQ(0UL, value);
954  } else {
955    EXPECT_TRUE(GoogleUpdateSettings::GetCollectStatsConsentAtLevel(
956                    GetParam().system_level()));
957    EXPECT_EQ(1UL, value);
958  }
959}
960
961INSTANTIATE_TEST_CASE_P(
962    UserLevelSingleInstall,
963    CollectStatsConsent,
964    ::testing::Values(
965        StatsState(StatsState::kUserLevel, StatsState::SINGLE_INSTALL,
966                   StatsState::NO_SETTING),
967        StatsState(StatsState::kUserLevel, StatsState::SINGLE_INSTALL,
968                   StatsState::FALSE_SETTING),
969        StatsState(StatsState::kUserLevel, StatsState::SINGLE_INSTALL,
970                   StatsState::TRUE_SETTING)));
971INSTANTIATE_TEST_CASE_P(
972    UserLevelMultiInstall,
973    CollectStatsConsent,
974    ::testing::Values(
975        StatsState(StatsState::kUserLevel, StatsState::MULTI_INSTALL,
976                   StatsState::NO_SETTING),
977        StatsState(StatsState::kUserLevel, StatsState::MULTI_INSTALL,
978                   StatsState::FALSE_SETTING),
979        StatsState(StatsState::kUserLevel, StatsState::MULTI_INSTALL,
980                   StatsState::TRUE_SETTING)));
981INSTANTIATE_TEST_CASE_P(
982    SystemLevelSingleInstall,
983    CollectStatsConsent,
984    ::testing::Values(
985        StatsState(StatsState::kSystemLevel, StatsState::SINGLE_INSTALL,
986                   StatsState::NO_SETTING, StatsState::NO_SETTING),
987        StatsState(StatsState::kSystemLevel, StatsState::SINGLE_INSTALL,
988                   StatsState::NO_SETTING, StatsState::FALSE_SETTING),
989        StatsState(StatsState::kSystemLevel, StatsState::SINGLE_INSTALL,
990                   StatsState::NO_SETTING, StatsState::TRUE_SETTING),
991        StatsState(StatsState::kSystemLevel, StatsState::SINGLE_INSTALL,
992                   StatsState::FALSE_SETTING, StatsState::NO_SETTING),
993        StatsState(StatsState::kSystemLevel, StatsState::SINGLE_INSTALL,
994                   StatsState::FALSE_SETTING, StatsState::FALSE_SETTING),
995        StatsState(StatsState::kSystemLevel, StatsState::SINGLE_INSTALL,
996                   StatsState::FALSE_SETTING, StatsState::TRUE_SETTING),
997        StatsState(StatsState::kSystemLevel, StatsState::SINGLE_INSTALL,
998                   StatsState::TRUE_SETTING, StatsState::NO_SETTING),
999        StatsState(StatsState::kSystemLevel, StatsState::SINGLE_INSTALL,
1000                   StatsState::TRUE_SETTING, StatsState::FALSE_SETTING),
1001        StatsState(StatsState::kSystemLevel, StatsState::SINGLE_INSTALL,
1002                   StatsState::TRUE_SETTING, StatsState::TRUE_SETTING)));
1003INSTANTIATE_TEST_CASE_P(
1004    SystemLevelMultiInstall,
1005    CollectStatsConsent,
1006    ::testing::Values(
1007        StatsState(StatsState::kSystemLevel, StatsState::MULTI_INSTALL,
1008                   StatsState::NO_SETTING, StatsState::NO_SETTING),
1009        StatsState(StatsState::kSystemLevel, StatsState::MULTI_INSTALL,
1010                   StatsState::NO_SETTING, StatsState::FALSE_SETTING),
1011        StatsState(StatsState::kSystemLevel, StatsState::MULTI_INSTALL,
1012                   StatsState::NO_SETTING, StatsState::TRUE_SETTING),
1013        StatsState(StatsState::kSystemLevel, StatsState::MULTI_INSTALL,
1014                   StatsState::FALSE_SETTING, StatsState::NO_SETTING),
1015        StatsState(StatsState::kSystemLevel, StatsState::MULTI_INSTALL,
1016                   StatsState::FALSE_SETTING, StatsState::FALSE_SETTING),
1017        StatsState(StatsState::kSystemLevel, StatsState::MULTI_INSTALL,
1018                   StatsState::FALSE_SETTING, StatsState::TRUE_SETTING),
1019        StatsState(StatsState::kSystemLevel, StatsState::MULTI_INSTALL,
1020                   StatsState::TRUE_SETTING, StatsState::NO_SETTING),
1021        StatsState(StatsState::kSystemLevel, StatsState::MULTI_INSTALL,
1022                   StatsState::TRUE_SETTING, StatsState::FALSE_SETTING),
1023        StatsState(StatsState::kSystemLevel, StatsState::MULTI_INSTALL,
1024                   StatsState::TRUE_SETTING, StatsState::TRUE_SETTING)));
1025