1 /* $Id: import.c,v 1.23 2003/10/12 17:05:44 hbirr Exp $
3 * COPYRIGHT: See COPYING in the top level directory
4 * PROJECT: ReactOS kernel
5 * FILE: ntoskrnl/cm/import.c
6 * PURPOSE: Registry-Hive import functions
7 * PROGRAMMERS: Eric Kohl
10 /* INCLUDES *****************************************************************/
13 #include <ddk/ntddk.h>
17 #include <internal/ob.h>
18 #include <internal/pool.h>
19 #include <internal/registry.h>
20 #include <internal/ntoskrnl.h>
23 #include <internal/debug.h>
27 /* GLOBALS ******************************************************************/
29 static BOOLEAN CmiHardwareHiveImported
= FALSE
;
32 /* FUNCTIONS ****************************************************************/
35 CmImportBinaryHive (PCHAR ChunkBase
,
38 PREGISTRY_HIVE
*RegistryHive
)
45 if (strncmp (ChunkBase
, "regf", 4))
47 DPRINT1 ("Found invalid '%*s' magic\n", 4, ChunkBase
);
51 /* Create a new hive */
52 Hive
= ExAllocatePool (NonPagedPool
,
53 sizeof(REGISTRY_HIVE
));
59 sizeof(REGISTRY_HIVE
));
64 /* Allocate hive header */
65 Hive
->HiveHeader
= (PHIVE_HEADER
)ExAllocatePool (NonPagedPool
,
67 if (Hive
->HiveHeader
== NULL
)
69 DPRINT1 ("Allocating hive header failed\n");
74 /* Import the hive header */
75 RtlCopyMemory (Hive
->HiveHeader
,
79 /* Read update counter */
80 Hive
->UpdateCounter
= Hive
->HiveHeader
->UpdateCounter1
;
82 /* Set the hive's size */
83 Hive
->FileSize
= ChunkSize
;
85 /* Set the size of the block list */
86 Hive
->BlockListSize
= (Hive
->FileSize
/ 4096) - 1;
88 /* Allocate block list */
89 DPRINT("Space needed for block list describing hive: 0x%x\n",
90 Hive
->BlockListSize
* sizeof(PHBIN
*));
91 Hive
->BlockList
= ExAllocatePool (NonPagedPool
,
92 Hive
->BlockListSize
* sizeof(PHBIN
*));
93 if (Hive
->BlockList
== NULL
)
95 DPRINT1 ("Allocating block list failed\n");
96 ExFreePool (Hive
->HiveHeader
);
100 RtlZeroMemory (Hive
->BlockList
,
101 Hive
->BlockListSize
* sizeof(PHBIN
*));
103 /* Import the bins */
104 Status
= CmiImportHiveBins(Hive
,
105 (PUCHAR
)((ULONG_PTR
)ChunkBase
+ 4096));
106 if (!NT_SUCCESS(Status
))
108 DPRINT1 ("CmiImportHiveBins() failed (Status %lx)\n", Status
);
109 CmiFreeHiveBins (Hive
);
110 ExFreePool (Hive
->BlockList
);
111 ExFreePool (Hive
->HiveHeader
);
116 /* Initialize the free cell list */
117 Status
= CmiCreateHiveFreeCellList (Hive
);
118 if (!NT_SUCCESS(Status
))
120 DPRINT1 ("CmiCreateHiveFreeCellList() failed (Status %lx)\n", Status
);
121 CmiFreeHiveBins (Hive
);
122 ExFreePool (Hive
->BlockList
);
123 ExFreePool (Hive
->HiveHeader
);
129 if (!(Hive
->Flags
& HIVE_NO_FILE
))
131 /* Create the block bitmap */
132 Status
= CmiCreateHiveBitmap (Hive
);
133 if (!NT_SUCCESS(Status
))
135 DPRINT1 ("CmiCreateHiveBitmap() failed (Status %lx)\n", Status
);
136 CmiFreeHiveFreeCellList (Hive
);
137 CmiFreeHiveBins (Hive
);
138 ExFreePool (Hive
->BlockList
);
139 ExFreePool (Hive
->HiveHeader
);
146 /* Initialize the hive's executive resource */
147 ExInitializeResourceLite(&Hive
->HiveResource
);
149 /* Acquire hive list lock exclusively */
150 ExAcquireResourceExclusiveLite(&CmiHiveListLock
, TRUE
);
152 /* Add the new hive to the hive list */
153 InsertTailList(&CmiHiveListHead
, &Hive
->HiveList
);
155 /* Release hive list lock */
156 ExReleaseResourceLite(&CmiHiveListLock
);
158 *RegistryHive
= Hive
;
164 BOOLEAN INIT_FUNCTION
165 CmImportSystemHive(PCHAR ChunkBase
,
168 OBJECT_ATTRIBUTES ObjectAttributes
;
169 PREGISTRY_HIVE RegistryHive
;
170 UNICODE_STRING KeyName
;
173 DPRINT ("CmImportSystemHive() called\n");
175 if (strncmp (ChunkBase
, "regf", 4))
177 DPRINT1 ("Found invalid '%.*s' magic\n", 4, ChunkBase
);
181 DPRINT ("Found '%.*s' magic\n", 4, ChunkBase
);
183 /* Import the binary system hive (non-volatile, offset-based, permanent) */
184 if (!CmImportBinaryHive (ChunkBase
, ChunkSize
, 0, &RegistryHive
))
186 DPRINT1 ("CmiImportBinaryHive() failed\n", Status
);
190 /* Attach it to the machine key */
191 RtlInitUnicodeString (&KeyName
,
192 L
"\\Registry\\Machine\\System");
193 InitializeObjectAttributes (&ObjectAttributes
,
195 OBJ_CASE_INSENSITIVE
,
198 Status
= CmiConnectHive (&ObjectAttributes
,
200 if (!NT_SUCCESS(Status
))
202 DPRINT1 ("CmiConnectHive() failed (Status %lx)\n", Status
);
203 // CmiRemoveRegistryHive(RegistryHive);
207 /* Set the hive filename */
208 RtlCreateUnicodeString (&RegistryHive
->HiveFileName
,
211 /* Set the log filename */
212 RtlCreateUnicodeString (&RegistryHive
->LogFileName
,
219 BOOLEAN INIT_FUNCTION
220 CmImportHardwareHive(PCHAR ChunkBase
,
223 OBJECT_ATTRIBUTES ObjectAttributes
;
224 PREGISTRY_HIVE RegistryHive
;
225 UNICODE_STRING KeyName
;
230 DPRINT ("CmImportHardwareHive() called\n");
232 if (CmiHardwareHiveImported
== TRUE
)
235 if (ChunkBase
== NULL
&&
238 /* Create '\Registry\Machine\HARDWARE' key. */
239 RtlInitUnicodeString (&KeyName
,
240 L
"\\Registry\\Machine\\HARDWARE");
241 InitializeObjectAttributes (&ObjectAttributes
,
243 OBJ_CASE_INSENSITIVE
,
246 Status
= NtCreateKey (&HardwareKey
,
253 if (!NT_SUCCESS(Status
))
257 NtClose (HardwareKey
);
259 /* Create '\Registry\Machine\HARDWARE\DESCRIPTION' key. */
260 RtlInitUnicodeString(&KeyName
,
261 L
"\\Registry\\Machine\\HARDWARE\\DESCRIPTION");
262 InitializeObjectAttributes (&ObjectAttributes
,
264 OBJ_CASE_INSENSITIVE
,
267 Status
= NtCreateKey (&HardwareKey
,
274 if (!NT_SUCCESS(Status
))
278 NtClose (HardwareKey
);
280 /* Create '\Registry\Machine\HARDWARE\DEVICEMAP' key. */
281 RtlInitUnicodeString (&KeyName
,
282 L
"\\Registry\\Machine\\HARDWARE\\DEVICEMAP");
283 InitializeObjectAttributes (&ObjectAttributes
,
285 OBJ_CASE_INSENSITIVE
,
288 Status
= NtCreateKey (&HardwareKey
,
295 if (!NT_SUCCESS(Status
))
299 NtClose (HardwareKey
);
301 /* Create '\Registry\Machine\HARDWARE\RESOURCEMAP' key. */
302 RtlInitUnicodeString(&KeyName
,
303 L
"\\Registry\\Machine\\HARDWARE\\RESOURCEMAP");
304 InitializeObjectAttributes (&ObjectAttributes
,
306 OBJ_CASE_INSENSITIVE
,
309 Status
= NtCreateKey (&HardwareKey
,
316 if (!NT_SUCCESS(Status
))
320 NtClose (HardwareKey
);
325 /* Check the hive magic */
326 if (strncmp (ChunkBase
, "regf", 4))
328 DPRINT1 ("Found invalid '%.*s' magic\n", 4, ChunkBase
);
332 DPRINT ("Found '%.*s' magic\n", 4, ChunkBase
);
333 DPRINT ("ChunkBase %lx ChunkSize %lu\n", ChunkBase
, ChunkSize
);
335 /* Import the binary system hive (volatile, offset-based, permanent) */
336 if (!CmImportBinaryHive (ChunkBase
, ChunkSize
, HIVE_NO_FILE
, &RegistryHive
))
338 DPRINT1 ("CmiImportBinaryHive() failed\n", Status
);
342 /* Attach it to the machine key */
343 RtlInitUnicodeString (&KeyName
,
344 L
"\\Registry\\Machine\\HARDWARE");
345 InitializeObjectAttributes (&ObjectAttributes
,
347 OBJ_CASE_INSENSITIVE
,
350 Status
= CmiConnectHive (&ObjectAttributes
,
352 if (!NT_SUCCESS(Status
))
354 DPRINT1 ("CmiConnectHive() failed (Status %lx)\n", Status
);
355 // CmiRemoveRegistryHive(RegistryHive);
359 /* Set the hive filename */
360 RtlInitUnicodeString (&RegistryHive
->HiveFileName
,
363 /* Set the log filename */
364 RtlInitUnicodeString (&RegistryHive
->LogFileName
,
367 CmiHardwareHiveImported
= TRUE
;