diff options
author | dcheng@chromium.org <dcheng@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-04-17 18:51:17 +0000 |
---|---|---|
committer | dcheng@chromium.org <dcheng@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-04-17 18:51:17 +0000 |
commit | 4d6f3301690cf9d7af1862533ccdcccdc6c780dd (patch) | |
tree | 7b97665254e9292eb1b3efaa4f650ee2fea32475 /chrome/installer/util/registry_key_backup.cc | |
parent | 8fb8eeb9607ccd4c3d447563777beb84e24cbd0a (diff) | |
download | chromium_src-4d6f3301690cf9d7af1862533ccdcccdc6c780dd.zip chromium_src-4d6f3301690cf9d7af1862533ccdcccdc6c780dd.tar.gz chromium_src-4d6f3301690cf9d7af1862533ccdcccdc6c780dd.tar.bz2 |
Remove scoped_array usage from RegistryKeyBackup.
BUG=171111
Review URL: https://codereview.chromium.org/14265020
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@194643 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/installer/util/registry_key_backup.cc')
-rw-r--r-- | chrome/installer/util/registry_key_backup.cc | 182 |
1 files changed, 74 insertions, 108 deletions
diff --git a/chrome/installer/util/registry_key_backup.cc b/chrome/installer/util/registry_key_backup.cc index e3494614..f06999b 100644 --- a/chrome/installer/util/registry_key_backup.cc +++ b/chrome/installer/util/registry_key_backup.cc @@ -5,7 +5,8 @@ #include "chrome/installer/util/registry_key_backup.h" #include <algorithm> -#include <limits> +#include <map> +#include <utility> #include <vector> #include "base/logging.h" @@ -14,47 +15,11 @@ using base::win::RegKey; namespace { -const REGSAM kKeyReadNoNotify = (KEY_READ) & ~(KEY_NOTIFY); -} // namespace - -// A container for a registry key, its values, and its subkeys. -class RegistryKeyBackup::KeyData { - public: - KeyData(); - ~KeyData(); - - // Initializes this object by reading the values and subkeys of |key|. - // Security descriptors are not backed up. Returns true if the operation was - // successful; false otherwise, in which case the state of this object is not - // modified. - bool Initialize(const RegKey& key); - - // Writes the contents of this object to |key|, which must have been opened - // with at least REG_SET_VALUE and KEY_CREATE_SUB_KEY access rights. Returns - // true if the operation was successful; false otherwise, in which case the - // contents of |key| may have been modified. - bool WriteTo(RegKey* key) const; - private: - class ValueData; - - // The values of this key. - scoped_array<ValueData> values_; - // The names of this key's sub-keys (the data for subkey_names_[i] is in - // subkeys_[i]). - scoped_array<std::wstring> subkey_names_; - // The key data of this key's sub-keys. - scoped_array<KeyData> subkeys_; - // The number of values for this key. - DWORD num_values_; - // The number of subkeys for this key. - DWORD num_subkeys_; - - DISALLOW_COPY_AND_ASSIGN(KeyData); -}; +const REGSAM kKeyReadNoNotify = (KEY_READ) & ~(KEY_NOTIFY); // A container for a registry value. -class RegistryKeyBackup::KeyData::ValueData { +class ValueData { public: ValueData(); ~ValueData(); @@ -89,18 +54,45 @@ class RegistryKeyBackup::KeyData::ValueData { // This value's type (e.g., REG_DWORD, REG_SZ, REG_QWORD, etc). DWORD type_; - DISALLOW_COPY_AND_ASSIGN(ValueData); + // Copy constructible and assignable for use in STL containers. +}; + +} // namespace + +// A container for a registry key, its values, and its subkeys. +class RegistryKeyBackup::KeyData { + public: + KeyData(); + ~KeyData(); + + // Initializes this object by reading the values and subkeys of |key|. + // Security descriptors are not backed up. Returns true if the operation was + // successful; false otherwise, in which case the state of this object is not + // modified. + bool Initialize(const RegKey& key); + + // Writes the contents of this object to |key|, which must have been opened + // with at least REG_SET_VALUE and KEY_CREATE_SUB_KEY access rights. Returns + // true if the operation was successful; false otherwise, in which case the + // contents of |key| may have been modified. + bool WriteTo(RegKey* key) const; + + private: + // The values of this key. + std::vector<ValueData> values_; + // Map of subkey names to the corresponding KeyData. + std::map<std::wstring, KeyData> subkeys_; + + // Copy constructible and assignable for use in STL containers. }; -RegistryKeyBackup::KeyData::ValueData::ValueData() - : type_(REG_NONE) { +ValueData::ValueData() : type_(REG_NONE) { } -RegistryKeyBackup::KeyData::ValueData::~ValueData() -{ +ValueData::~ValueData() { } -void RegistryKeyBackup::KeyData::ValueData::Initialize( +void ValueData::Initialize( const wchar_t* name_buffer, DWORD name_size, DWORD type, @@ -111,19 +103,15 @@ void RegistryKeyBackup::KeyData::ValueData::Initialize( data_.assign(data, data + data_size); } -RegistryKeyBackup::KeyData::KeyData() - : num_values_(0), - num_subkeys_(0) { +RegistryKeyBackup::KeyData::KeyData() { } -RegistryKeyBackup::KeyData::~KeyData() -{ +RegistryKeyBackup::KeyData::~KeyData() { } bool RegistryKeyBackup::KeyData::Initialize(const RegKey& key) { - scoped_array<ValueData> values; - scoped_array<std::wstring> subkey_names; - scoped_array<KeyData> subkeys; + std::vector<ValueData> values; + std::map<std::wstring, KeyData> subkeys; DWORD num_subkeys = 0; DWORD max_subkey_name_len = 0; @@ -138,52 +126,38 @@ bool RegistryKeyBackup::KeyData::Initialize(const RegKey& key) { LOG(ERROR) << "Failed getting info of key to backup, result: " << result; return false; } - if (max_subkey_name_len >= std::numeric_limits<DWORD>::max() - 1 || - max_value_name_len >= std::numeric_limits<DWORD>::max() - 1) { - LOG(ERROR) - << "Failed backing up key; subkeys and/or names are out of range."; - return false; - } DWORD max_name_len = std::max(max_subkey_name_len, max_value_name_len) + 1; - scoped_array<wchar_t> name_buffer(new wchar_t[max_name_len]); + std::vector<wchar_t> name_buffer(max_name_len); // Backup the values. if (num_values != 0) { - values.reset(new ValueData[num_values]); - scoped_array<uint8> value_buffer(new uint8[max_value_len]); + values.reserve(num_values); + std::vector<uint8> value_buffer(max_value_len != 0 ? max_value_len : 1); DWORD name_size = 0; DWORD value_type = REG_NONE; DWORD value_size = 0; for (DWORD i = 0; i < num_values; ) { - name_size = max_name_len; - value_size = max_value_len; - result = RegEnumValue(key.Handle(), i, name_buffer.get(), &name_size, - NULL, &value_type, value_buffer.get(), &value_size); + name_size = name_buffer.size(); + value_size = value_buffer.size(); + result = RegEnumValue(key.Handle(), i, &name_buffer[0], &name_size, + NULL, &value_type, &value_buffer[0], &value_size); switch (result) { case ERROR_NO_MORE_ITEMS: num_values = i; break; case ERROR_SUCCESS: - values[i].Initialize(name_buffer.get(), name_size, value_type, - value_buffer.get(), value_size); + values.push_back(ValueData()); + values.back().Initialize(&name_buffer[0], name_size, value_type, + &value_buffer[0], value_size); ++i; break; case ERROR_MORE_DATA: - if (value_size > max_value_len) { - max_value_len = value_size; - value_buffer.reset(); // Release to heap before new allocation. - value_buffer.reset(new uint8[max_value_len]); - } else { - DCHECK_LT(max_name_len - 1, name_size); - if (name_size >= std::numeric_limits<DWORD>::max() - 1) { - LOG(ERROR) << "Failed backing up key; value name out of range."; - return false; - } - max_name_len = name_size + 1; - name_buffer.reset(); // Release to heap before new allocation. - name_buffer.reset(new wchar_t[max_name_len]); - } + if (value_size > value_buffer.size()) + value_buffer.resize(value_size); + // |name_size| does not include space for the terminating NULL. + if (name_size + 1 > name_buffer.size()) + name_buffer.resize(name_size + 1); break; default: LOG(ERROR) << "Failed backing up value " << i << ", result: " @@ -191,7 +165,7 @@ bool RegistryKeyBackup::KeyData::Initialize(const RegKey& key) { return false; } } - DLOG_IF(WARNING, RegEnumValue(key.Handle(), num_values, name_buffer.get(), + DLOG_IF(WARNING, RegEnumValue(key.Handle(), num_values, &name_buffer[0], &name_size, NULL, &value_type, NULL, NULL) != ERROR_NO_MORE_ITEMS) << "Concurrent modifications to registry key during backup operation."; @@ -199,30 +173,23 @@ bool RegistryKeyBackup::KeyData::Initialize(const RegKey& key) { // Backup the subkeys. if (num_subkeys != 0) { - subkey_names.reset(new std::wstring[num_subkeys]); - subkeys.reset(new KeyData[num_subkeys]); DWORD name_size = 0; // Get the names of them. for (DWORD i = 0; i < num_subkeys; ) { - name_size = max_name_len; - result = RegEnumKeyEx(key.Handle(), i, name_buffer.get(), &name_size, + name_size = name_buffer.size(); + result = RegEnumKeyEx(key.Handle(), i, &name_buffer[0], &name_size, NULL, NULL, NULL, NULL); switch (result) { case ERROR_NO_MORE_ITEMS: num_subkeys = i; break; case ERROR_SUCCESS: - subkey_names[i].assign(name_buffer.get(), name_size); + subkeys.insert(std::make_pair(&name_buffer[0], KeyData())); ++i; break; case ERROR_MORE_DATA: - if (name_size >= std::numeric_limits<DWORD>::max() - 1) { - LOG(ERROR) << "Failed backing up key; subkey name out of range."; - return false; - } - max_name_len = name_size + 1; - name_buffer.reset(new wchar_t[max_name_len]); + name_buffer.resize(name_size + 1); break; default: LOG(ERROR) << "Failed getting name of subkey " << i @@ -237,26 +204,23 @@ bool RegistryKeyBackup::KeyData::Initialize(const RegKey& key) { // Get their values. RegKey subkey; - for (DWORD i = 0; i < num_subkeys; ++i) { - result = subkey.Open(key.Handle(), subkey_names[i].c_str(), - kKeyReadNoNotify); + for (std::map<std::wstring, KeyData>::iterator it = subkeys.begin(); + it != subkeys.end(); ++it) { + result = subkey.Open(key.Handle(), it->first.c_str(), kKeyReadNoNotify); if (result != ERROR_SUCCESS) { - LOG(ERROR) << "Failed opening subkey \"" << subkey_names[i] + LOG(ERROR) << "Failed opening subkey \"" << it->first << "\" for backup, result: " << result; return false; } - if (!subkeys[i].Initialize(subkey)) { - LOG(ERROR) << "Failed backing up subkey \"" << subkey_names[i] << "\""; + if (!it->second.Initialize(subkey)) { + LOG(ERROR) << "Failed backing up subkey \"" << it->first << "\""; return false; } } } values_.swap(values); - subkey_names_.swap(subkey_names); subkeys_.swap(subkeys); - num_values_ = num_values; - num_subkeys_ = num_subkeys; return true; } @@ -267,8 +231,9 @@ bool RegistryKeyBackup::KeyData::WriteTo(RegKey* key) const { LONG result = ERROR_SUCCESS; // Write the values. - for (DWORD i = 0; i < num_values_; ++i) { - const ValueData& value = values_[i]; + for (std::vector<ValueData>::const_iterator it = values_.begin(); + it != values_.end(); ++it) { + const ValueData& value = *it; result = RegSetValueEx(key->Handle(), value.name(), 0, value.type(), value.data(), value.data_len()); if (result != ERROR_SUCCESS) { @@ -280,8 +245,9 @@ bool RegistryKeyBackup::KeyData::WriteTo(RegKey* key) const { // Write the subkeys. RegKey subkey; - for (DWORD i = 0; i < num_subkeys_; ++i) { - const std::wstring& name = subkey_names_[i]; + for (std::map<std::wstring, KeyData>::const_iterator it = subkeys_.begin(); + it != subkeys_.end(); ++it) { + const std::wstring& name = it->first; result = subkey.Create(key->Handle(), name.c_str(), KEY_WRITE); if (result != ERROR_SUCCESS) { @@ -289,7 +255,7 @@ bool RegistryKeyBackup::KeyData::WriteTo(RegKey* key) const { << result; return false; } - if (!subkeys_[i].WriteTo(&subkey)) { + if (!it->second.WriteTo(&subkey)) { LOG(ERROR) << "Failed writing subkey \"" << name << "\", result: " << result; return false; |