Home | History | Annotate | Download | only in win
      1 // Copyright (c) 2011 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 "base/win/registry.h"
      6 
      7 #include <cstring>
      8 #include <vector>
      9 
     10 #include "base/compiler_specific.h"
     11 #include "base/stl_util.h"
     12 #include "testing/gtest/include/gtest/gtest.h"
     13 
     14 namespace base {
     15 namespace win {
     16 
     17 namespace {
     18 
     19 const wchar_t kRootKey[] = L"Base_Registry_Unittest";
     20 
     21 class RegistryTest : public testing::Test {
     22  public:
     23   RegistryTest() {}
     24 
     25  protected:
     26   virtual void SetUp() OVERRIDE {
     27     // Create a temporary key.
     28     RegKey key(HKEY_CURRENT_USER, L"", KEY_ALL_ACCESS);
     29     key.DeleteKey(kRootKey);
     30     ASSERT_NE(ERROR_SUCCESS, key.Open(HKEY_CURRENT_USER, kRootKey, KEY_READ));
     31     ASSERT_EQ(ERROR_SUCCESS, key.Create(HKEY_CURRENT_USER, kRootKey, KEY_READ));
     32   }
     33 
     34   virtual void TearDown() OVERRIDE {
     35     // Clean up the temporary key.
     36     RegKey key(HKEY_CURRENT_USER, L"", KEY_SET_VALUE);
     37     ASSERT_EQ(ERROR_SUCCESS, key.DeleteKey(kRootKey));
     38   }
     39 
     40  private:
     41   DISALLOW_COPY_AND_ASSIGN(RegistryTest);
     42 };
     43 
     44 TEST_F(RegistryTest, ValueTest) {
     45   RegKey key;
     46 
     47   std::wstring foo_key(kRootKey);
     48   foo_key += L"\\Foo";
     49   ASSERT_EQ(ERROR_SUCCESS, key.Create(HKEY_CURRENT_USER, foo_key.c_str(),
     50                                       KEY_READ));
     51 
     52   {
     53     ASSERT_EQ(ERROR_SUCCESS, key.Open(HKEY_CURRENT_USER, foo_key.c_str(),
     54                                       KEY_READ | KEY_SET_VALUE));
     55     ASSERT_TRUE(key.Valid());
     56 
     57     const wchar_t kStringValueName[] = L"StringValue";
     58     const wchar_t kDWORDValueName[] = L"DWORDValue";
     59     const wchar_t kInt64ValueName[] = L"Int64Value";
     60     const wchar_t kStringData[] = L"string data";
     61     const DWORD kDWORDData = 0xdeadbabe;
     62     const int64 kInt64Data = 0xdeadbabedeadbabeLL;
     63 
     64     // Test value creation
     65     ASSERT_EQ(ERROR_SUCCESS, key.WriteValue(kStringValueName, kStringData));
     66     ASSERT_EQ(ERROR_SUCCESS, key.WriteValue(kDWORDValueName, kDWORDData));
     67     ASSERT_EQ(ERROR_SUCCESS, key.WriteValue(kInt64ValueName, &kInt64Data,
     68                                             sizeof(kInt64Data), REG_QWORD));
     69     EXPECT_EQ(3U, key.GetValueCount());
     70     EXPECT_TRUE(key.HasValue(kStringValueName));
     71     EXPECT_TRUE(key.HasValue(kDWORDValueName));
     72     EXPECT_TRUE(key.HasValue(kInt64ValueName));
     73 
     74     // Test Read
     75     std::wstring string_value;
     76     DWORD dword_value = 0;
     77     int64 int64_value = 0;
     78     ASSERT_EQ(ERROR_SUCCESS, key.ReadValue(kStringValueName, &string_value));
     79     ASSERT_EQ(ERROR_SUCCESS, key.ReadValueDW(kDWORDValueName, &dword_value));
     80     ASSERT_EQ(ERROR_SUCCESS, key.ReadInt64(kInt64ValueName, &int64_value));
     81     EXPECT_STREQ(kStringData, string_value.c_str());
     82     EXPECT_EQ(kDWORDData, dword_value);
     83     EXPECT_EQ(kInt64Data, int64_value);
     84 
     85     // Make sure out args are not touched if ReadValue fails
     86     const wchar_t* kNonExistent = L"NonExistent";
     87     ASSERT_NE(ERROR_SUCCESS, key.ReadValue(kNonExistent, &string_value));
     88     ASSERT_NE(ERROR_SUCCESS, key.ReadValueDW(kNonExistent, &dword_value));
     89     ASSERT_NE(ERROR_SUCCESS, key.ReadInt64(kNonExistent, &int64_value));
     90     EXPECT_STREQ(kStringData, string_value.c_str());
     91     EXPECT_EQ(kDWORDData, dword_value);
     92     EXPECT_EQ(kInt64Data, int64_value);
     93 
     94     // Test delete
     95     ASSERT_EQ(ERROR_SUCCESS, key.DeleteValue(kStringValueName));
     96     ASSERT_EQ(ERROR_SUCCESS, key.DeleteValue(kDWORDValueName));
     97     ASSERT_EQ(ERROR_SUCCESS, key.DeleteValue(kInt64ValueName));
     98     EXPECT_EQ(0U, key.GetValueCount());
     99     EXPECT_FALSE(key.HasValue(kStringValueName));
    100     EXPECT_FALSE(key.HasValue(kDWORDValueName));
    101     EXPECT_FALSE(key.HasValue(kInt64ValueName));
    102   }
    103 }
    104 
    105 TEST_F(RegistryTest, BigValueIteratorTest) {
    106   RegKey key;
    107   std::wstring foo_key(kRootKey);
    108   foo_key += L"\\Foo";
    109   ASSERT_EQ(ERROR_SUCCESS, key.Create(HKEY_CURRENT_USER, foo_key.c_str(),
    110                                       KEY_READ));
    111   ASSERT_EQ(ERROR_SUCCESS, key.Open(HKEY_CURRENT_USER, foo_key.c_str(),
    112                                     KEY_READ | KEY_SET_VALUE));
    113   ASSERT_TRUE(key.Valid());
    114 
    115   // Create a test value that is larger than MAX_PATH.
    116   std::wstring data(MAX_PATH * 2, L'a');
    117 
    118   ASSERT_EQ(ERROR_SUCCESS, key.WriteValue(data.c_str(), data.c_str()));
    119 
    120   RegistryValueIterator iterator(HKEY_CURRENT_USER, foo_key.c_str());
    121   ASSERT_TRUE(iterator.Valid());
    122   EXPECT_STREQ(data.c_str(), iterator.Name());
    123   EXPECT_STREQ(data.c_str(), iterator.Value());
    124   // ValueSize() is in bytes, including NUL.
    125   EXPECT_EQ((MAX_PATH * 2 + 1) * sizeof(wchar_t), iterator.ValueSize());
    126   ++iterator;
    127   EXPECT_FALSE(iterator.Valid());
    128 }
    129 
    130 TEST_F(RegistryTest, TruncatedCharTest) {
    131   RegKey key;
    132   std::wstring foo_key(kRootKey);
    133   foo_key += L"\\Foo";
    134   ASSERT_EQ(ERROR_SUCCESS, key.Create(HKEY_CURRENT_USER, foo_key.c_str(),
    135                                       KEY_READ));
    136   ASSERT_EQ(ERROR_SUCCESS, key.Open(HKEY_CURRENT_USER, foo_key.c_str(),
    137                                     KEY_READ | KEY_SET_VALUE));
    138   ASSERT_TRUE(key.Valid());
    139 
    140   const wchar_t kName[] = L"name";
    141   // kData size is not a multiple of sizeof(wchar_t).
    142   const uint8 kData[] = { 1, 2, 3, 4, 5 };
    143   EXPECT_EQ(5, arraysize(kData));
    144   ASSERT_EQ(ERROR_SUCCESS, key.WriteValue(kName, kData,
    145                                           arraysize(kData), REG_BINARY));
    146 
    147   RegistryValueIterator iterator(HKEY_CURRENT_USER, foo_key.c_str());
    148   ASSERT_TRUE(iterator.Valid());
    149   EXPECT_STREQ(kName, iterator.Name());
    150   // ValueSize() is in bytes.
    151   ASSERT_EQ(arraysize(kData), iterator.ValueSize());
    152   // Value() is NUL terminated.
    153   int end = (iterator.ValueSize() + sizeof(wchar_t) - 1) / sizeof(wchar_t);
    154   EXPECT_NE(L'\0', iterator.Value()[end-1]);
    155   EXPECT_EQ(L'\0', iterator.Value()[end]);
    156   EXPECT_EQ(0, std::memcmp(kData, iterator.Value(), arraysize(kData)));
    157   ++iterator;
    158   EXPECT_FALSE(iterator.Valid());
    159 }
    160 
    161 }  // namespace
    162 
    163 }  // namespace win
    164 }  // namespace base
    165