- KdDebuggerNotPresent should be FALSE by default.
[reactos.git] / reactos / ntoskrnl / cm / import.c
1 /* $Id$
2 *
3 * PROJECT: ReactOS Kernel
4 * COPYRIGHT: GPL - See COPYING in the top level directory
5 * FILE: ntoskrnl/cm/import.c
6 * PURPOSE: Registry-Hive import functions
7 *
8 * PROGRAMMERS: Eric Kohl
9 */
10
11 /* INCLUDES *****************************************************************/
12
13 #include <ntoskrnl.h>
14 #define NDEBUG
15 #include <internal/debug.h>
16
17 #include "cm.h"
18
19 #if defined (ALLOC_PRAGMA)
20 #pragma alloc_text(INIT, CmImportHardwareHive)
21 #endif
22
23 /* GLOBALS ******************************************************************/
24
25 static BOOLEAN CmiHardwareHiveImported = FALSE;
26
27 /* FUNCTIONS ****************************************************************/
28
29 static BOOLEAN
30 CmImportBinaryHive (PCHAR ChunkBase,
31 ULONG ChunkSize,
32 ULONG Flags,
33 PEREGISTRY_HIVE *RegistryHive)
34 {
35 PEREGISTRY_HIVE Hive;
36 NTSTATUS Status;
37
38 *RegistryHive = NULL;
39
40 /* Create a new hive */
41 Hive = ExAllocatePool (NonPagedPool,
42 sizeof(EREGISTRY_HIVE));
43 if (Hive == NULL)
44 {
45 return FALSE;
46 }
47 RtlZeroMemory (Hive,
48 sizeof(EREGISTRY_HIVE));
49
50 /* Set hive flags */
51 Hive->Flags = Flags;
52
53 /* Allocate hive header */
54 ((PHBASE_BLOCK)ChunkBase)->Length = ChunkSize;
55 Status = HvInitialize(&Hive->Hive, HV_OPERATION_MEMORY, 0, 0,
56 (ULONG_PTR)ChunkBase, 0,
57 CmpAllocate, CmpFree,
58 CmpFileRead, CmpFileWrite, CmpFileSetSize,
59 CmpFileFlush, NULL);
60 if (!NT_SUCCESS(Status))
61 {
62 DPRINT1 ("Opening hive failed (%x)\n", Status);
63 ExFreePool (Hive);
64 return FALSE;
65 }
66
67 CmPrepareHive(&Hive->Hive);
68
69 /* Acquire hive list lock exclusively */
70 KeEnterCriticalRegion();
71 ExAcquireResourceExclusiveLite(&CmiRegistryLock, TRUE);
72
73 DPRINT("Adding new hive\n");
74
75 /* Add the new hive to the hive list */
76 InsertTailList(&CmiHiveListHead, &Hive->HiveList);
77
78 /* Release hive list lock */
79 ExReleaseResourceLite(&CmiRegistryLock);
80 KeLeaveCriticalRegion();
81
82 *RegistryHive = Hive;
83
84 return TRUE;
85 }
86
87
88 BOOLEAN INIT_FUNCTION
89 CmImportSystemHive(PCHAR ChunkBase,
90 ULONG ChunkSize)
91 {
92 OBJECT_ATTRIBUTES ObjectAttributes;
93 PEREGISTRY_HIVE RegistryHive;
94 UNICODE_STRING KeyName;
95 NTSTATUS Status;
96
97 DPRINT ("CmImportSystemHive() called\n");
98
99 if (strncmp (ChunkBase, "regf", 4))
100 {
101 DPRINT1 ("Found invalid '%.*s' magic\n", 4, ChunkBase);
102 return FALSE;
103 }
104
105 DPRINT ("Found '%.*s' magic\n", 4, ChunkBase);
106
107 /* Import the binary system hive (non-volatile, offset-based, permanent) */
108 if (!CmImportBinaryHive (ChunkBase, ChunkSize, 0, &RegistryHive))
109 {
110 DPRINT1 ("CmiImportBinaryHive() failed\n");
111 return FALSE;
112 }
113
114 /* Attach it to the machine key */
115 RtlInitUnicodeString (&KeyName,
116 REG_SYSTEM_KEY_NAME);
117 InitializeObjectAttributes (&ObjectAttributes,
118 &KeyName,
119 OBJ_CASE_INSENSITIVE,
120 NULL,
121 NULL);
122 Status = CmiConnectHive (&ObjectAttributes,
123 RegistryHive);
124 if (!NT_SUCCESS(Status))
125 {
126 DPRINT1 ("CmiConnectHive(%wZ) failed (Status %lx)\n", &KeyName, Status);
127 return FALSE;
128 }
129
130 /* Set the hive filename */
131 RtlCreateUnicodeString (&RegistryHive->HiveFileName,
132 SYSTEM_REG_FILE);
133
134 /* Set the log filename */
135 RtlCreateUnicodeString (&RegistryHive->LogFileName,
136 SYSTEM_LOG_FILE);
137
138 return TRUE;
139 }
140
141
142 BOOLEAN INIT_FUNCTION
143 CmImportHardwareHive(PCHAR ChunkBase,
144 ULONG ChunkSize)
145 {
146 OBJECT_ATTRIBUTES ObjectAttributes;
147 PEREGISTRY_HIVE RegistryHive;
148 UNICODE_STRING KeyName;
149 HANDLE HardwareKey;
150 ULONG Disposition;
151 NTSTATUS Status;
152
153 DPRINT ("CmImportHardwareHive() called\n");
154
155 if (CmiHardwareHiveImported == TRUE)
156 return TRUE;
157
158 if (ChunkBase == NULL &&
159 ChunkSize == 0)
160 {
161 /* Create '\Registry\Machine\HARDWARE' key. */
162 RtlInitUnicodeString (&KeyName,
163 REG_HARDWARE_KEY_NAME);
164 InitializeObjectAttributes (&ObjectAttributes,
165 &KeyName,
166 OBJ_CASE_INSENSITIVE,
167 NULL,
168 NULL);
169 Status = ZwCreateKey (&HardwareKey,
170 KEY_ALL_ACCESS,
171 &ObjectAttributes,
172 0,
173 NULL,
174 REG_OPTION_VOLATILE,
175 &Disposition);
176 if (!NT_SUCCESS(Status))
177 {
178 DPRINT1("NtCreateKey() failed, status: 0x%x\n", Status);
179 return FALSE;
180 }
181 ZwClose (HardwareKey);
182
183 /* Create '\Registry\Machine\HARDWARE\DESCRIPTION' key. */
184 RtlInitUnicodeString(&KeyName,
185 REG_DESCRIPTION_KEY_NAME);
186 InitializeObjectAttributes (&ObjectAttributes,
187 &KeyName,
188 OBJ_CASE_INSENSITIVE,
189 NULL,
190 NULL);
191 Status = ZwCreateKey (&HardwareKey,
192 KEY_ALL_ACCESS,
193 &ObjectAttributes,
194 0,
195 NULL,
196 REG_OPTION_VOLATILE,
197 &Disposition);
198 if (!NT_SUCCESS(Status))
199 {
200 DPRINT1("NtCreateKey() failed, status: 0x%x\n", Status);
201 return FALSE;
202 }
203 ZwClose (HardwareKey);
204
205 /* Create '\Registry\Machine\HARDWARE\DEVICEMAP' key. */
206 RtlInitUnicodeString (&KeyName,
207 REG_DEVICEMAP_KEY_NAME);
208 InitializeObjectAttributes (&ObjectAttributes,
209 &KeyName,
210 OBJ_CASE_INSENSITIVE,
211 NULL,
212 NULL);
213 Status = ZwCreateKey (&HardwareKey,
214 KEY_ALL_ACCESS,
215 &ObjectAttributes,
216 0,
217 NULL,
218 REG_OPTION_VOLATILE,
219 &Disposition);
220 if (!NT_SUCCESS(Status))
221 {
222 DPRINT1("NtCreateKey() failed, status: 0x%x\n", Status);
223 return FALSE;
224 }
225 ZwClose (HardwareKey);
226
227 /* Create '\Registry\Machine\HARDWARE\RESOURCEMAP' key. */
228 RtlInitUnicodeString(&KeyName,
229 REG_RESOURCEMAP_KEY_NAME);
230 InitializeObjectAttributes (&ObjectAttributes,
231 &KeyName,
232 OBJ_CASE_INSENSITIVE,
233 NULL,
234 NULL);
235 Status = ZwCreateKey (&HardwareKey,
236 KEY_ALL_ACCESS,
237 &ObjectAttributes,
238 0,
239 NULL,
240 REG_OPTION_VOLATILE,
241 &Disposition);
242 if (!NT_SUCCESS(Status))
243 {
244 DPRINT1("NtCreateKey() failed, status: 0x%x\n", Status);
245 return FALSE;
246 }
247 ZwClose (HardwareKey);
248
249 return TRUE;
250 }
251
252 /* Check the hive magic */
253 if (strncmp (ChunkBase, "regf", 4))
254 {
255 DPRINT1 ("Found invalid '%.*s' magic\n", 4, ChunkBase);
256 return FALSE;
257 }
258
259 DPRINT ("Found '%.*s' magic\n", 4, ChunkBase);
260 DPRINT ("ChunkBase %lx ChunkSize %lu\n", ChunkBase, ChunkSize);
261
262 /* Import the binary system hive (volatile, offset-based, permanent) */
263 if (!CmImportBinaryHive (ChunkBase, ChunkSize, HIVE_NO_FILE, &RegistryHive))
264 {
265 DPRINT1 ("CmiImportBinaryHive() failed\n");
266 return FALSE;
267 }
268
269 /* Attach it to the machine key */
270 RtlInitUnicodeString (&KeyName,
271 REG_HARDWARE_KEY_NAME);
272 InitializeObjectAttributes (&ObjectAttributes,
273 &KeyName,
274 OBJ_CASE_INSENSITIVE,
275 NULL,
276 NULL);
277 Status = CmiConnectHive (&ObjectAttributes,
278 RegistryHive);
279 if (!NT_SUCCESS(Status))
280 {
281 DPRINT1 ("CmiConnectHive(%wZ) failed (Status %lx)\n", &KeyName, Status);
282 // CmiRemoveRegistryHive(RegistryHive);
283 return FALSE;
284 }
285
286 /* Set the hive filename */
287 RtlInitUnicodeString (&RegistryHive->HiveFileName,
288 NULL);
289
290 /* Set the log filename */
291 RtlInitUnicodeString (&RegistryHive->LogFileName,
292 NULL);
293
294 CmiHardwareHiveImported = TRUE;
295
296 return TRUE;
297 }
298
299 /* EOF */