Fixed querying and enumerating the subkeys of HKEY_LOCAL_MACHINE.

This fixes bug #78.

svn path=/trunk/; revision=7936
This commit is contained in:
Eric Kohl 2004-01-31 14:33:01 +00:00
parent faa1a76919
commit c88b53bb8e
4 changed files with 140 additions and 99 deletions

View file

@ -14,10 +14,10 @@
#define REG_DEVICEMAP_KEY_NAME L"\\Registry\\Machine\\HARDWARE\\DEVICEMAP" #define REG_DEVICEMAP_KEY_NAME L"\\Registry\\Machine\\HARDWARE\\DEVICEMAP"
#define REG_RESOURCEMAP_KEY_NAME L"\\Registry\\Machine\\HARDWARE\\RESOURCEMAP" #define REG_RESOURCEMAP_KEY_NAME L"\\Registry\\Machine\\HARDWARE\\RESOURCEMAP"
#define REG_CLASSES_KEY_NAME L"\\Registry\\Machine\\Software\\Classes" #define REG_CLASSES_KEY_NAME L"\\Registry\\Machine\\Software\\Classes"
#define REG_SYSTEM_KEY_NAME L"\\Registry\\Machine\\System" #define REG_SYSTEM_KEY_NAME L"\\Registry\\Machine\\SYSTEM"
#define REG_SOFTWARE_KEY_NAME L"\\Registry\\Machine\\Software" #define REG_SOFTWARE_KEY_NAME L"\\Registry\\Machine\\SOFTWARE"
#define REG_SAM_KEY_NAME L"\\Registry\\Machine\\Sam" #define REG_SAM_KEY_NAME L"\\Registry\\Machine\\SAM"
#define REG_SEC_KEY_NAME L"\\Registry\\Machine\\Security" #define REG_SEC_KEY_NAME L"\\Registry\\Machine\\SECURITY"
#define REG_USER_KEY_NAME L"\\Registry\\User" #define REG_USER_KEY_NAME L"\\Registry\\User"
#define REG_DEFAULT_USER_KEY_NAME L"\\Registry\\User\\.Default" #define REG_DEFAULT_USER_KEY_NAME L"\\Registry\\User\\.Default"
#define REG_CURRENT_USER_KEY_NAME L"\\Registry\\User\\CurrentUser" #define REG_CURRENT_USER_KEY_NAME L"\\Registry\\User\\CurrentUser"
@ -451,6 +451,9 @@ CmiRemoveRegistryHive(PREGISTRY_HIVE RegistryHive);
NTSTATUS NTSTATUS
CmiFlushRegistryHive(PREGISTRY_HIVE RegistryHive); CmiFlushRegistryHive(PREGISTRY_HIVE RegistryHive);
ULONG
CmiGetNumberOfSubKeys(PKEY_OBJECT KeyObject);
ULONG ULONG
CmiGetMaxNameLength(IN PKEY_OBJECT KeyObject); CmiGetMaxNameLength(IN PKEY_OBJECT KeyObject);

View file

@ -1,4 +1,4 @@
/* $Id: import.c,v 1.27 2004/01/05 14:28:19 weiden Exp $ /* $Id: import.c,v 1.28 2004/01/31 14:33:01 ekohl Exp $
* *
* COPYRIGHT: See COPYING in the top level directory * COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS kernel * PROJECT: ReactOS kernel
@ -186,7 +186,7 @@ CmImportSystemHive(PCHAR ChunkBase,
/* Attach it to the machine key */ /* Attach it to the machine key */
RtlInitUnicodeString (&KeyName, RtlInitUnicodeString (&KeyName,
L"\\Registry\\Machine\\System"); REG_SYSTEM_KEY_NAME);
InitializeObjectAttributes (&ObjectAttributes, InitializeObjectAttributes (&ObjectAttributes,
&KeyName, &KeyName,
OBJ_CASE_INSENSITIVE, OBJ_CASE_INSENSITIVE,
@ -234,7 +234,7 @@ CmImportHardwareHive(PCHAR ChunkBase,
{ {
/* Create '\Registry\Machine\HARDWARE' key. */ /* Create '\Registry\Machine\HARDWARE' key. */
RtlInitUnicodeString (&KeyName, RtlInitUnicodeString (&KeyName,
L"\\Registry\\Machine\\HARDWARE"); REG_HARDWARE_KEY_NAME);
InitializeObjectAttributes (&ObjectAttributes, InitializeObjectAttributes (&ObjectAttributes,
&KeyName, &KeyName,
OBJ_CASE_INSENSITIVE, OBJ_CASE_INSENSITIVE,
@ -255,7 +255,7 @@ CmImportHardwareHive(PCHAR ChunkBase,
/* Create '\Registry\Machine\HARDWARE\DESCRIPTION' key. */ /* Create '\Registry\Machine\HARDWARE\DESCRIPTION' key. */
RtlInitUnicodeString(&KeyName, RtlInitUnicodeString(&KeyName,
L"\\Registry\\Machine\\HARDWARE\\DESCRIPTION"); REG_DESCRIPTION_KEY_NAME);
InitializeObjectAttributes (&ObjectAttributes, InitializeObjectAttributes (&ObjectAttributes,
&KeyName, &KeyName,
OBJ_CASE_INSENSITIVE, OBJ_CASE_INSENSITIVE,
@ -276,7 +276,7 @@ CmImportHardwareHive(PCHAR ChunkBase,
/* Create '\Registry\Machine\HARDWARE\DEVICEMAP' key. */ /* Create '\Registry\Machine\HARDWARE\DEVICEMAP' key. */
RtlInitUnicodeString (&KeyName, RtlInitUnicodeString (&KeyName,
L"\\Registry\\Machine\\HARDWARE\\DEVICEMAP"); REG_DEVICEMAP_KEY_NAME);
InitializeObjectAttributes (&ObjectAttributes, InitializeObjectAttributes (&ObjectAttributes,
&KeyName, &KeyName,
OBJ_CASE_INSENSITIVE, OBJ_CASE_INSENSITIVE,
@ -297,7 +297,7 @@ CmImportHardwareHive(PCHAR ChunkBase,
/* Create '\Registry\Machine\HARDWARE\RESOURCEMAP' key. */ /* Create '\Registry\Machine\HARDWARE\RESOURCEMAP' key. */
RtlInitUnicodeString(&KeyName, RtlInitUnicodeString(&KeyName,
L"\\Registry\\Machine\\HARDWARE\\RESOURCEMAP"); REG_RESOURCEMAP_KEY_NAME);
InitializeObjectAttributes (&ObjectAttributes, InitializeObjectAttributes (&ObjectAttributes,
&KeyName, &KeyName,
OBJ_CASE_INSENSITIVE, OBJ_CASE_INSENSITIVE,
@ -338,7 +338,7 @@ CmImportHardwareHive(PCHAR ChunkBase,
/* Attach it to the machine key */ /* Attach it to the machine key */
RtlInitUnicodeString (&KeyName, RtlInitUnicodeString (&KeyName,
L"\\Registry\\Machine\\HARDWARE"); REG_HARDWARE_KEY_NAME);
InitializeObjectAttributes (&ObjectAttributes, InitializeObjectAttributes (&ObjectAttributes,
&KeyName, &KeyName,
OBJ_CASE_INSENSITIVE, OBJ_CASE_INSENSITIVE,

View file

@ -273,6 +273,7 @@ NtEnumerateKey(IN HANDLE KeyHandle,
OUT PULONG ResultLength) OUT PULONG ResultLength)
{ {
PKEY_OBJECT KeyObject; PKEY_OBJECT KeyObject;
PKEY_OBJECT SubKeyObject;
PREGISTRY_HIVE RegistryHive; PREGISTRY_HIVE RegistryHive;
PKEY_CELL KeyCell, SubKeyCell; PKEY_CELL KeyCell, SubKeyCell;
PHASH_TABLE_CELL HashTableBlock; PHASH_TABLE_CELL HashTableBlock;
@ -314,6 +315,8 @@ NtEnumerateKey(IN HANDLE KeyHandle,
KeyCell = KeyObject->KeyCell; KeyCell = KeyObject->KeyCell;
RegistryHive = KeyObject->RegistryHive; RegistryHive = KeyObject->RegistryHive;
SubKeyObject = NULL;
/* Check for hightest possible sub key index */ /* Check for hightest possible sub key index */
if (Index >= KeyCell->NumberOfSubKeys + KeyObject->NumberOfSubKeys) if (Index >= KeyCell->NumberOfSubKeys + KeyObject->NumberOfSubKeys)
{ {
@ -354,6 +357,7 @@ NtEnumerateKey(IN HANDLE KeyHandle,
return STATUS_NO_MORE_ENTRIES; return STATUS_NO_MORE_ENTRIES;
} }
SubKeyObject = CurKey;
SubKeyCell = CurKey->KeyCell; SubKeyCell = CurKey->KeyCell;
} }
else else
@ -415,6 +419,16 @@ NtEnumerateKey(IN HANDLE KeyHandle,
BasicInformation->TitleIndex = Index; BasicInformation->TitleIndex = Index;
BasicInformation->NameLength = NameSize; BasicInformation->NameLength = NameSize;
if (SubKeyObject != NULL)
{
BasicInformation->NameLength = SubKeyObject->Name.Length;
RtlCopyMemory(BasicInformation->Name,
SubKeyObject->Name.Buffer,
SubKeyObject->Name.Length);
}
else
{
BasicInformation->NameLength = NameSize;
if (SubKeyCell->Flags & REG_KEY_NAME_PACKED) if (SubKeyCell->Flags & REG_KEY_NAME_PACKED)
{ {
CmiCopyPackedName(BasicInformation->Name, CmiCopyPackedName(BasicInformation->Name,
@ -428,6 +442,7 @@ NtEnumerateKey(IN HANDLE KeyHandle,
SubKeyCell->NameSize); SubKeyCell->NameSize);
} }
} }
}
break; break;
case KeyNodeInformation: case KeyNodeInformation:
@ -456,8 +471,17 @@ NtEnumerateKey(IN HANDLE KeyHandle,
NodeInformation->TitleIndex = Index; NodeInformation->TitleIndex = Index;
NodeInformation->ClassOffset = sizeof(KEY_NODE_INFORMATION) + NameSize; NodeInformation->ClassOffset = sizeof(KEY_NODE_INFORMATION) + NameSize;
NodeInformation->ClassLength = SubKeyCell->ClassSize; NodeInformation->ClassLength = SubKeyCell->ClassSize;
NodeInformation->NameLength = NameSize;
if (SubKeyObject != NULL)
{
NodeInformation->NameLength = SubKeyObject->Name.Length;
RtlCopyMemory(NodeInformation->Name,
SubKeyObject->Name.Buffer,
SubKeyObject->Name.Length);
}
else
{
NodeInformation->NameLength = NameSize;
if (SubKeyCell->Flags & REG_KEY_NAME_PACKED) if (SubKeyCell->Flags & REG_KEY_NAME_PACKED)
{ {
CmiCopyPackedName(NodeInformation->Name, CmiCopyPackedName(NodeInformation->Name,
@ -470,6 +494,7 @@ NtEnumerateKey(IN HANDLE KeyHandle,
SubKeyCell->Name, SubKeyCell->Name,
SubKeyCell->NameSize); SubKeyCell->NameSize);
} }
}
if (SubKeyCell->ClassSize != 0) if (SubKeyCell->ClassSize != 0)
{ {
@ -502,7 +527,7 @@ NtEnumerateKey(IN HANDLE KeyHandle,
FullInformation->ClassOffset = sizeof(KEY_FULL_INFORMATION) - FullInformation->ClassOffset = sizeof(KEY_FULL_INFORMATION) -
sizeof(WCHAR); sizeof(WCHAR);
FullInformation->ClassLength = SubKeyCell->ClassSize; FullInformation->ClassLength = SubKeyCell->ClassSize;
FullInformation->SubKeys = SubKeyCell->NumberOfSubKeys; FullInformation->SubKeys = CmiGetNumberOfSubKeys(KeyObject); //SubKeyCell->NumberOfSubKeys;
FullInformation->MaxNameLen = CmiGetMaxNameLength(KeyObject); FullInformation->MaxNameLen = CmiGetMaxNameLength(KeyObject);
FullInformation->MaxClassLen = CmiGetMaxClassLength(KeyObject); FullInformation->MaxClassLen = CmiGetMaxClassLength(KeyObject);
FullInformation->Values = SubKeyCell->NumberOfValues; FullInformation->Values = SubKeyCell->NumberOfValues;
@ -914,18 +939,9 @@ NtQueryKey(IN HANDLE KeyHandle,
BasicInformation->TitleIndex = 0; BasicInformation->TitleIndex = 0;
BasicInformation->NameLength = KeyObject->Name.Length; BasicInformation->NameLength = KeyObject->Name.Length;
if (KeyCell->Flags & REG_KEY_NAME_PACKED)
{
CmiCopyPackedName(BasicInformation->Name,
KeyCell->Name,
KeyCell->NameSize);
}
else
{
RtlCopyMemory(BasicInformation->Name, RtlCopyMemory(BasicInformation->Name,
KeyCell->Name, KeyObject->Name.Buffer,
KeyCell->NameSize); KeyObject->Name.Length);
}
} }
break; break;
@ -950,18 +966,9 @@ NtQueryKey(IN HANDLE KeyHandle,
NodeInformation->ClassLength = KeyCell->ClassSize; NodeInformation->ClassLength = KeyCell->ClassSize;
NodeInformation->NameLength = KeyObject->Name.Length; NodeInformation->NameLength = KeyObject->Name.Length;
if (KeyCell->Flags & REG_KEY_NAME_PACKED)
{
CmiCopyPackedName(NodeInformation->Name,
KeyCell->Name,
KeyCell->NameSize);
}
else
{
RtlCopyMemory(NodeInformation->Name, RtlCopyMemory(NodeInformation->Name,
KeyCell->Name, KeyObject->Name.Buffer,
KeyCell->NameSize); KeyObject->Name.Length);
}
if (KeyCell->ClassSize != 0) if (KeyCell->ClassSize != 0)
{ {
@ -993,7 +1000,7 @@ NtQueryKey(IN HANDLE KeyHandle,
FullInformation->TitleIndex = 0; FullInformation->TitleIndex = 0;
FullInformation->ClassOffset = sizeof(KEY_FULL_INFORMATION) - sizeof(WCHAR); FullInformation->ClassOffset = sizeof(KEY_FULL_INFORMATION) - sizeof(WCHAR);
FullInformation->ClassLength = KeyCell->ClassSize; FullInformation->ClassLength = KeyCell->ClassSize;
FullInformation->SubKeys = KeyCell->NumberOfSubKeys; FullInformation->SubKeys = CmiGetNumberOfSubKeys(KeyObject); //KeyCell->NumberOfSubKeys;
FullInformation->MaxNameLen = CmiGetMaxNameLength(KeyObject); FullInformation->MaxNameLen = CmiGetMaxNameLength(KeyObject);
FullInformation->MaxClassLen = CmiGetMaxClassLength(KeyObject); FullInformation->MaxClassLen = CmiGetMaxClassLength(KeyObject);
FullInformation->Values = KeyCell->NumberOfValues; FullInformation->Values = KeyCell->NumberOfValues;

View file

@ -2026,6 +2026,36 @@ CmiFlushRegistryHive(PREGISTRY_HIVE RegistryHive)
} }
ULONG
CmiGetNumberOfSubKeys(PKEY_OBJECT KeyObject)
{
PKEY_OBJECT CurKey;
PKEY_CELL KeyCell;
ULONG SubKeyCount;
ULONG i;
VERIFY_KEY_OBJECT(KeyObject);
KeyCell = KeyObject->KeyCell;
VERIFY_KEY_CELL(KeyCell);
SubKeyCount = (KeyCell == NULL) ? 0 : KeyCell->NumberOfSubKeys;
/* Search for volatile or 'foreign' keys */
for (i = 0; i < KeyObject->NumberOfSubKeys; i++)
{
CurKey = KeyObject->SubKeys[i];
if (CurKey->RegistryHive == CmiVolatileHive ||
CurKey->RegistryHive != KeyObject->RegistryHive)
{
SubKeyCount++;
}
}
return SubKeyCount;
}
ULONG ULONG
CmiGetMaxNameLength(PKEY_OBJECT KeyObject) CmiGetMaxNameLength(PKEY_OBJECT KeyObject)
{ {
@ -2076,13 +2106,13 @@ CmiGetMaxNameLength(PKEY_OBJECT KeyObject)
} }
} }
} }
if (KeyObject->RegistryHive != CmiVolatileHive)
{
DPRINT("KeyObject->NumberOfSubKeys %d\n", KeyObject->NumberOfSubKeys); DPRINT("KeyObject->NumberOfSubKeys %d\n", KeyObject->NumberOfSubKeys);
for (i = 0; i < KeyObject->NumberOfSubKeys; i++) for (i = 0; i < KeyObject->NumberOfSubKeys; i++)
{ {
CurKey = KeyObject->SubKeys[i]; CurKey = KeyObject->SubKeys[i];
if (CurKey->RegistryHive == CmiVolatileHive) if (CurKey->RegistryHive == CmiVolatileHive ||
CurKey->RegistryHive != KeyObject->RegistryHive)
{ {
CurSubKeyCell = CurKey->KeyCell; CurSubKeyCell = CurKey->KeyCell;
if (CurSubKeyCell == NULL) if (CurSubKeyCell == NULL)
@ -2090,18 +2120,19 @@ CmiGetMaxNameLength(PKEY_OBJECT KeyObject)
DPRINT("CmiGetBlock() failed\n"); DPRINT("CmiGetBlock() failed\n");
continue; continue;
} }
NameSize = CurSubKeyCell->NameSize; NameSize = CurSubKeyCell->NameSize;
if (CurSubKeyCell->Flags & REG_KEY_NAME_PACKED) if (CurSubKeyCell->Flags & REG_KEY_NAME_PACKED)
{ {
NameSize *= sizeof(WCHAR); NameSize *= sizeof(WCHAR);
} }
if (MaxName < NameSize) if (MaxName < NameSize)
{ {
MaxName = NameSize; MaxName = NameSize;
} }
} }
} }
}
return MaxName; return MaxName;
} }
@ -2152,13 +2183,13 @@ CmiGetMaxClassLength(PKEY_OBJECT KeyObject)
} }
} }
} }
if (KeyObject->RegistryHive != CmiVolatileHive)
{
DPRINT("KeyObject->NumberOfSubKeys %d\n", KeyObject->NumberOfSubKeys); DPRINT("KeyObject->NumberOfSubKeys %d\n", KeyObject->NumberOfSubKeys);
for (i = 0; i < KeyObject->NumberOfSubKeys; i++) for (i = 0; i < KeyObject->NumberOfSubKeys; i++)
{ {
CurKey = KeyObject->SubKeys[i]; CurKey = KeyObject->SubKeys[i];
if (CurKey->RegistryHive == CmiVolatileHive) if (CurKey->RegistryHive == CmiVolatileHive ||
CurKey->RegistryHive != KeyObject->RegistryHive)
{ {
CurSubKeyCell = CurKey->KeyCell; CurSubKeyCell = CurKey->KeyCell;
if (CurSubKeyCell == NULL) if (CurSubKeyCell == NULL)
@ -2166,13 +2197,13 @@ CmiGetMaxClassLength(PKEY_OBJECT KeyObject)
DPRINT("CmiGetBlock() failed\n"); DPRINT("CmiGetBlock() failed\n");
continue; continue;
} }
if (MaxClass < CurSubKeyCell->ClassSize) if (MaxClass < CurSubKeyCell->ClassSize)
{ {
MaxClass = CurSubKeyCell->ClassSize; MaxClass = CurSubKeyCell->ClassSize;
} }
} }
} }
}
return MaxClass; return MaxClass;
} }