10 #define REG_ROOT_KEY_NAME L"\\Registry"
11 #define REG_MACHINE_KEY_NAME L"\\Registry\\Machine"
12 #define REG_HARDWARE_KEY_NAME L"\\Registry\\Machine\\HARDWARE"
13 #define REG_DESCRIPTION_KEY_NAME L"\\Registry\\Machine\\HARDWARE\\DESCRIPTION"
14 #define REG_DEVICEMAP_KEY_NAME L"\\Registry\\Machine\\HARDWARE\\DEVICEMAP"
15 #define REG_RESOURCEMAP_KEY_NAME L"\\Registry\\Machine\\HARDWARE\\RESOURCEMAP"
16 #define REG_CLASSES_KEY_NAME L"\\Registry\\Machine\\Software\\Classes"
17 #define REG_SYSTEM_KEY_NAME L"\\Registry\\Machine\\System"
18 #define REG_SOFTWARE_KEY_NAME L"\\Registry\\Machine\\Software"
19 #define REG_SAM_KEY_NAME L"\\Registry\\Machine\\Sam"
20 #define REG_SEC_KEY_NAME L"\\Registry\\Machine\\Security"
21 #define REG_USER_KEY_NAME L"\\Registry\\User"
22 #define REG_DEFAULT_USER_KEY_NAME L"\\Registry\\User\\.Default"
23 #define REG_CURRENT_USER_KEY_NAME L"\\Registry\\User\\CurrentUser"
25 #define SYSTEM_REG_FILE L"\\SystemRoot\\System32\\Config\\SYSTEM"
26 #define SYSTEM_LOG_FILE L"\\SystemRoot\\System32\\Config\\SYSTEM.log"
27 #define SOFTWARE_REG_FILE L"\\SystemRoot\\System32\\Config\\SOFTWARE"
28 #define DEFAULT_USER_REG_FILE L"\\SystemRoot\\System32\\Config\\DEFAULT"
29 #define SAM_REG_FILE L"\\SystemRoot\\System32\\Config\\SAM"
30 #define SEC_REG_FILE L"\\SystemRoot\\System32\\Config\\SECURITY"
32 #define REG_SYSTEM_FILE_NAME L"\\SYSTEM"
33 #define REG_SOFTWARE_FILE_NAME L"\\SOFTWARE"
34 #define REG_DEFAULT_USER_FILE_NAME L"\\DEFAULT"
35 #define REG_SAM_FILE_NAME L"\\SAM"
36 #define REG_SEC_FILE_NAME L"\\SECURITY"
38 #define REG_BLOCK_SIZE 4096
39 #define REG_HBIN_DATA_OFFSET 32
40 #define REG_BIN_ID 0x6e696268
41 #define REG_INIT_BLOCK_LIST_SIZE 32
42 #define REG_INIT_HASH_TABLE_SIZE 3
43 #define REG_EXTEND_HASH_TABLE_SIZE 4
44 #define REG_VALUE_LIST_CELL_MULTIPLE 4
45 #define REG_KEY_CELL_ID 0x6b6e
46 #define REG_HASH_TABLE_BLOCK_ID 0x666c
47 #define REG_VALUE_CELL_ID 0x6b76
48 #define REG_HIVE_ID 0x66676572
51 // BLOCK_OFFSET = offset in file after header block
52 typedef ULONG BLOCK_OFFSET
;
54 /* header for registry hive file : */
55 typedef struct _HIVE_HEADER
57 /* Hive identifier "regf" (0x66676572) */
66 /* When this hive file was last modified */
67 FILETIME DateModified
;
69 /* Registry format version ? (1?) */
72 /* Registry format version ? (3?) */
75 /* Registry format version ? (0?) */
78 /* Registry format version ? (1?) */
81 /* Offset into file from the byte after the end of the base block.
82 If the hive is volatile, this is the actual pointer to the KEY_CELL */
83 BLOCK_OFFSET RootKeyCell
;
85 /* Size of each hive block ? */
91 /* Name of hive file */
97 /* Checksum of first 0x200 bytes */
99 } __attribute__((packed
)) HIVE_HEADER
, *PHIVE_HEADER
;
103 /* Bin identifier "hbin" (0x6E696268) */
106 /* Block offset of this bin */
107 BLOCK_OFFSET BlockOffset
;
109 /* Size in bytes, multiple of the block size (4KB) */
115 /* When this bin was last modified */
116 FILETIME DateModified
;
120 } __attribute__((packed
)) HBIN
, *PHBIN
;
122 typedef struct _CELL_HEADER
124 /* <0 if used, >0 if free */
126 } __attribute__((packed
)) CELL_HEADER
, *PCELL_HEADER
;
128 typedef struct _KEY_CELL
130 /* Size of this cell */
133 /* Key cell identifier "kn" (0x6b6e) */
139 /* Time of last flush */
140 FILETIME LastWriteTime
;
145 /* Block offset of parent key cell */
146 BLOCK_OFFSET ParentKeyOffset
;
148 /* Count of sub keys for the key in this key cell */
149 ULONG NumberOfSubKeys
;
154 /* Block offset of has table for FIXME: subkeys/values? */
155 BLOCK_OFFSET HashTableOffset
;
160 /* Count of values contained in this key cell */
161 ULONG NumberOfValues
;
163 /* Block offset of VALUE_LIST_CELL */
164 BLOCK_OFFSET ValuesOffset
;
166 /* Block offset of security cell */
167 BLOCK_OFFSET SecurityKeyOffset
;
169 /* Block offset of registry key class */
170 BLOCK_OFFSET ClassNameOffset
;
175 /* Size in bytes of key name */
178 /* Size of class name in bytes */
181 /* Name of key (not zero terminated) */
183 } __attribute__((packed
)) KEY_CELL
, *PKEY_CELL
;
185 /* KEY_CELL.Flags constants */
186 #define REG_KEY_ROOT_CELL 0x0C
187 #define REG_KEY_LINK_CELL 0x10
188 #define REG_KEY_NAME_PACKED 0x20
195 * packed name: four letters of value's name
198 typedef struct _HASH_RECORD
200 BLOCK_OFFSET KeyOffset
;
202 } __attribute__((packed
)) HASH_RECORD
, *PHASH_RECORD
;
204 typedef struct _HASH_TABLE_CELL
208 USHORT HashTableSize
;
209 HASH_RECORD Table
[0];
210 } __attribute__((packed
)) HASH_TABLE_CELL
, *PHASH_TABLE_CELL
;
213 typedef struct _VALUE_LIST_CELL
216 BLOCK_OFFSET Values
[0];
217 } __attribute__((packed
)) VALUE_LIST_CELL
, *PVALUE_LIST_CELL
;
219 typedef struct _VALUE_CELL
223 USHORT NameSize
; // length of Name
224 LONG DataSize
; // length of datas in the cell pointed by DataOffset
225 BLOCK_OFFSET DataOffset
;// datas are here if high bit of DataSize is set
229 UCHAR Name
[0]; /* warning : not zero terminated */
230 } __attribute__((packed
)) VALUE_CELL
, *PVALUE_CELL
;
232 /* VALUE_CELL.Flags constants */
233 #define REG_VALUE_NAME_PACKED 0x0001
236 typedef struct _DATA_CELL
240 } __attribute__((packed
)) DATA_CELL
, *PDATA_CELL
;
242 typedef struct _REGISTRY_HIVE
246 UNICODE_STRING HiveFileName
;
247 UNICODE_STRING LogFileName
;
249 PHIVE_HEADER HiveHeader
;
255 PCELL_HEADER
*FreeList
;
256 BLOCK_OFFSET
*FreeListOffset
;
257 ERESOURCE HiveResource
;
260 RTL_BITMAP DirtyBitMap
;
262 } REGISTRY_HIVE
, *PREGISTRY_HIVE
;
264 /* REGISTRY_HIVE.Flags constants */
265 /* When set, the hive uses pointers instead of offsets. */
266 #define HIVE_POINTER 0x00000001
268 /* When set, the hive is not backed by a file.
269 Therefore, it can not be flushed to disk. */
270 #define HIVE_NO_FILE 0x00000002
272 /* When set, a modified (dirty) hive is not synchronized automatically.
273 Explicit synchronization (save/flush) works. */
274 #define HIVE_NO_SYNCH 0x00000004
276 #define IsPointerHive(Hive) ((Hive)->Flags & HIVE_POINTER)
277 #define IsNoFileHive(Hive) ((Hive)->Flags & HIVE_NO_FILE)
278 #define IsNoSynchHive(Hive) ((Hive)->Flags & HIVE_NO_SYNCH)
281 #define IsFreeCell(Cell)(Cell->CellSize >= 0)
282 #define IsUsedCell(Cell)(Cell->CellSize < 0)
285 /* KEY_OBJECT.Flags */
287 /* When set, the key is scheduled for deletion, and all
288 attempts to access the key must not succeed */
289 #define KO_MARKED_FOR_DELETE 0x00000001
292 /* Type defining the Object Manager Key Object */
293 typedef struct _KEY_OBJECT
295 /* Fields used by the Object Manager */
305 /* Registry hive the key belongs to */
306 PREGISTRY_HIVE RegistryHive
;
308 /* Block offset of the key cell this key belongs in */
309 BLOCK_OFFSET BlockOffset
;
311 /* KEY_CELL this key belong in */
314 /* Link to the parent KEY_OBJECT for this key */
315 struct _KEY_OBJECT
*ParentKey
;
317 /* Subkeys loaded in SubKeys */
318 ULONG NumberOfSubKeys
;
320 /* Space allocated in SubKeys */
323 /* List of subkeys loaded */
324 struct _KEY_OBJECT
**SubKeys
;
325 } KEY_OBJECT
, *PKEY_OBJECT
;
327 /* Bits 31-22 (top 10 bits) of the cell index is the directory index */
328 #define CmiDirectoryIndex(CellIndex)(CellIndex & 0xffc000000)
329 /* Bits 21-12 (middle 10 bits) of the cell index is the table index */
330 #define CmiTableIndex(Cellndex)(CellIndex & 0x003ff000)
331 /* Bits 11-0 (bottom 12 bits) of the cell index is the byte offset */
332 #define CmiByteOffset(Cellndex)(CellIndex & 0x00000fff)
335 extern BOOLEAN CmiDoVerify
;
336 extern PREGISTRY_HIVE CmiVolatileHive
;
337 extern POBJECT_TYPE CmiKeyType
;
338 extern KSPIN_LOCK CmiKeyListLock
;
340 extern LIST_ENTRY CmiHiveListHead
;
341 extern ERESOURCE CmiHiveListLock
;
345 CmiVerifyBinCell(PHBIN BinCell
);
347 CmiVerifyKeyCell(PKEY_CELL KeyCell
);
349 CmiVerifyRootKeyCell(PKEY_CELL RootKeyCell
);
351 CmiVerifyKeyObject(PKEY_OBJECT KeyObject
);
353 CmiVerifyRegistryHive(PREGISTRY_HIVE RegistryHive
);
356 #define VERIFY_BIN_CELL CmiVerifyBinCell
357 #define VERIFY_KEY_CELL CmiVerifyKeyCell
358 #define VERIFY_ROOT_KEY_CELL CmiVerifyRootKeyCell
359 #define VERIFY_VALUE_CELL CmiVerifyValueCell
360 #define VERIFY_VALUE_LIST_CELL CmiVerifyValueListCell
361 #define VERIFY_KEY_OBJECT CmiVerifyKeyObject
362 #define VERIFY_REGISTRY_HIVE CmiVerifyRegistryHive
364 #define VERIFY_BIN_CELL(x)
365 #define VERIFY_KEY_CELL(x)
366 #define VERIFY_ROOT_KEY_CELL(x)
367 #define VERIFY_VALUE_CELL(x)
368 #define VERIFY_VALUE_LIST_CELL(x)
369 #define VERIFY_KEY_OBJECT(x)
370 #define VERIFY_REGISTRY_HIVE(x)
374 CmiObjectParse(IN PVOID ParsedObject
,
375 OUT PVOID
*NextObject
,
376 IN PUNICODE_STRING FullPath
,
381 CmiObjectCreate(PVOID ObjectBody
,
384 POBJECT_ATTRIBUTES ObjectAttributes
);
387 CmiObjectDelete(PVOID DeletedObject
);
390 CmiObjectSecurity(PVOID ObjectBody
,
391 SECURITY_OPERATION_CODE OperationCode
,
392 SECURITY_INFORMATION SecurityInformation
,
393 PSECURITY_DESCRIPTOR SecurityDescriptor
,
394 PULONG BufferLength
);
397 CmiObjectQueryName (PVOID ObjectBody
,
398 POBJECT_NAME_INFORMATION ObjectNameInfo
,
400 PULONG ReturnLength
);
403 CmiImportHiveBins(PREGISTRY_HIVE Hive
,
407 CmiFreeHiveBins(PREGISTRY_HIVE Hive
);
410 CmiCreateHiveFreeCellList(PREGISTRY_HIVE Hive
);
413 CmiFreeHiveFreeCellList(PREGISTRY_HIVE Hive
);
416 CmiCreateHiveBitmap(PREGISTRY_HIVE Hive
);
420 CmiAddKeyToList(IN PKEY_OBJECT ParentKey
,
421 IN PKEY_OBJECT NewKey
);
424 CmiRemoveKeyFromList(IN PKEY_OBJECT NewKey
);
427 CmiScanKeyList(IN PKEY_OBJECT Parent
,
428 IN PUNICODE_STRING KeyName
,
429 IN ULONG Attributes
);
432 CmiCreateVolatileHive(PREGISTRY_HIVE
*RegistryHive
);
435 CmiLoadHive(POBJECT_ATTRIBUTES KeyObjectAttributes
,
436 PUNICODE_STRING FileName
,
440 CmiRemoveRegistryHive(PREGISTRY_HIVE RegistryHive
);
443 CmiFlushRegistryHive(PREGISTRY_HIVE RegistryHive
);
446 CmiGetMaxNameLength(IN PREGISTRY_HIVE RegistryHive
,
447 IN PKEY_CELL KeyCell
);
450 CmiGetMaxClassLength(IN PREGISTRY_HIVE RegistryHive
,
451 IN PKEY_CELL KeyCell
);
454 CmiGetMaxValueNameLength(IN PREGISTRY_HIVE RegistryHive
,
455 IN PKEY_CELL KeyCell
);
458 CmiGetMaxValueDataLength(IN PREGISTRY_HIVE RegistryHive
,
459 IN PKEY_CELL KeyCell
);
462 CmiScanForSubKey(IN PREGISTRY_HIVE RegistryHive
,
463 IN PKEY_CELL KeyCell
,
464 OUT PKEY_CELL
*SubKeyCell
,
465 OUT BLOCK_OFFSET
*BlockOffset
,
466 IN PUNICODE_STRING KeyName
,
467 IN ACCESS_MASK DesiredAccess
,
468 IN ULONG Attributes
);
471 CmiAddSubKey(IN PREGISTRY_HIVE RegistryHive
,
472 IN PKEY_OBJECT Parent
,
473 OUT PKEY_OBJECT SubKey
,
474 IN PUNICODE_STRING SubKeyName
,
476 IN PUNICODE_STRING Class
,
477 IN ULONG CreateOptions
);
480 CmiRemoveSubKey(IN PREGISTRY_HIVE RegistryHive
,
481 IN PKEY_OBJECT Parent
,
482 IN PKEY_OBJECT SubKey
);
485 CmiScanKeyForValue(IN PREGISTRY_HIVE RegistryHive
,
486 IN PKEY_CELL KeyCell
,
487 IN PUNICODE_STRING ValueName
,
488 OUT PVALUE_CELL
*ValueCell
,
489 OUT BLOCK_OFFSET
*VBOffset
);
492 CmiGetValueFromKeyByIndex(IN PREGISTRY_HIVE RegistryHive
,
493 IN PKEY_CELL KeyCell
,
495 OUT PVALUE_CELL
*ValueCell
);
498 CmiAddValueToKey(IN PREGISTRY_HIVE RegistryHive
,
499 IN PKEY_CELL KeyCell
,
500 IN PUNICODE_STRING ValueName
,
501 OUT PVALUE_CELL
*pValueCell
,
502 OUT BLOCK_OFFSET
*pVBOffset
);
505 CmiDeleteValueFromKey(IN PREGISTRY_HIVE RegistryHive
,
506 IN PKEY_CELL KeyCell
,
507 IN BLOCK_OFFSET KeyCellOffset
,
508 IN PUNICODE_STRING ValueName
);
511 CmiAllocateHashTableBlock(IN PREGISTRY_HIVE RegistryHive
,
512 OUT PHASH_TABLE_CELL
*HashBlock
,
513 OUT BLOCK_OFFSET
*HBOffset
,
514 IN ULONG HashTableSize
);
517 CmiGetKeyFromHashByIndex(PREGISTRY_HIVE RegistryHive
,
518 PHASH_TABLE_CELL HashBlock
,
522 CmiAddKeyToHashTable(PREGISTRY_HIVE RegistryHive
,
523 PHASH_TABLE_CELL HashBlock
,
524 PKEY_CELL NewKeyCell
,
525 BLOCK_OFFSET NKBOffset
);
528 CmiRemoveKeyFromHashTable(PREGISTRY_HIVE RegistryHive
,
529 PHASH_TABLE_CELL HashBlock
,
530 BLOCK_OFFSET NKBOffset
);
533 CmiAllocateValueCell(IN PREGISTRY_HIVE RegistryHive
,
534 OUT PVALUE_CELL
*ValueCell
,
535 OUT BLOCK_OFFSET
*VBOffset
,
536 IN PUNICODE_STRING ValueName
);
539 CmiDestroyValueCell(PREGISTRY_HIVE RegistryHive
,
540 PVALUE_CELL ValueCell
,
541 BLOCK_OFFSET VBOffset
);
544 CmiAllocateBlock(PREGISTRY_HIVE RegistryHive
,
547 BLOCK_OFFSET
* pBlockOffset
);
550 CmiDestroyBlock(PREGISTRY_HIVE RegistryHive
,
552 BLOCK_OFFSET Offset
);
555 CmiGetBlock(PREGISTRY_HIVE RegistryHive
,
556 BLOCK_OFFSET BlockOffset
,
560 CmiMarkBlockDirty(PREGISTRY_HIVE RegistryHive
,
561 BLOCK_OFFSET BlockOffset
);
564 CmiMarkBinDirty(PREGISTRY_HIVE RegistryHive
,
565 BLOCK_OFFSET BinOffset
);
568 CmiAddFree(PREGISTRY_HIVE RegistryHive
,
569 PCELL_HEADER FreeBlock
,
570 BLOCK_OFFSET FreeOffset
,
571 BOOLEAN MergeFreeBlocks
);
574 CmiConnectHive(POBJECT_ATTRIBUTES KeyObjectAttributes
,
575 PREGISTRY_HIVE RegistryHive
);
578 CmiDisconnectHive (POBJECT_ATTRIBUTES KeyObjectAttributes
,
579 PREGISTRY_HIVE
*RegistryHive
);
582 CmiInitHives(BOOLEAN SetupBoot
);
585 CmiGetPackedNameLength(IN PUNICODE_STRING Name
,
586 OUT PBOOLEAN Packable
);
589 CmiComparePackedNames(IN PUNICODE_STRING Name
,
591 IN USHORT NameBufferSize
,
592 IN BOOLEAN NamePacked
);
595 CmiCopyPackedName(PWCHAR NameBuffer
,
596 PCHAR PackedNameBuffer
,
597 ULONG PackedNameSize
);
600 CmiCompareHash(PUNICODE_STRING KeyName
,
604 CmiCompareHashI(PUNICODE_STRING KeyName
,
608 CmiCompareKeyNames(PUNICODE_STRING KeyName
,
612 CmiCompareKeyNamesI(PUNICODE_STRING KeyName
,
619 #endif /*__INCLUDE_CM_H*/