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_INIT_BLOCK_LIST_SIZE 32
41 #define REG_INIT_HASH_TABLE_SIZE 3
42 #define REG_EXTEND_HASH_TABLE_SIZE 4
43 #define REG_VALUE_LIST_CELL_MULTIPLE 4
45 #define REG_HIVE_ID 0x66676572
46 #define REG_BIN_ID 0x6e696268
47 #define REG_KEY_CELL_ID 0x6b6e
48 #define REG_HASH_TABLE_CELL_ID 0x666c
49 #define REG_VALUE_CELL_ID 0x6b76
50 #define REG_SECURITY_CELL_ID 0x6b73
53 // BLOCK_OFFSET = offset in file after header block
54 typedef ULONG BLOCK_OFFSET
, *PBLOCK_OFFSET
;
58 /* header for registry hive file : */
59 typedef struct _HIVE_HEADER
61 /* Hive identifier "regf" (0x66676572) */
70 /* When this hive file was last modified */
71 LARGE_INTEGER DateModified
;
73 /* Registry format major version (1) */
76 /* Registry format minor version (3)
77 Version 3 added fast indexes, version 5 has large value optimizations */
80 /* Registry file type (0 - Primary, 1 - Log) */
83 /* Registry format (1 is the only defined value so far) */
86 /* Offset into file from the byte after the end of the base block.
87 If the hive is volatile, this is the actual pointer to the KEY_CELL */
88 BLOCK_OFFSET RootKeyOffset
;
90 /* Size of each hive block ? */
96 /* Name of hive file */
101 /* Checksum of first 0x200 bytes */
103 } HIVE_HEADER
, *PHIVE_HEADER
;
105 typedef struct _BIN_HEADER
107 /* Bin identifier "hbin" (0x6E696268) */
110 /* Block offset of this bin */
111 BLOCK_OFFSET BinOffset
;
113 /* Size in bytes, multiple of the block size (4KB) */
118 /* When this bin was last modified */
119 LARGE_INTEGER DateModified
;
121 /* ? (In-memory only) */
125 typedef struct _CELL_HEADER
127 /* <0 if used, >0 if free */
129 } CELL_HEADER
, *PCELL_HEADER
;
131 typedef struct _KEY_CELL
133 /* Size of this cell */
136 /* Key cell identifier "kn" (0x6b6e) */
142 /* Time of last flush */
143 LARGE_INTEGER LastWriteTime
;
148 /* Block offset of parent key cell */
149 BLOCK_OFFSET ParentKeyOffset
;
151 /* Count of sub keys for the key in this key cell */
152 ULONG NumberOfSubKeys
;
157 /* Block offset of has table for FIXME: subkeys/values? */
158 BLOCK_OFFSET HashTableOffset
;
163 /* Count of values contained in this key cell */
164 ULONG NumberOfValues
;
166 /* Block offset of VALUE_LIST_CELL */
167 BLOCK_OFFSET ValueListOffset
;
169 /* Block offset of security cell */
170 BLOCK_OFFSET SecurityKeyOffset
;
172 /* Block offset of registry key class */
173 BLOCK_OFFSET ClassNameOffset
;
178 /* Size in bytes of key name */
181 /* Size of class name in bytes */
184 /* Name of key (not zero terminated) */
186 } KEY_CELL
, *PKEY_CELL
;
188 /* KEY_CELL.Flags constants */
189 #define REG_KEY_ROOT_CELL 0x0C
190 #define REG_KEY_LINK_CELL 0x10
191 #define REG_KEY_NAME_PACKED 0x20
197 * packed name: four letters of value's name
200 typedef struct _HASH_RECORD
202 BLOCK_OFFSET KeyOffset
;
204 } HASH_RECORD
, *PHASH_RECORD
;
206 typedef struct _HASH_TABLE_CELL
210 USHORT HashTableSize
;
211 HASH_RECORD Table
[0];
212 } HASH_TABLE_CELL
, *PHASH_TABLE_CELL
;
215 typedef struct _VALUE_LIST_CELL
218 BLOCK_OFFSET ValueOffset
[0];
219 } VALUE_LIST_CELL
, *PVALUE_LIST_CELL
;
221 typedef struct _VALUE_CELL
225 USHORT NameSize
; // length of Name
226 ULONG DataSize
; // length of datas in the cell pointed by DataOffset
227 BLOCK_OFFSET DataOffset
;// datas are here if high bit of DataSize is set
231 UCHAR Name
[0]; /* warning : not zero terminated */
232 } VALUE_CELL
, *PVALUE_CELL
;
234 /* VALUE_CELL.Flags constants */
235 #define REG_VALUE_NAME_PACKED 0x0001
237 /* VALUE_CELL.DataSize mask constants */
238 #define REG_DATA_SIZE_MASK 0x7FFFFFFF
239 #define REG_DATA_IN_OFFSET 0x80000000
242 typedef struct _SECURITY_CELL
247 BLOCK_OFFSET PrevSecurityCell
;
248 BLOCK_OFFSET NextSecurityCell
;
252 } SECURITY_CELL
, *PSECURITY_CELL
;
255 typedef struct _DATA_CELL
259 } DATA_CELL
, *PDATA_CELL
;
264 typedef struct _BLOCK_LIST_ENTRY
268 } BLOCK_LIST_ENTRY
, *PBLOCK_LIST_ENTRY
;
271 typedef struct _REGISTRY_HIVE
275 UNICODE_STRING HiveFileName
;
276 UNICODE_STRING LogFileName
;
278 PHIVE_HEADER HiveHeader
;
281 PBLOCK_LIST_ENTRY BlockList
;
284 PCELL_HEADER
*FreeList
;
285 BLOCK_OFFSET
*FreeListOffset
;
287 PSECURITY_CELL RootSecurityCell
;
290 RTL_BITMAP DirtyBitMap
;
292 } REGISTRY_HIVE
, *PREGISTRY_HIVE
;
294 /* REGISTRY_HIVE.Flags constants */
295 /* When set, the hive uses pointers instead of offsets. */
296 #define HIVE_POINTER 0x00000001
298 /* When set, the hive is not backed by a file.
299 Therefore, it can not be flushed to disk. */
300 #define HIVE_NO_FILE 0x00000002
302 /* When set, a modified (dirty) hive is not synchronized automatically.
303 Explicit synchronization (save/flush) works. */
304 #define HIVE_NO_SYNCH 0x00000004
306 #define IsPointerHive(Hive) ((Hive)->Flags & HIVE_POINTER)
307 #define IsNoFileHive(Hive) ((Hive)->Flags & HIVE_NO_FILE)
308 #define IsNoSynchHive(Hive) ((Hive)->Flags & HIVE_NO_SYNCH)
311 #define IsFreeCell(Cell)(Cell->CellSize >= 0)
312 #define IsUsedCell(Cell)(Cell->CellSize < 0)
315 /* KEY_OBJECT.Flags */
317 /* When set, the key is scheduled for deletion, and all
318 attempts to access the key must not succeed */
319 #define KO_MARKED_FOR_DELETE 0x00000001
322 /* Type defining the Object Manager Key Object */
323 typedef struct _KEY_OBJECT
325 /* Fields used by the Object Manager */
335 /* Registry hive the key belongs to */
336 PREGISTRY_HIVE RegistryHive
;
338 /* Block offset of the key cell this key belongs in */
339 BLOCK_OFFSET KeyCellOffset
;
341 /* KEY_CELL this key belong in */
344 /* Link to the parent KEY_OBJECT for this key */
345 struct _KEY_OBJECT
*ParentKey
;
347 /* Subkeys loaded in SubKeys */
348 ULONG NumberOfSubKeys
;
350 /* Space allocated in SubKeys */
353 /* List of subkeys loaded */
354 struct _KEY_OBJECT
**SubKeys
;
356 /* List entry into the global key object list */
357 LIST_ENTRY ListEntry
;
359 /* Time stamp for the last access by the parse routine */
362 /* List entry for connected hives */
364 } KEY_OBJECT
, *PKEY_OBJECT
;
366 /* Bits 31-22 (top 10 bits) of the cell index is the directory index */
367 #define CmiDirectoryIndex(CellIndex)(CellIndex & 0xffc000000)
368 /* Bits 21-12 (middle 10 bits) of the cell index is the table index */
369 #define CmiTableIndex(Cellndex)(CellIndex & 0x003ff000)
370 /* Bits 11-0 (bottom 12 bits) of the cell index is the byte offset */
371 #define CmiByteOffset(Cellndex)(CellIndex & 0x00000fff)
374 extern BOOLEAN CmiDoVerify
;
375 extern PREGISTRY_HIVE CmiVolatileHive
;
376 extern POBJECT_TYPE CmiKeyType
;
377 extern KSPIN_LOCK CmiKeyListLock
;
379 extern LIST_ENTRY CmiHiveListHead
;
381 extern ERESOURCE CmiRegistryLock
;
384 /* Registry Callback Function */
385 typedef NTSTATUS (STDCALL
*PEX_CALLBACK_FUNCTION
) (
386 IN PVOID CallbackContext
,
387 IN REG_NOTIFY_CLASS Argument1
,
391 typedef struct _REGISTRY_CALLBACK
393 LIST_ENTRY ListEntry
;
394 EX_RUNDOWN_REF RundownRef
;
395 PEX_CALLBACK_FUNCTION Function
;
397 LARGE_INTEGER Cookie
;
398 BOOLEAN PendingDelete
;
399 } REGISTRY_CALLBACK
, *PREGISTRY_CALLBACK
;
402 CmiCallRegisteredCallbacks(IN REG_NOTIFY_CLASS Argument1
,
406 CmiVerifyBinHeader(PHBIN BinHeader
);
408 CmiVerifyKeyCell(PKEY_CELL KeyCell
);
410 CmiVerifyRootKeyCell(PKEY_CELL RootKeyCell
);
412 CmiVerifyKeyObject(PKEY_OBJECT KeyObject
);
414 CmiVerifyRegistryHive(PREGISTRY_HIVE RegistryHive
);
417 #define VERIFY_BIN_HEADER CmiVerifyBinHeader
418 #define VERIFY_KEY_CELL CmiVerifyKeyCell
419 #define VERIFY_ROOT_KEY_CELL CmiVerifyRootKeyCell
420 #define VERIFY_VALUE_CELL CmiVerifyValueCell
421 #define VERIFY_VALUE_LIST_CELL CmiVerifyValueListCell
422 #define VERIFY_KEY_OBJECT CmiVerifyKeyObject
423 #define VERIFY_REGISTRY_HIVE CmiVerifyRegistryHive
425 #define VERIFY_BIN_HEADER(x)
426 #define VERIFY_KEY_CELL(x)
427 #define VERIFY_ROOT_KEY_CELL(x)
428 #define VERIFY_VALUE_CELL(x)
429 #define VERIFY_VALUE_LIST_CELL(x)
430 #define VERIFY_KEY_OBJECT(x)
431 #define VERIFY_REGISTRY_HIVE(x)
435 CmRegisterCallback(IN PEX_CALLBACK_FUNCTION Function
,
437 IN OUT PLARGE_INTEGER Cookie
441 CmUnRegisterCallback(IN LARGE_INTEGER Cookie
);
444 CmiObjectParse(IN PVOID ParsedObject
,
446 IN OUT PACCESS_STATE AccessState
,
447 IN KPROCESSOR_MODE AccessMode
,
449 IN OUT PUNICODE_STRING FullPath
,
450 IN OUT PUNICODE_STRING RemainingName
,
451 IN OUT PVOID Context OPTIONAL
,
452 IN PSECURITY_QUALITY_OF_SERVICE SecurityQos OPTIONAL
,
453 OUT PVOID
*NextObject
);
456 CmiObjectDelete(PVOID DeletedObject
);
459 CmiObjectSecurity(PVOID ObjectBody
,
460 SECURITY_OPERATION_CODE OperationCode
,
461 SECURITY_INFORMATION SecurityInformation
,
462 PSECURITY_DESCRIPTOR SecurityDescriptor
,
464 PSECURITY_DESCRIPTOR
*OldSecurityDescriptor
,
466 PGENERIC_MAPPING GenericMapping
);
469 CmiObjectQueryName (PVOID ObjectBody
,
470 IN BOOLEAN HasObjectName
,
471 POBJECT_NAME_INFORMATION ObjectNameInfo
,
474 IN KPROCESSOR_MODE PreviousMode
);
477 CmiImportHiveBins(PREGISTRY_HIVE Hive
,
481 CmiFreeHiveBins(PREGISTRY_HIVE Hive
);
484 CmiCreateHiveFreeCellList(PREGISTRY_HIVE Hive
);
487 CmiFreeHiveFreeCellList(PREGISTRY_HIVE Hive
);
490 CmiCreateHiveBitmap(PREGISTRY_HIVE Hive
);
494 CmiAddKeyToList(IN PKEY_OBJECT ParentKey
,
495 IN PKEY_OBJECT NewKey
);
498 CmiRemoveKeyFromList(IN PKEY_OBJECT NewKey
);
501 CmiScanKeyList(IN PKEY_OBJECT Parent
,
502 IN PUNICODE_STRING KeyName
,
504 PKEY_OBJECT
* ReturnedObject
);
507 CmiCreateVolatileHive(PREGISTRY_HIVE
*RegistryHive
);
510 CmiLoadHive(POBJECT_ATTRIBUTES KeyObjectAttributes
,
511 PUNICODE_STRING FileName
,
515 CmiRemoveRegistryHive(PREGISTRY_HIVE RegistryHive
);
518 CmiFlushRegistryHive(PREGISTRY_HIVE RegistryHive
);
521 CmiGetNumberOfSubKeys(PKEY_OBJECT KeyObject
);
524 CmiGetMaxNameLength(IN PKEY_OBJECT KeyObject
);
527 CmiGetMaxClassLength(IN PKEY_OBJECT KeyObject
);
530 CmiGetMaxValueNameLength(IN PREGISTRY_HIVE RegistryHive
,
531 IN PKEY_CELL KeyCell
);
534 CmiGetMaxValueDataLength(IN PREGISTRY_HIVE RegistryHive
,
535 IN PKEY_CELL KeyCell
);
538 CmiScanForSubKey(IN PREGISTRY_HIVE RegistryHive
,
539 IN PKEY_CELL KeyCell
,
540 OUT PKEY_CELL
*SubKeyCell
,
541 OUT BLOCK_OFFSET
*BlockOffset
,
542 IN PUNICODE_STRING KeyName
,
543 IN ACCESS_MASK DesiredAccess
,
544 IN ULONG Attributes
);
547 CmiAddSubKey(IN PREGISTRY_HIVE RegistryHive
,
548 IN PKEY_OBJECT ParentKey
,
549 OUT PKEY_OBJECT SubKey
,
550 IN PUNICODE_STRING SubKeyName
,
552 IN PUNICODE_STRING Class
,
553 IN ULONG CreateOptions
);
556 CmiRemoveSubKey(IN PREGISTRY_HIVE RegistryHive
,
557 IN PKEY_OBJECT Parent
,
558 IN PKEY_OBJECT SubKey
);
561 CmiScanKeyForValue(IN PREGISTRY_HIVE RegistryHive
,
562 IN PKEY_CELL KeyCell
,
563 IN PUNICODE_STRING ValueName
,
564 OUT PVALUE_CELL
*ValueCell
,
565 OUT BLOCK_OFFSET
*VBOffset
);
568 CmiGetValueFromKeyByIndex(IN PREGISTRY_HIVE RegistryHive
,
569 IN PKEY_CELL KeyCell
,
571 OUT PVALUE_CELL
*ValueCell
);
574 CmiAddValueToKey(IN PREGISTRY_HIVE RegistryHive
,
575 IN PKEY_CELL KeyCell
,
576 IN BLOCK_OFFSET KeyCellOffset
,
577 IN PUNICODE_STRING ValueName
,
578 OUT PVALUE_CELL
*pValueCell
,
579 OUT BLOCK_OFFSET
*pValueCellOffset
);
582 CmiDeleteValueFromKey(IN PREGISTRY_HIVE RegistryHive
,
583 IN PKEY_CELL KeyCell
,
584 IN BLOCK_OFFSET KeyCellOffset
,
585 IN PUNICODE_STRING ValueName
);
588 CmiAllocateHashTableCell(IN PREGISTRY_HIVE RegistryHive
,
589 OUT PHASH_TABLE_CELL
*HashBlock
,
590 OUT BLOCK_OFFSET
*HBOffset
,
591 IN ULONG HashTableSize
);
594 CmiGetKeyFromHashByIndex(PREGISTRY_HIVE RegistryHive
,
595 PHASH_TABLE_CELL HashBlock
,
599 CmiAddKeyToHashTable(PREGISTRY_HIVE RegistryHive
,
600 PHASH_TABLE_CELL HashCell
,
601 BLOCK_OFFSET HashCellOffset
,
602 PKEY_CELL NewKeyCell
,
603 BLOCK_OFFSET NKBOffset
);
606 CmiRemoveKeyFromHashTable(PREGISTRY_HIVE RegistryHive
,
607 PHASH_TABLE_CELL HashBlock
,
608 BLOCK_OFFSET NKBOffset
);
611 CmiAllocateValueCell(IN PREGISTRY_HIVE RegistryHive
,
612 OUT PVALUE_CELL
*ValueCell
,
613 OUT BLOCK_OFFSET
*VBOffset
,
614 IN PUNICODE_STRING ValueName
);
617 CmiDestroyValueCell(PREGISTRY_HIVE RegistryHive
,
618 PVALUE_CELL ValueCell
,
619 BLOCK_OFFSET VBOffset
);
622 CmiAllocateCell(PREGISTRY_HIVE RegistryHive
,
625 BLOCK_OFFSET
*CellOffset
);
628 CmiDestroyCell(PREGISTRY_HIVE RegistryHive
,
630 BLOCK_OFFSET CellOffset
);
633 CmiGetBin (PREGISTRY_HIVE RegistryHive
,
634 BLOCK_OFFSET CellOffset
);
637 CmiGetCell (PREGISTRY_HIVE RegistryHive
,
638 BLOCK_OFFSET CellOffset
,
642 CmiMarkBlockDirty(PREGISTRY_HIVE RegistryHive
,
643 BLOCK_OFFSET BlockOffset
);
646 CmiMarkBinDirty(PREGISTRY_HIVE RegistryHive
,
647 BLOCK_OFFSET BinOffset
);
650 CmiAddFree(PREGISTRY_HIVE RegistryHive
,
651 PCELL_HEADER FreeBlock
,
652 BLOCK_OFFSET FreeOffset
,
653 BOOLEAN MergeFreeBlocks
);
656 CmiConnectHive(POBJECT_ATTRIBUTES KeyObjectAttributes
,
657 PREGISTRY_HIVE RegistryHive
);
660 CmiDisconnectHive (POBJECT_ATTRIBUTES KeyObjectAttributes
,
661 PREGISTRY_HIVE
*RegistryHive
);
664 CmiInitHives(BOOLEAN SetupBoot
);
667 CmiGetPackedNameLength(IN PUNICODE_STRING Name
,
668 OUT PBOOLEAN Packable
);
671 CmiComparePackedNames(IN PUNICODE_STRING Name
,
672 IN PUCHAR NameBuffer
,
673 IN USHORT NameBufferSize
,
674 IN BOOLEAN NamePacked
);
677 CmiCopyPackedName(PWCHAR NameBuffer
,
678 PUCHAR PackedNameBuffer
,
679 ULONG PackedNameSize
);
682 CmiCompareHash(PUNICODE_STRING KeyName
,
686 CmiCompareHashI(PUNICODE_STRING KeyName
,
690 CmiCompareKeyNames(PUNICODE_STRING KeyName
,
694 CmiCompareKeyNamesI(PUNICODE_STRING KeyName
,
703 CmiCreateTempHive(PREGISTRY_HIVE
*RegistryHive
);
706 CmiCopyKey (PREGISTRY_HIVE DstHive
,
707 PKEY_CELL DstKeyCell
,
708 PREGISTRY_HIVE SrcHive
,
709 PKEY_CELL SrcKeyCell
);
712 CmiSaveTempHive (PREGISTRY_HIVE Hive
,
718 POBJECT_CREATE_INFORMATION ObjectCreateInfo
,
719 PUNICODE_STRING ObjectName
,
720 PVOID
* ReturnedObject
,
721 PUNICODE_STRING RemainingPath
,
722 POBJECT_TYPE ObjectType
,
723 IN PACCESS_STATE AccessState
,
724 IN PVOID ParseContext
726 #endif /*__INCLUDE_CM_H*/