diff options
author | rvargas <rvargas@chromium.org> | 2014-10-16 18:28:58 -0700 |
---|---|---|
committer | Commit bot <commit-bot@chromium.org> | 2014-10-17 01:29:21 +0000 |
commit | 6f315b85b9126cdbbeee5457a7fa1dbeed058105 (patch) | |
tree | 94595e0e952654a1c1d9132b256ab004c72dbbad /base/win/registry.cc | |
parent | fde4714574d7c7c7f87620e7735c4bcf474df2ec (diff) | |
download | chromium_src-6f315b85b9126cdbbeee5457a7fa1dbeed058105.zip chromium_src-6f315b85b9126cdbbeee5457a7fa1dbeed058105.tar.gz chromium_src-6f315b85b9126cdbbeee5457a7fa1dbeed058105.tar.bz2 |
Remove raw handles from base::win::RegKey
BUG=419210, 423634
R=cpu@chromium.org, eroman@chromium.org, sky@chromium.org
Committed: https://crrev.com/1aa0fa75b65f403e08ae0f3f2fcb053c02cd9ef2
Cr-Commit-Position: refs/heads/master@{#299737}
Review URL: https://codereview.chromium.org/632833002
Cr-Commit-Position: refs/heads/master@{#300036}
Diffstat (limited to 'base/win/registry.cc')
-rw-r--r-- | base/win/registry.cc | 106 |
1 files changed, 59 insertions, 47 deletions
diff --git a/base/win/registry.cc b/base/win/registry.cc index e8fb892..23ad12c 100644 --- a/base/win/registry.cc +++ b/base/win/registry.cc @@ -34,23 +34,67 @@ const REGSAM kWow64AccessMask = KEY_WOW64_32KEY | KEY_WOW64_64KEY; } // namespace +// Watches for modifications to a key. +class RegKey::Watcher : public ObjectWatcher::Delegate { + public: + explicit Watcher(RegKey* owner) : owner_(owner) {} + ~Watcher() {} + + bool StartWatching(HKEY key, const ChangeCallback& callback); + + // Implementation of ObjectWatcher::Delegate. + void OnObjectSignaled(HANDLE object) override { + DCHECK(watch_event_.IsValid() && watch_event_.Get() == object); + ChangeCallback callback = callback_; + callback_.Reset(); + callback.Run(); + } + + private: + RegKey* owner_; + ScopedHandle watch_event_; + ObjectWatcher object_watcher_; + ChangeCallback callback_; + DISALLOW_COPY_AND_ASSIGN(Watcher); +}; + +bool RegKey::Watcher::StartWatching(HKEY key, const ChangeCallback& callback) { + DCHECK(key); + DCHECK(callback_.is_null()); + + if (!watch_event_.IsValid()) + watch_event_.Set(CreateEvent(NULL, TRUE, FALSE, NULL)); + + if (!watch_event_.IsValid()) + return false; + + DWORD filter = REG_NOTIFY_CHANGE_NAME | + REG_NOTIFY_CHANGE_ATTRIBUTES | + REG_NOTIFY_CHANGE_LAST_SET | + REG_NOTIFY_CHANGE_SECURITY; + + // Watch the registry key for a change of value. + LONG result = RegNotifyChangeKeyValue(key, TRUE, filter, watch_event_.Get(), + TRUE); + if (result != ERROR_SUCCESS) { + watch_event_.Close(); + return false; + } + + callback_ = callback; + return object_watcher_.StartWatching(watch_event_.Get(), this); +} + // RegKey ---------------------------------------------------------------------- -RegKey::RegKey() - : key_(NULL), - watch_event_(0), - wow64access_(0) { +RegKey::RegKey() : key_(NULL), wow64access_(0) { } -RegKey::RegKey(HKEY key) - : key_(key), - watch_event_(0), - wow64access_(0) { +RegKey::RegKey(HKEY key) : key_(key), wow64access_(0) { } RegKey::RegKey(HKEY rootkey, const wchar_t* subkey, REGSAM access) : key_(NULL), - watch_event_(0), wow64access_(0) { if (rootkey) { if (access & (KEY_SET_VALUE | KEY_CREATE_SUB_KEY | KEY_CREATE_LINK)) @@ -150,7 +194,6 @@ LONG RegKey::OpenKey(const wchar_t* relative_key_name, REGSAM access) { } void RegKey::Close() { - StopWatching(); if (key_) { ::RegCloseKey(key_); key_ = NULL; @@ -168,7 +211,6 @@ void RegKey::Set(HKEY key) { HKEY RegKey::Take() { DCHECK(wow64access_ == 0); - StopWatching(); HKEY key = key_; key_ = NULL; return key; @@ -367,44 +409,14 @@ LONG RegKey::WriteValue(const wchar_t* name, return result; } -LONG RegKey::StartWatching() { - DCHECK(key_); - if (!watch_event_) - watch_event_ = CreateEvent(NULL, TRUE, FALSE, NULL); - - DWORD filter = REG_NOTIFY_CHANGE_NAME | - REG_NOTIFY_CHANGE_ATTRIBUTES | - REG_NOTIFY_CHANGE_LAST_SET | - REG_NOTIFY_CHANGE_SECURITY; - - // Watch the registry key for a change of value. - LONG result = RegNotifyChangeKeyValue(key_, TRUE, filter, watch_event_, TRUE); - if (result != ERROR_SUCCESS) { - CloseHandle(watch_event_); - watch_event_ = 0; - } +bool RegKey::StartWatching(const ChangeCallback& callback) { + if (!key_watcher_) + key_watcher_.reset(new Watcher(this)); - return result; -} - -bool RegKey::HasChanged() { - if (watch_event_) { - if (WaitForSingleObject(watch_event_, 0) == WAIT_OBJECT_0) { - StartWatching(); - return true; - } - } - return false; -} + if (!key_watcher_.get()->StartWatching(key_, callback)) + return false; -LONG RegKey::StopWatching() { - LONG result = ERROR_INVALID_HANDLE; - if (watch_event_) { - CloseHandle(watch_event_); - watch_event_ = 0; - result = ERROR_SUCCESS; - } - return result; + return true; } // static |