2 * COPYRIGHT: GPL, see COPYING in the top level directory
3 * PROJECT: ReactOS win32 kernel mode subsystem server
4 * PURPOSE: Registry loading and storing
5 * FILE: subsystem/win32/win32k/misc/registry.c
6 * PROGRAMER: Timo Kreuzer (timo.kreuzer@reactos.org)
21 OBJECT_ATTRIBUTES ObjectAttributes
;
22 UNICODE_STRING ustrKeyName
;
25 /* Initialize the key name */
26 RtlInitUnicodeString(&ustrKeyName
, pwszKeyName
);
28 /* Initialize object attributes */
29 InitializeObjectAttributes(&ObjectAttributes
,
36 Status
= ZwOpenKey((PHANDLE
)&hkey
, KEY_READ
, &ObjectAttributes
);
37 if (NT_SUCCESS(Status
))
49 IN PCWSTR pwszValueName
,
52 IN OUT PULONG pcbValue
)
55 UNICODE_STRING ustrValueName
;
57 PKEY_VALUE_PARTIAL_INFORMATION pInfo
;
58 ULONG cbInfoSize
, cbDataSize
;
60 /* Check if the local buffer is sufficient */
61 cbInfoSize
= FIELD_OFFSET(KEY_VALUE_PARTIAL_INFORMATION
, Data
[*pcbValue
]);
62 if (cbInfoSize
<= sizeof(ajBuffer
))
64 pInfo
= (PVOID
)ajBuffer
;
68 /* It's not, allocate a sufficient buffer */
69 pInfo
= ExAllocatePoolWithTag(PagedPool
, cbInfoSize
, TAG_TEMP
);
72 return STATUS_INSUFFICIENT_RESOURCES
;
77 RtlInitUnicodeString(&ustrValueName
, pwszValueName
);
78 Status
= ZwQueryValueKey(hkey
,
80 KeyValuePartialInformation
,
85 cbDataSize
= pInfo
->DataLength
;
87 /* Note: STATUS_BUFFER_OVERFLOW is not a success */
88 if (NT_SUCCESS(Status
))
90 /* Did we get the right type */
91 if (pInfo
->Type
== ulType
)
93 /* Copy the contents to the caller */
94 RtlCopyMemory(pvData
, pInfo
->Data
, cbDataSize
);
97 Status
= STATUS_OBJECT_TYPE_MISMATCH
;
100 /* Return the data size to the caller */
101 *pcbValue
= cbDataSize
;
104 if (pInfo
!= (PVOID
)ajBuffer
)
105 ExFreePoolWithTag(pInfo
, TAG_TEMP
);
113 RegWriteSZ(HKEY hkey
, PWSTR pwszValue
, PWSTR pwszData
)
115 UNICODE_STRING ustrValue
;
116 UNICODE_STRING ustrData
;
118 RtlInitUnicodeString(&ustrValue
, pwszValue
);
119 RtlInitUnicodeString(&ustrData
, pwszData
);
120 ZwSetValueKey(hkey
, &ustrValue
, 0, REG_SZ
, &ustrData
, ustrData
.Length
+ sizeof(WCHAR
));
125 RegWriteDWORD(HKEY hkey
, PWSTR pwszValue
, DWORD dwData
)
127 UNICODE_STRING ustrValue
;
129 RtlInitUnicodeString(&ustrValue
, pwszValue
);
130 ZwSetValueKey(hkey
, &ustrValue
, 0, REG_DWORD
, &dwData
, sizeof(DWORD
));
135 RegReadDWORD(HKEY hkey
, PWSTR pwszValue
, PDWORD pdwData
)
138 ULONG cbSize
= sizeof(DWORD
);
139 Status
= RegQueryValue(hkey
, pwszValue
, REG_DWORD
, pdwData
, &cbSize
);
140 return NT_SUCCESS(Status
);
146 IN PCWSTR pwszKeyName
,
147 IN PCWSTR pwszValueName
,
153 OBJECT_ATTRIBUTES ObjectAttributes
;
154 UNICODE_STRING usCurrentUserKey
, usKeyName
, usValueName
;
155 WCHAR awcBuffer
[MAX_PATH
];
157 PKEY_VALUE_PARTIAL_INFORMATION pInfo
;
158 ULONG cbInfoSize
, cbReqSize
;
160 /* Get the path of the current user's profile */
161 Status
= RtlFormatCurrentUserKeyPath(&usCurrentUserKey
);
162 if (!NT_SUCCESS(Status
))
167 /* Initialize empty key name */
168 RtlInitEmptyUnicodeString(&usKeyName
, awcBuffer
, sizeof(awcBuffer
));
170 /* Append the current user key name */
171 Status
= RtlAppendUnicodeStringToString(&usKeyName
, &usCurrentUserKey
);
173 /* Free the current user key name */
174 RtlFreeUnicodeString(&usCurrentUserKey
);
176 /* Check for success */
177 if (!NT_SUCCESS(Status
))
182 /* Append a '\', we can trust in enough space left. */
183 usKeyName
.Buffer
[usKeyName
.Length
/ sizeof(WCHAR
)] = '\\';
184 usKeyName
.Length
+= sizeof(WCHAR
);
186 /* Append the subkey name */
187 Status
= RtlAppendUnicodeToString(&usKeyName
, pwszKeyName
);
188 if (!NT_SUCCESS(Status
))
193 /* Initialize object attributes */
194 InitializeObjectAttributes(&ObjectAttributes
,
196 OBJ_CASE_INSENSITIVE
,
201 Status
= ZwOpenKey((PHANDLE
)&hkey
, KEY_READ
, &ObjectAttributes
);
202 if (!NT_SUCCESS(Status
))
207 /* Check if the local buffer is sufficient */
208 cbInfoSize
= sizeof(KEY_VALUE_PARTIAL_INFORMATION
) + cbDataSize
;
209 if (cbInfoSize
<= sizeof(awcBuffer
))
211 pInfo
= (PVOID
)awcBuffer
;
215 /* It's not, allocate a sufficient buffer */
216 pInfo
= ExAllocatePoolWithTag(PagedPool
, cbInfoSize
, TAG_TEMP
);
224 /* Query the value */
225 RtlInitUnicodeString(&usValueName
, pwszValueName
);
226 Status
= ZwQueryValueKey(hkey
,
228 KeyValuePartialInformation
,
232 if (NT_SUCCESS(Status
))
234 /* Did we get the right type */
235 if (pInfo
->Type
== ulType
)
237 /* Copy the contents to the caller */
238 RtlCopyMemory(pvData
, pInfo
->Data
, cbDataSize
);
244 if (pInfo
!= (PVOID
)awcBuffer
)
245 ExFreePoolWithTag(pInfo
, TAG_TEMP
);
247 return NT_SUCCESS(Status
);
253 IN PCWSTR pwszKeyName
,
254 IN PCWSTR pwszValueName
,
260 OBJECT_ATTRIBUTES ObjectAttributes
;
261 UNICODE_STRING usCurrentUserKey
, usKeyName
, usValueName
;
262 WCHAR awcBuffer
[MAX_PATH
];
265 // FIXME: Logged in user versus current process user?
266 /* Get the path of the current user's profile */
267 Status
= RtlFormatCurrentUserKeyPath(&usCurrentUserKey
);
268 if (!NT_SUCCESS(Status
))
270 DPRINT1("RtlFormatCurrentUserKeyPath failed\n");
274 /* Initialize empty key name */
275 RtlInitEmptyUnicodeString(&usKeyName
, awcBuffer
, sizeof(awcBuffer
));
277 /* Append the current user key name */
278 Status
= RtlAppendUnicodeStringToString(&usKeyName
, &usCurrentUserKey
);
279 if (!NT_SUCCESS(Status
))
284 /* Free the current user key name */
285 RtlFreeUnicodeString(&usCurrentUserKey
);
287 /* Append a '\', we can trust in enough space left. */
288 usKeyName
.Buffer
[usKeyName
.Length
/ sizeof(WCHAR
)] = '\\';
289 usKeyName
.Length
+= sizeof(WCHAR
);
291 /* Append the subkey name */
292 Status
= RtlAppendUnicodeToString(&usKeyName
, pwszKeyName
);
293 if (!NT_SUCCESS(Status
))
295 DPRINT1("RtlAppendUnicodeToString failed with Status=0x%lx, buf:%u,%u\n",
296 Status
, usKeyName
.Length
, usKeyName
.MaximumLength
);
300 /* Initialize object attributes */
301 InitializeObjectAttributes(&ObjectAttributes
,
303 OBJ_CASE_INSENSITIVE
,
307 /* Open or create the key */
308 Status
= ZwCreateKey((PHANDLE
)&hkey
,
309 KEY_READ
| KEY_WRITE
,
315 if(!NT_SUCCESS(Status
))
317 DPRINT1("Failed to create key: 0x%x\n", Status
);
321 /* Initialize the value name string */
322 RtlInitUnicodeString(&usValueName
, pwszValueName
);
324 Status
= ZwSetValueKey(hkey
, &usValueName
, 0, ulType
, pvData
, cbDataSize
);
325 if(!NT_SUCCESS(Status
))
327 DPRINT1("Failed to write reg key '%S' value '%S', Status = %lx\n",
328 pwszKeyName
, pwszValueName
, Status
);
334 return NT_SUCCESS(Status
);