• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  Copyright 2003 The WebRTC Project Authors. All rights reserved.
3  *
4  *  Use of this source code is governed by a BSD-style license
5  *  that can be found in the LICENSE file in the root of the source
6  *  tree. An additional intellectual property rights grant can be found
7  *  in the file PATENTS.  All contributing project authors may
8  *  be found in the AUTHORS file in the root of the source tree.
9  */
10 
11 // Registry configuration wrappers class
12 //
13 // Offers static functions for convenient
14 // fast access for individual values
15 //
16 // Also provides a wrapper class for efficient
17 // batch operations on values of a given registry key.
18 //
19 
20 #ifndef WEBRTC_BASE_WIN32REGKEY_H_
21 #define WEBRTC_BASE_WIN32REGKEY_H_
22 
23 #include <string>
24 #include <vector>
25 
26 #include "webrtc/base/basictypes.h"
27 #include "webrtc/base/constructormagic.h"
28 #include "webrtc/base/win32.h"
29 
30 namespace rtc {
31 
32 // maximum sizes registry key and value names
33 const int kMaxKeyNameChars = 255 + 1;
34 const int kMaxValueNameChars = 16383 + 1;
35 
36 class RegKey {
37  public:
38   // constructor
39   RegKey();
40 
41   // destructor
42   ~RegKey();
43 
44   // create a reg key
45   HRESULT Create(HKEY parent_key, const wchar_t* key_name);
46 
47   HRESULT Create(HKEY parent_key,
48                  const wchar_t* key_name,
49                  wchar_t* reg_class,
50                  DWORD options,
51                  REGSAM sam_desired,
52                  LPSECURITY_ATTRIBUTES lp_sec_attr,
53                  LPDWORD lp_disposition);
54 
55   // open an existing reg key
56   HRESULT Open(HKEY parent_key, const wchar_t* key_name);
57 
58   HRESULT Open(HKEY parent_key, const wchar_t* key_name, REGSAM sam_desired);
59 
60   // close this reg key
61   HRESULT Close();
62 
63   // check if the key has a specified value
64   bool HasValue(const wchar_t* value_name) const;
65 
66   // get the number of values for this key
67   uint32_t GetValueCount();
68 
69   // Called to get the value name for the given value name index
70   // Use GetValueCount() to get the total value_name count for this key
71   // Returns failure if no key at the specified index
72   // If you modify the key while enumerating, the indexes will be out of order.
73   // Since the index order is not guaranteed, you need to reset your counting
74   // loop.
75   // 'type' refers to REG_DWORD, REG_QWORD, etc..
76   // 'type' can be NULL if not interested in the value type
77   HRESULT GetValueNameAt(int index, std::wstring* value_name, DWORD* type);
78 
79   // check if the current key has the specified subkey
80   bool HasSubkey(const wchar_t* key_name) const;
81 
82   // get the number of subkeys for this key
83   uint32_t GetSubkeyCount();
84 
85   // Called to get the key name for the given key index
86   // Use GetSubkeyCount() to get the total count for this key
87   // Returns failure if no key at the specified index
88   // If you modify the key while enumerating, the indexes will be out of order.
89   // Since the index order is not guaranteed, you need to reset your counting
90   // loop.
91   HRESULT GetSubkeyNameAt(int index, std::wstring* key_name);
92 
93   // SETTERS
94 
95   // set an int32_t value - use when reading multiple values from a key
96   HRESULT SetValue(const wchar_t* value_name, DWORD value) const;
97 
98   // set an int64_t value
99   HRESULT SetValue(const wchar_t* value_name, DWORD64 value) const;
100 
101   // set a string value
102   HRESULT SetValue(const wchar_t* value_name, const wchar_t* value) const;
103 
104   // set binary data
105   HRESULT SetValue(const wchar_t* value_name,
106                    const uint8_t* value,
107                    DWORD byte_count) const;
108 
109   // set raw data, including type
110   HRESULT SetValue(const wchar_t* value_name,
111                    const uint8_t* value,
112                    DWORD byte_count,
113                    DWORD type) const;
114 
115   // GETTERS
116 
117   // get an int32_t value
118   HRESULT GetValue(const wchar_t* value_name, DWORD* value) const;
119 
120   // get an int64_t value
121   HRESULT GetValue(const wchar_t* value_name, DWORD64* value) const;
122 
123   // get a string value - the caller must free the return buffer
124   HRESULT GetValue(const wchar_t* value_name, wchar_t** value) const;
125 
126   // get a string value
127   HRESULT GetValue(const wchar_t* value_name, std::wstring* value) const;
128 
129   // get a std::vector<std::wstring> value from REG_MULTI_SZ type
130   HRESULT GetValue(const wchar_t* value_name,
131                    std::vector<std::wstring>* value) const;
132 
133   // get binary data - the caller must free the return buffer
134   HRESULT GetValue(const wchar_t* value_name,
135                    uint8_t** value,
136                    DWORD* byte_count) const;
137 
138   // get raw data, including type - the caller must free the return buffer
139   HRESULT GetValue(const wchar_t* value_name,
140                    uint8_t** value,
141                    DWORD* byte_count,
142                    DWORD* type) const;
143 
144   // STATIC VERSIONS
145 
146   // flush
147   static HRESULT FlushKey(const wchar_t* full_key_name);
148 
149   // check if a key exists
150   static bool HasKey(const wchar_t* full_key_name);
151 
152   // check if the key has a specified value
153   static bool HasValue(const wchar_t* full_key_name, const wchar_t* value_name);
154 
155   // SETTERS
156 
157   // STATIC int32_t set
158   static HRESULT SetValue(const wchar_t* full_key_name,
159                           const wchar_t* value_name,
160                           DWORD value);
161 
162   // STATIC int64_t set
163   static HRESULT SetValue(const wchar_t* full_key_name,
164                           const wchar_t* value_name,
165                           DWORD64 value);
166 
167   // STATIC float set
168   static HRESULT SetValue(const wchar_t* full_key_name,
169                           const wchar_t* value_name,
170                           float value);
171 
172   // STATIC double set
173   static HRESULT SetValue(const wchar_t* full_key_name,
174                           const wchar_t* value_name,
175                           double value);
176 
177   // STATIC string set
178   static HRESULT SetValue(const wchar_t* full_key_name,
179                           const wchar_t* value_name,
180                           const wchar_t* value);
181 
182   // STATIC binary data set
183   static HRESULT SetValue(const wchar_t* full_key_name,
184                           const wchar_t* value_name,
185                           const uint8_t* value,
186                           DWORD byte_count);
187 
188   // STATIC multi-string set
189   static HRESULT SetValueMultiSZ(const wchar_t* full_key_name,
190                                  const TCHAR* value_name,
191                                  const uint8_t* value,
192                                  DWORD byte_count);
193 
194   // GETTERS
195 
196   // STATIC int32_t get
197   static HRESULT GetValue(const wchar_t* full_key_name,
198                           const wchar_t* value_name,
199                           DWORD* value);
200 
201   // STATIC int64_t get
202   //
203   // Note: if you are using time64 you should
204   // likely use GetLimitedTimeValue (util.h) instead of this method.
205   static HRESULT GetValue(const wchar_t* full_key_name,
206                           const wchar_t* value_name,
207                           DWORD64* value);
208 
209   // STATIC float get
210   static HRESULT GetValue(const wchar_t* full_key_name,
211                           const wchar_t* value_name,
212                           float* value);
213 
214   // STATIC double get
215   static HRESULT GetValue(const wchar_t* full_key_name,
216                           const wchar_t* value_name,
217                           double* value);
218 
219   // STATIC string get
220   // Note: the caller must free the return buffer for wchar_t* version
221   static HRESULT GetValue(const wchar_t* full_key_name,
222                           const wchar_t* value_name,
223                           wchar_t** value);
224   static HRESULT GetValue(const wchar_t* full_key_name,
225                           const wchar_t* value_name,
226                           std::wstring* value);
227 
228   // STATIC REG_MULTI_SZ get
229   static HRESULT GetValue(const wchar_t* full_key_name,
230                           const wchar_t* value_name,
231                           std::vector<std::wstring>* value);
232 
233   // STATIC get binary data - the caller must free the return buffer
234   static HRESULT GetValue(const wchar_t* full_key_name,
235                           const wchar_t* value_name,
236                           uint8_t** value,
237                           DWORD* byte_count);
238 
239   // Get type of a registry value
240   static HRESULT GetValueType(const wchar_t* full_key_name,
241                               const wchar_t* value_name,
242                               DWORD* value_type);
243 
244   // delete a subkey of the current key (with no subkeys)
245   HRESULT DeleteSubKey(const wchar_t* key_name);
246 
247   // recursively delete a sub key of the current key (and all its subkeys)
248   HRESULT RecurseDeleteSubKey(const wchar_t* key_name);
249 
250   // STATIC version of delete key - handles nested keys also
251   // delete a key and all its sub-keys recursively
252   // Returns S_FALSE if key didn't exist, S_OK if deletion was successful,
253   // and failure otherwise.
254   static HRESULT DeleteKey(const wchar_t* full_key_name);
255 
256   // STATIC version of delete key
257   // delete a key recursively or non-recursively
258   // Returns S_FALSE if key didn't exist, S_OK if deletion was successful,
259   // and failure otherwise.
260   static HRESULT DeleteKey(const wchar_t* full_key_name, bool recursive);
261 
262   // delete the specified value
263   HRESULT DeleteValue(const wchar_t* value_name);
264 
265   // STATIC version of delete value
266   // Returns S_FALSE if key didn't exist, S_OK if deletion was successful,
267   // and failure otherwise.
268   static HRESULT DeleteValue(const wchar_t* full_key_name,
269                              const wchar_t* value_name);
270 
271   // Peek inside (use a RegKey as a smart wrapper around a registry handle)
key()272   HKEY key() { return h_key_; }
273 
274   // helper function to get the HKEY and the root key from a string
275   // modifies the argument in place and returns the key name
276   // e.g. HKLM\\Software\\Google\... returns HKLM, "Software\\Google\..."
277   // Necessary for the static versions that use the full name of the reg key
278   static HKEY GetRootKeyInfo(std::wstring* full_key_name);
279 
280   // Returns true if this key name is 'safe' for deletion (doesn't specify a key
281   // root)
282   static bool SafeKeyNameForDeletion(const wchar_t* key_name);
283 
284   // save the key and all of its subkeys and values to a file
285   static HRESULT Save(const wchar_t* full_key_name, const wchar_t* file_name);
286 
287   // restore the key and all of its subkeys and values which are saved into a
288   // file
289   static HRESULT Restore(const wchar_t* full_key_name,
290                          const wchar_t* file_name);
291 
292   // Is the key empty: having no sub-keys and values
293   static bool IsKeyEmpty(const wchar_t* full_key_name);
294 
295  private:
296 
297   // helper function to get any value from the registry
298   // used when the size of the data is unknown
299   HRESULT GetValueHelper(const wchar_t* value_name,
300                          DWORD* type,
301                          uint8_t** value,
302                          DWORD* byte_count) const;
303 
304   // helper function to get the parent key name and the subkey from a string
305   // modifies the argument in place and returns the key name
306   // Necessary for the static versions that use the full name of the reg key
307   static std::wstring GetParentKeyInfo(std::wstring* key_name);
308 
309   // common SET Helper for the static case
310   static HRESULT SetValueStaticHelper(const wchar_t* full_key_name,
311                                       const wchar_t* value_name,
312                                       DWORD type,
313                                       LPVOID value,
314                                       DWORD byte_count = 0);
315 
316   // common GET Helper for the static case
317   static HRESULT GetValueStaticHelper(const wchar_t* full_key_name,
318                                       const wchar_t* value_name,
319                                       DWORD type,
320                                       LPVOID value,
321                                       DWORD* byte_count = NULL);
322 
323   // convert REG_MULTI_SZ bytes to string array
324   static HRESULT MultiSZBytesToStringArray(const uint8_t* buffer,
325                                            DWORD byte_count,
326                                            std::vector<std::wstring>* value);
327 
328   // the HKEY for the current key
329   HKEY h_key_;
330 
331   // for unittest
332   friend void RegKeyHelperFunctionsTest();
333 
334   RTC_DISALLOW_COPY_AND_ASSIGN(RegKey);
335 };
336 
337 }  // namespace rtc
338 
339 #endif  // WEBRTC_BASE_WIN32REGKEY_H_
340