work on ntopenkey forkeys insystem hive

svn path=/trunk/; revision=1368
This commit is contained in:
jean 2000-09-21 13:45:42 +00:00
parent 56cd5f816c
commit 572b3bf901

View file

@ -1,4 +1,4 @@
/* $Id: registry.c,v 1.35 2000/09/18 09:39:18 jean Exp $ /* $Id: registry.c,v 1.36 2000/09/21 13:45:42 jean Exp $
* *
* COPYRIGHT: See COPYING in the top level directory * COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS kernel * PROJECT: ReactOS kernel
@ -56,17 +56,18 @@ typedef DWORD BLOCK_OFFSET;
typedef struct _HEADER_BLOCK typedef struct _HEADER_BLOCK
{ {
DWORD BlockId; DWORD BlockId;
DWORD Unused1; DWORD Unused1; /* file version ?*/
DWORD Unused2; DWORD Unused2; /* file version ?*/
LARGE_INTEGER DateModified; LARGE_INTEGER DateModified;
DWORD Unused3; DWORD Unused3; /* registry format version ? */
DWORD Unused4; DWORD Unused4; /* registry format version ? */
DWORD Unused5; DWORD Unused5; /* registry format version ? */
DWORD Unused6; DWORD Unused6; /* registry format version ? */
BLOCK_OFFSET RootKeyBlock; BLOCK_OFFSET RootKeyBlock;
DWORD BlockSize; DWORD BlockSize;
DWORD Unused7; DWORD Unused7;
DWORD Unused8[115]; WCHAR FileName[64]; /* end of file name */
DWORD Unused8[83];
DWORD Checksum; DWORD Checksum;
} HEADER_BLOCK, *PHEADER_BLOCK; } HEADER_BLOCK, *PHEADER_BLOCK;
@ -75,6 +76,9 @@ typedef struct _HEAP_BLOCK
DWORD BlockId; DWORD BlockId;
BLOCK_OFFSET BlockOffset; BLOCK_OFFSET BlockOffset;
DWORD BlockSize; DWORD BlockSize;
DWORD Unused1;
LARGE_INTEGER DateModified;
DWORD Unused2;
} HEAP_BLOCK, *PHEAP_BLOCK; } HEAP_BLOCK, *PHEAP_BLOCK;
// each sub_block begin with this struct : // each sub_block begin with this struct :
@ -139,16 +143,9 @@ typedef struct _VALUE_BLOCK
WORD Flags; WORD Flags;
WORD Unused1; WORD Unused1;
// FIXME : Name is char, not wchar // FIXME : Name is char, not wchar
WCHAR Name[0]; /* warning : not zero terminated */ UCHAR Name[0]; /* warning : not zero terminated */
} VALUE_BLOCK, *PVALUE_BLOCK; } VALUE_BLOCK, *PVALUE_BLOCK;
typedef struct _IN_MEMORY_BLOCK
{
DWORD FileOffset;
DWORD BlockSize;
PVOID *Data;
} IN_MEMORY_BLOCK, *PIN_MEMORY_BLOCK;
typedef struct _REGISTRY_FILE typedef struct _REGISTRY_FILE
{ {
PWSTR Filename; PWSTR Filename;
@ -169,11 +166,14 @@ typedef struct _KEY_OBJECT
CSHORT Size; CSHORT Size;
ULONG Flags; ULONG Flags;
WCHAR *Name; WORD NameSize; // length of Name
UCHAR *Name;
PREGISTRY_FILE RegistryFile; PREGISTRY_FILE RegistryFile;
PKEY_BLOCK KeyBlock; PKEY_BLOCK KeyBlock;
struct _KEY_OBJECT *NextKey; struct _KEY_OBJECT *ParentKey;
struct _KEY_OBJECT *SubKey; DWORD NumberOfSubKeys; /* subkeys loaded in SubKeys */
DWORD SizeOfSubKeys; /* space allocated in SubKeys */
struct _KEY_OBJECT **SubKeys; /* list of subkeys loaded */
} KEY_OBJECT, *PKEY_OBJECT; } KEY_OBJECT, *PKEY_OBJECT;
@ -181,12 +181,14 @@ typedef struct _KEY_OBJECT
static POBJECT_TYPE CmiKeyType = NULL; static POBJECT_TYPE CmiKeyType = NULL;
static PREGISTRY_FILE CmiVolatileFile = NULL; static PREGISTRY_FILE CmiVolatileFile = NULL;
static PKEY_OBJECT CmiKeyList = NULL; static PKEY_OBJECT CmiRootKey = NULL;
static PKEY_OBJECT CmiMachineKey = NULL;
static KSPIN_LOCK CmiKeyListLock; static KSPIN_LOCK CmiKeyListLock;
static PREGISTRY_FILE CmiSystemFile = NULL; static PREGISTRY_FILE CmiSystemFile = NULL;
/* ----------------------------------------- Forward Declarations */ /* ----------------------------------------- Forward Declarations */
static NTSTATUS CmiObjectParse(PVOID ParsedObject, static NTSTATUS CmiObjectParse(PVOID ParsedObject,
PVOID *NextObject, PVOID *NextObject,
PUNICODE_STRING FullPath, PUNICODE_STRING FullPath,
@ -196,9 +198,9 @@ static NTSTATUS CmiObjectParse(PVOID ParsedObject,
static VOID CmiObjectDelete(PVOID DeletedObject); static VOID CmiObjectDelete(PVOID DeletedObject);
static NTSTATUS CmiBuildKeyPath(PWSTR *KeyPath, static NTSTATUS CmiBuildKeyPath(PWSTR *KeyPath,
POBJECT_ATTRIBUTES ObjectAttributes); POBJECT_ATTRIBUTES ObjectAttributes);
static VOID CmiAddKeyToList(PKEY_OBJECT NewKey); static VOID CmiAddKeyToList(PKEY_OBJECT ParentKey,PKEY_OBJECT NewKey);
static VOID CmiRemoveKeyFromList(PKEY_OBJECT NewKey); static VOID CmiRemoveKeyFromList(PKEY_OBJECT NewKey);
static PKEY_OBJECT CmiScanKeyList(PWSTR KeyNameBuf); static PKEY_OBJECT CmiScanKeyList(PKEY_OBJECT Parent,PCHAR KeyNameBuf);
static PREGISTRY_FILE CmiCreateRegistry(PWSTR Filename); static PREGISTRY_FILE CmiCreateRegistry(PWSTR Filename);
static NTSTATUS CmiCreateKey(IN PREGISTRY_FILE RegistryFile, static NTSTATUS CmiCreateKey(IN PREGISTRY_FILE RegistryFile,
IN PWSTR KeyNameBuf, IN PWSTR KeyNameBuf,
@ -208,12 +210,14 @@ static NTSTATUS CmiCreateKey(IN PREGISTRY_FILE RegistryFile,
IN PUNICODE_STRING Class, IN PUNICODE_STRING Class,
IN ULONG CreateOptions, IN ULONG CreateOptions,
OUT PULONG Disposition); OUT PULONG Disposition);
#ifdef xxx
static NTSTATUS CmiFindKey(IN PREGISTRY_FILE RegistryFile, static NTSTATUS CmiFindKey(IN PREGISTRY_FILE RegistryFile,
IN PWSTR KeyNameBuf, IN PWSTR KeyNameBuf,
OUT PKEY_BLOCK *KeyBlock, OUT PKEY_BLOCK *KeyBlock,
IN ACCESS_MASK DesiredAccess, IN ACCESS_MASK DesiredAccess,
IN ULONG TitleIndex, IN ULONG TitleIndex,
IN PUNICODE_STRING Class); IN PUNICODE_STRING Class);
#endif
static ULONG CmiGetMaxNameLength(PREGISTRY_FILE RegistryFile, static ULONG CmiGetMaxNameLength(PREGISTRY_FILE RegistryFile,
PKEY_BLOCK KeyBlock); PKEY_BLOCK KeyBlock);
static ULONG CmiGetMaxClassLength(PREGISTRY_FILE RegistryFile, static ULONG CmiGetMaxClassLength(PREGISTRY_FILE RegistryFile,
@ -236,7 +240,7 @@ static NTSTATUS CmiAddSubKey(IN PREGISTRY_FILE RegistryFile,
IN ULONG CreateOptions); IN ULONG CreateOptions);
static NTSTATUS CmiScanKeyForValue(IN PREGISTRY_FILE RegistryFile, static NTSTATUS CmiScanKeyForValue(IN PREGISTRY_FILE RegistryFile,
IN PKEY_BLOCK KeyBlock, IN PKEY_BLOCK KeyBlock,
IN PWSTR ValueName, IN PCHAR ValueName,
OUT PVALUE_BLOCK *ValueBlock); OUT PVALUE_BLOCK *ValueBlock);
static NTSTATUS CmiGetValueFromKeyByIndex(IN PREGISTRY_FILE RegistryFile, static NTSTATUS CmiGetValueFromKeyByIndex(IN PREGISTRY_FILE RegistryFile,
IN PKEY_BLOCK KeyBlock, IN PKEY_BLOCK KeyBlock,
@ -244,13 +248,13 @@ static NTSTATUS CmiGetValueFromKeyByIndex(IN PREGISTRY_FILE RegistryFile,
OUT PVALUE_BLOCK *ValueBlock); OUT PVALUE_BLOCK *ValueBlock);
static NTSTATUS CmiAddValueToKey(IN PREGISTRY_FILE RegistryFile, static NTSTATUS CmiAddValueToKey(IN PREGISTRY_FILE RegistryFile,
IN PKEY_BLOCK KeyBlock, IN PKEY_BLOCK KeyBlock,
IN PWSTR ValueNameBuf, IN PCHAR ValueNameBuf,
IN ULONG Type, IN ULONG Type,
IN PVOID Data, IN PVOID Data,
IN ULONG DataSize); IN ULONG DataSize);
static NTSTATUS CmiDeleteValueFromKey(IN PREGISTRY_FILE RegistryFile, static NTSTATUS CmiDeleteValueFromKey(IN PREGISTRY_FILE RegistryFile,
IN PKEY_BLOCK KeyBlock, IN PKEY_BLOCK KeyBlock,
IN PWSTR ValueName); IN PCHAR ValueName);
static NTSTATUS CmiAllocateKeyBlock(IN PREGISTRY_FILE RegistryFile, static NTSTATUS CmiAllocateKeyBlock(IN PREGISTRY_FILE RegistryFile,
OUT PKEY_BLOCK *KeyBlock, OUT PKEY_BLOCK *KeyBlock,
IN PCHAR NewSubKeyName, IN PCHAR NewSubKeyName,
@ -272,7 +276,7 @@ static NTSTATUS CmiDestroyHashTableBlock(PREGISTRY_FILE RegistryFile,
PHASH_TABLE_BLOCK HashBlock); PHASH_TABLE_BLOCK HashBlock);
static NTSTATUS CmiAllocateValueBlock(IN PREGISTRY_FILE RegistryFile, static NTSTATUS CmiAllocateValueBlock(IN PREGISTRY_FILE RegistryFile,
OUT PVALUE_BLOCK *ValueBlock, OUT PVALUE_BLOCK *ValueBlock,
IN PWSTR ValueNameBuf, IN PCHAR ValueNameBuf,
IN ULONG Type, IN ULONG Type,
IN PVOID Data, IN PVOID Data,
IN ULONG DataSize); IN ULONG DataSize);
@ -307,7 +311,8 @@ CmInitializeRegistry(VOID)
HANDLE RootKeyHandle; HANDLE RootKeyHandle;
UNICODE_STRING RootKeyName; UNICODE_STRING RootKeyName;
OBJECT_ATTRIBUTES ObjectAttributes; OBJECT_ATTRIBUTES ObjectAttributes;
PKEY_BLOCK KeyBlock; PKEY_OBJECT NewKey;
HANDLE KeyHandle;
/* Initialize the Key object type */ /* Initialize the Key object type */
CmiKeyType = ExAllocatePool(NonPagedPool, sizeof(OBJECT_TYPE)); CmiKeyType = ExAllocatePool(NonPagedPool, sizeof(OBJECT_TYPE));
@ -325,34 +330,73 @@ CmInitializeRegistry(VOID)
CmiKeyType->Security = NULL; CmiKeyType->Security = NULL;
CmiKeyType->QueryName = NULL; CmiKeyType->QueryName = NULL;
CmiKeyType->OkayToClose = NULL; CmiKeyType->OkayToClose = NULL;
CmiKeyType->Create = NULL;
RtlInitUnicodeString(&CmiKeyType->TypeName, L"Key"); RtlInitUnicodeString(&CmiKeyType->TypeName, L"Key");
/* Build the Root Key Object */
/* FIXME: This should be split into two objects, 1 system and 1 user */
RtlInitUnicodeString(&RootKeyName, REG_ROOT_KEY_NAME);
InitializeObjectAttributes(&ObjectAttributes, &RootKeyName, 0, NULL, NULL);
ObCreateObject(&RootKeyHandle,
STANDARD_RIGHTS_REQUIRED,
&ObjectAttributes,
CmiKeyType);
KeInitializeSpinLock(&CmiKeyListLock);
/* Build volitile registry store */ /* Build volitile registry store */
CmiVolatileFile = CmiCreateRegistry(NULL); CmiVolatileFile = CmiCreateRegistry(NULL);
/* Build system registry store */ /* Build the Root Key Object */
CmiSystemFile = NULL; // CmiCreateRegistry(SYSTEM_REG_FILE); RtlInitUnicodeString(&RootKeyName, REG_ROOT_KEY_NAME);
InitializeObjectAttributes(&ObjectAttributes, &RootKeyName, 0, NULL, NULL);
NewKey=ObCreateObject(&RootKeyHandle,
STANDARD_RIGHTS_REQUIRED,
&ObjectAttributes,
CmiKeyType);
CmiRootKey = NewKey;
ObAddEntryDirectory(NameSpaceRoot, CmiRootKey, L"Registry");
Status = ObReferenceObjectByHandle(RootKeyHandle,
STANDARD_RIGHTS_REQUIRED,
ObDirectoryType,
UserMode,
(PVOID*)&CmiRootKey,
NULL);
CmiRootKey->RegistryFile = CmiVolatileFile;
CmiRootKey->KeyBlock = CmiGetBlock(CmiVolatileFile,CmiVolatileFile->HeaderBlock->RootKeyBlock);
CmiRootKey->Flags = 0;
CmiRootKey->NumberOfSubKeys=0;
CmiRootKey->SubKeys= NULL;
CmiRootKey->SizeOfSubKeys= NewKey->KeyBlock->NumberOfSubKeys;
CmiRootKey->Name=ExAllocatePool(PagedPool,strlen("Registry"));
CmiRootKey->NameSize=strlen("Registry");
memcpy(CmiRootKey->Name,"Registry",strlen("Registry"));
KeInitializeSpinLock(&CmiKeyListLock);
/* Create initial predefined symbolic links */ /* Create initial predefined symbolic links */
/* HKEY_LOCAL_MACHINE */ /* HKEY_LOCAL_MACHINE */
Status = CmiCreateKey(CmiVolatileFile, RtlInitUnicodeString(&RootKeyName, REG_MACHINE_KEY_NAME);
L"Machine", InitializeObjectAttributes(&ObjectAttributes, &RootKeyName, 0, NULL, NULL);
&KeyBlock, NewKey=ObCreateObject(&KeyHandle,
KEY_ALL_ACCESS, STANDARD_RIGHTS_REQUIRED,
&ObjectAttributes,
CmiKeyType);
Status = CmiAddSubKey(CmiVolatileFile,
CmiRootKey->KeyBlock,
&NewKey->KeyBlock,
"Machine",
0,
NULL,
0);
NewKey->RegistryFile = CmiVolatileFile;
NewKey->Flags = 0;
NewKey->NumberOfSubKeys=0;
NewKey->SubKeys= NULL;
NewKey->SizeOfSubKeys= NewKey->KeyBlock->NumberOfSubKeys;
NewKey->Name=ExAllocatePool(PagedPool,strlen("Machine"));
NewKey->NameSize=strlen("Machine");
memcpy(NewKey->Name,"Machine",strlen("Machine"));
CmiAddKeyToList(CmiRootKey,NewKey);
CmiMachineKey=NewKey;
#ifdef xxx
/* HKEY_LOCAL_MACHINE */
Status = CmiAddSubKey(CmiVolatileFile,
CmiRootKey->KeyBlock,
&KeyBlock,
"Machine",
0, 0,
NULL, NULL,
REG_OPTION_VOLATILE,
0); 0);
if (!NT_SUCCESS(Status)) if (!NT_SUCCESS(Status))
{ {
@ -361,13 +405,12 @@ CmInitializeRegistry(VOID)
CmiReleaseBlock(CmiVolatileFile, KeyBlock); CmiReleaseBlock(CmiVolatileFile, KeyBlock);
/* HKEY_USERS */ /* HKEY_USERS */
Status = CmiCreateKey(CmiVolatileFile, Status = CmiAddSubKey(CmiVolatileFile,
L"Users", CmiRootKey->KeyBlock,
&KeyBlock, &KeyBlock,
KEY_ALL_ACCESS, "Users",
0, 0,
NULL, NULL,
REG_OPTION_VOLATILE,
0); 0);
if (!NT_SUCCESS(Status)) if (!NT_SUCCESS(Status))
{ {
@ -375,6 +418,7 @@ CmInitializeRegistry(VOID)
} }
CHECKPOINT; CHECKPOINT;
CmiReleaseBlock(CmiVolatileFile, KeyBlock); CmiReleaseBlock(CmiVolatileFile, KeyBlock);
#endif
/* FIXME: create remaining structure needed for default handles */ /* FIXME: create remaining structure needed for default handles */
/* FIXME: load volatile registry data from ROSDTECT */ /* FIXME: load volatile registry data from ROSDTECT */
@ -394,6 +438,7 @@ CmInitializeRegistry2(VOID)
CmiSystemFile = CmiCreateRegistry(SYSTEM_REG_FILE); CmiSystemFile = CmiCreateRegistry(SYSTEM_REG_FILE);
if( CmiSystemFile ) if( CmiSystemFile )
{ {
CHECKPOINT;
RtlInitUnicodeString(&KeyName, REG_SYSTEM_KEY_NAME); RtlInitUnicodeString(&KeyName, REG_SYSTEM_KEY_NAME);
InitializeObjectAttributes(&ObjectAttributes, &KeyName, 0, NULL, NULL); InitializeObjectAttributes(&ObjectAttributes, &KeyName, 0, NULL, NULL);
NewKey=ObCreateObject(&KeyHandle, NewKey=ObCreateObject(&KeyHandle,
@ -402,11 +447,15 @@ CmInitializeRegistry2(VOID)
CmiKeyType); CmiKeyType);
NewKey->RegistryFile = CmiSystemFile; NewKey->RegistryFile = CmiSystemFile;
NewKey->KeyBlock = CmiGetBlock(CmiSystemFile,32); NewKey->KeyBlock = CmiGetBlock(CmiSystemFile,32);
DPRINT("root : id = %x\n",NewKey->KeyBlock->SubBlockId);
DPRINT("root : hashOffset = %x\n",NewKey->KeyBlock->HashTableOffset);
DPRINT("root : nom = %6.6s\n",NewKey->KeyBlock->Name);
NewKey->Flags = 0; NewKey->Flags = 0;
NewKey->NextKey = NULL; NewKey->NumberOfSubKeys=0;
NewKey->SubKeys= ExAllocatePool(PagedPool
, NewKey->KeyBlock->NumberOfSubKeys * sizeof(DWORD));
NewKey->SizeOfSubKeys= NewKey->KeyBlock->NumberOfSubKeys;
NewKey->Name=ExAllocatePool(PagedPool,strlen("System"));
NewKey->NameSize=strlen("System");
memcpy(NewKey->Name,"System",strlen("System"));
CmiAddKeyToList(CmiMachineKey,NewKey);
/* tests :*/ /* tests :*/
{ {
HANDLE HKey; HANDLE HKey;
@ -415,26 +464,17 @@ DPRINT("root : nom = %6.6s\n",NewKey->KeyBlock->Name);
Status = CmiScanForSubKey(CmiSystemFile, Status = CmiScanForSubKey(CmiSystemFile,
NewKey->KeyBlock, NewKey->KeyBlock,
&SubKeyBlock, &SubKeyBlock,
L"ControlSet001", "ControlSet001",
KEY_READ); KEY_READ);
CHECKPOINT;
if(NT_SUCCESS(Status))
{
DPRINT("found subkey ,ptr=%x\n",SubKeyBlock);
DPRINT(" Id=%x\n",SubKeyBlock->SubBlockId);
DPRINT(" Type=%x\n",SubKeyBlock->Type);
DPRINT(" parent=%x\n",SubKeyBlock->ParentKeyOffset);
DPRINT(" name=%x\n",SubKeyBlock->Name);
}
else
{
DPRINT("not found subkey ControlSet001\n");
}
//RtlInitUnicodeString(&KeyName, L"\\Registry\\Machine\\Software\\Windows"); //RtlInitUnicodeString(&KeyName, L"\\Registry\\Machine\\Software\\Windows");
RtlInitUnicodeString(&KeyName, L"\\Registry\\Machine\\System\\ControlSet001"); RtlInitUnicodeString(&KeyName, L"\\Registry\\Machine\\System\\ControlSet001");
InitializeObjectAttributes(&ObjectAttributes, &KeyName, 0, NULL, NULL); InitializeObjectAttributes(&ObjectAttributes, &KeyName, 0, NULL, NULL);
Status = NtOpenKey ( &HKey, KEY_READ , &ObjectAttributes); Status = NtOpenKey ( &HKey, KEY_READ , &ObjectAttributes);
DPRINT(" NtOpenKey = %x, HKey=%x\n",Status,HKey); DPRINT(" NtOpenKey = %x, HKey=%x\n",Status,HKey);
//for(;;)
//{
//__asm__ ("hlt\n\t");
//}
} }
} }
#endif #endif
@ -467,6 +507,7 @@ NtCreateKey (
assert(ObjectAttributes != NULL); assert(ObjectAttributes != NULL);
/* FIXME : FileToUse depends also from Parent Key */
FileToUse = (CreateOptions & REG_OPTION_VOLATILE) ? FileToUse = (CreateOptions & REG_OPTION_VOLATILE) ?
CmiVolatileFile : CmiSystemFile; CmiVolatileFile : CmiSystemFile;
@ -478,7 +519,9 @@ NtCreateKey (
} }
/* Scan the key list to see if key already open */ /* Scan the key list to see if key already open */
CurKey = CmiScanKeyList(KeyNameBuf); /* FIXME : walk through the tree of opened keys */
// CurKey = CmiScanKeyList(KeyNameBuf);
CurKey = NULL;
if (CurKey != NULL) if (CurKey != NULL)
{ {
/* Unmark the key if the key has been marked for Delete */ /* Unmark the key if the key has been marked for Delete */
@ -527,10 +570,11 @@ NtCreateKey (
return STATUS_UNSUCCESSFUL; return STATUS_UNSUCCESSFUL;
} }
NewKey->Flags = 0; NewKey->Flags = 0;
NewKey->Name = KeyNameBuf; NewKey->Name = KeyBlock->Name;
NewKey->NameSize = KeyBlock->NameSize;
NewKey->KeyBlock = KeyBlock; NewKey->KeyBlock = KeyBlock;
NewKey->RegistryFile = FileToUse; NewKey->RegistryFile = FileToUse;
CmiAddKeyToList(NewKey); CmiAddKeyToList(CurKey,NewKey);
Status = ObCreateHandle(PsGetCurrentProcess(), Status = ObCreateHandle(PsGetCurrentProcess(),
NewKey, NewKey,
DesiredAccess, DesiredAccess,
@ -793,7 +837,8 @@ NtEnumerateValueKey (
ValueBasicInformation->Type = ValueBlock->DataType; ValueBasicInformation->Type = ValueBlock->DataType;
ValueBasicInformation->NameLength = ValueBasicInformation->NameLength =
(ValueBlock->NameSize + 1) * sizeof(WCHAR); (ValueBlock->NameSize + 1) * sizeof(WCHAR);
wcscpy(ValueBasicInformation->Name, ValueBlock->Name); mbstowcs(ValueBasicInformation->Name, ValueBlock->Name,ValueBlock->NameSize);
ValueBasicInformation->Name[ValueBlock->NameSize]=0;
} }
break; break;
@ -838,7 +883,8 @@ NtEnumerateValueKey (
ValueFullInformation->DataLength = ValueBlock->DataSize; ValueFullInformation->DataLength = ValueBlock->DataSize;
ValueFullInformation->NameLength = ValueFullInformation->NameLength =
(ValueBlock->NameSize + 1) * sizeof(WCHAR); (ValueBlock->NameSize + 1) * sizeof(WCHAR);
wcscpy(ValueFullInformation->Name, ValueBlock->Name); mbstowcs(ValueFullInformation->Name, ValueBlock->Name,ValueBlock->NameSize);
ValueFullInformation->Name[ValueBlock->NameSize]=0;
DataBlock = CmiGetBlock(RegistryFile, ValueBlock->DataOffset); DataBlock = CmiGetBlock(RegistryFile, ValueBlock->DataOffset);
RtlCopyMemory(&ValueFullInformation->Name[ValueBlock->NameSize + 1], RtlCopyMemory(&ValueFullInformation->Name[ValueBlock->NameSize + 1],
DataBlock, DataBlock,
@ -876,6 +922,41 @@ NtOpenKey (
IN POBJECT_ATTRIBUTES ObjectAttributes IN POBJECT_ATTRIBUTES ObjectAttributes
) )
{ {
NTSTATUS Status;
PVOID Object;
DPRINT("NtOpenKey (Name %wZ)\n",
ObjectAttributes->ObjectName);
Status = ObReferenceObjectByName(
ObjectAttributes->ObjectName,
ObjectAttributes->Attributes,
NULL,
DesiredAccess,
CmiKeyType,
UserMode,
NULL,
& Object
);
if (!NT_SUCCESS(Status))
{
return Status;
}
Status = ObCreateHandle(
PsGetCurrentProcess(),
Object,
DesiredAccess,
FALSE,
KeyHandle
);
if (!NT_SUCCESS(Status))
{
return Status;
}
return STATUS_SUCCESS;
#ifdef xxx
NTSTATUS Status; NTSTATUS Status;
PWSTR KeyNameBuf; PWSTR KeyNameBuf;
PREGISTRY_FILE FileToUse; PREGISTRY_FILE FileToUse;
@ -889,8 +970,10 @@ NtOpenKey (
return Status; return Status;
} }
/* FIXME : walk through the tree of opened keys */
/* Scan the key list to see if key already open */ /* Scan the key list to see if key already open */
CurKey = CmiScanKeyList(KeyNameBuf); //CurKey = CmiScanKeyList(KeyNameBuf);
CurKey = NULL;
if (CurKey != NULL) if (CurKey != NULL)
{ {
/* Fail if the key has been deleted */ /* Fail if the key has been deleted */
@ -947,10 +1030,11 @@ NtOpenKey (
return STATUS_UNSUCCESSFUL; return STATUS_UNSUCCESSFUL;
} }
NewKey->Flags = 0; NewKey->Flags = 0;
NewKey->Name = KeyNameBuf; NewKey->Name = KeyBlock->Name;
NewKey->NameSize = KeyBlock->NameSize;
NewKey->RegistryFile = FileToUse; NewKey->RegistryFile = FileToUse;
NewKey->KeyBlock = KeyBlock; NewKey->KeyBlock = KeyBlock;
CmiAddKeyToList(NewKey); CmiAddKeyToList(CurKey,NewKey);
Status = ObCreateHandle(PsGetCurrentProcess(), Status = ObCreateHandle(PsGetCurrentProcess(),
NewKey, NewKey,
DesiredAccess, DesiredAccess,
@ -958,6 +1042,7 @@ NtOpenKey (
KeyHandle); KeyHandle);
return Status; return Status;
#endif
} }
@ -1118,6 +1203,10 @@ NtQueryValueKey (
PKEY_VALUE_BASIC_INFORMATION ValueBasicInformation; PKEY_VALUE_BASIC_INFORMATION ValueBasicInformation;
PKEY_VALUE_PARTIAL_INFORMATION ValuePartialInformation; PKEY_VALUE_PARTIAL_INFORMATION ValuePartialInformation;
PKEY_VALUE_FULL_INFORMATION ValueFullInformation; PKEY_VALUE_FULL_INFORMATION ValueFullInformation;
char ValueName2[MAX_PATH];
wcstombs(ValueName2,ValueName->Buffer,ValueName->Length);
ValueName2[ValueName->Length]=0;
/* Verify that the handle is valid and is a registry key */ /* Verify that the handle is valid and is a registry key */
Status = ObReferenceObjectByHandle(KeyHandle, Status = ObReferenceObjectByHandle(KeyHandle,
@ -1138,7 +1227,7 @@ NtQueryValueKey (
/* Get Value block of interest */ /* Get Value block of interest */
Status = CmiScanKeyForValue(RegistryFile, Status = CmiScanKeyForValue(RegistryFile,
KeyBlock, KeyBlock,
ValueName->Buffer, ValueName2,
&ValueBlock); &ValueBlock);
if (!NT_SUCCESS(Status)) if (!NT_SUCCESS(Status))
{ {
@ -1162,7 +1251,8 @@ NtQueryValueKey (
ValueBasicInformation->TitleIndex = 0; ValueBasicInformation->TitleIndex = 0;
ValueBasicInformation->Type = ValueBlock->DataType; ValueBasicInformation->Type = ValueBlock->DataType;
ValueBasicInformation->NameLength = ValueBlock->NameSize; ValueBasicInformation->NameLength = ValueBlock->NameSize;
wcscpy(ValueBasicInformation->Name, ValueBlock->Name); mbstowcs(ValueBasicInformation->Name, ValueBlock->Name,ValueBlock->NameSize);
ValueBasicInformation->Name[ValueBlock->NameSize]=0;
} }
break; break;
@ -1206,7 +1296,8 @@ NtQueryValueKey (
ValueBlock->NameSize * sizeof(WCHAR); ValueBlock->NameSize * sizeof(WCHAR);
ValueFullInformation->DataLength = ValueBlock->DataSize; ValueFullInformation->DataLength = ValueBlock->DataSize;
ValueFullInformation->NameLength = ValueBlock->NameSize; ValueFullInformation->NameLength = ValueBlock->NameSize;
wcscpy(ValueFullInformation->Name, ValueBlock->Name); mbstowcs(ValueFullInformation->Name, ValueBlock->Name,ValueBlock->NameSize);
ValueFullInformation->Name[ValueBlock->NameSize]=0;
DataBlock = CmiGetBlock(RegistryFile, ValueBlock->DataOffset); DataBlock = CmiGetBlock(RegistryFile, ValueBlock->DataOffset);
RtlCopyMemory(&ValueFullInformation->Name[ValueBlock->NameSize + 1], RtlCopyMemory(&ValueFullInformation->Name[ValueBlock->NameSize + 1],
DataBlock, DataBlock,
@ -1242,6 +1333,10 @@ NtSetValueKey (
PREGISTRY_FILE RegistryFile; PREGISTRY_FILE RegistryFile;
PKEY_BLOCK KeyBlock; PKEY_BLOCK KeyBlock;
PVALUE_BLOCK ValueBlock; PVALUE_BLOCK ValueBlock;
char ValueName2[MAX_PATH];
wcstombs(ValueName2,ValueName->Buffer,ValueName->Length);
ValueName2[ValueName->Length]=0;
/* Verify that the handle is valid and is a registry key */ /* Verify that the handle is valid and is a registry key */
Status = ObReferenceObjectByHandle(KeyHandle, Status = ObReferenceObjectByHandle(KeyHandle,
@ -1260,7 +1355,7 @@ NtSetValueKey (
RegistryFile = KeyObject->RegistryFile; RegistryFile = KeyObject->RegistryFile;
Status = CmiScanKeyForValue(RegistryFile, Status = CmiScanKeyForValue(RegistryFile,
KeyBlock, KeyBlock,
ValueName->Buffer, ValueName2,
&ValueBlock); &ValueBlock);
if (!NT_SUCCESS(Status)) if (!NT_SUCCESS(Status))
{ {
@ -1271,7 +1366,7 @@ NtSetValueKey (
{ {
Status = CmiAddValueToKey(RegistryFile, Status = CmiAddValueToKey(RegistryFile,
KeyBlock, KeyBlock,
ValueName->Buffer, ValueName2,
Type, Type,
Data, Data,
DataSize); DataSize);
@ -1300,6 +1395,10 @@ NtDeleteValueKey (
PKEY_OBJECT KeyObject; PKEY_OBJECT KeyObject;
PREGISTRY_FILE RegistryFile; PREGISTRY_FILE RegistryFile;
PKEY_BLOCK KeyBlock; PKEY_BLOCK KeyBlock;
char ValueName2[MAX_PATH];
wcstombs(ValueName2,ValueName->Buffer,ValueName->Length);
ValueName2[ValueName->Length]=0;
/* Verify that the handle is valid and is a registry key */ /* Verify that the handle is valid and is a registry key */
Status = ObReferenceObjectByHandle(KeyHandle, Status = ObReferenceObjectByHandle(KeyHandle,
@ -1318,7 +1417,7 @@ NtDeleteValueKey (
RegistryFile = KeyObject->RegistryFile; RegistryFile = KeyObject->RegistryFile;
Status = CmiDeleteValueFromKey(RegistryFile, Status = CmiDeleteValueFromKey(RegistryFile,
KeyBlock, KeyBlock,
ValueName->Buffer); ValueName2);
ObDereferenceObject(KeyObject); ObDereferenceObject(KeyObject);
return Status; return Status;
@ -1522,105 +1621,82 @@ static NTSTATUS CmiObjectParse(PVOID ParsedObject,
PWSTR *Path, PWSTR *Path,
POBJECT_TYPE ObjectType) POBJECT_TYPE ObjectType)
{ {
NTSTATUS Status; CHAR cPath[MAX_PATH];
/* FIXME: this should be allocated based on the largest subkey name */ PWSTR end;
CHAR CurKeyName[260]; PKEY_OBJECT FoundObject;
PWSTR Remainder, NextSlash; PKEY_OBJECT ParsedKey=ParsedObject;
PREGISTRY_FILE RegistryFile; PKEY_BLOCK SubKeyBlock;
PKEY_OBJECT NewKeyObject; NTSTATUS Status;
HANDLE KeyHandle; HANDLE KeyHandle;
PKEY_BLOCK CurKeyBlock, SubKeyBlock; DPRINT("CmiObjectParse Object %x Path %S FullPath %S\n",ParsedObject
, *Path,FullPath->Buffer);
Status = STATUS_SUCCESS; *NextObject = NULL;
if ((*Path) == NULL)
/* FIXME: it should probably get this from ParsedObject */ {
RegistryFile = CmiVolatileFile; return STATUS_UNSUCCESSFUL;
}
/* Scan key object list for key already open */
NewKeyObject = CmiScanKeyList((*Path) + 1); end = wcschr((*Path)+1, '\\');
if (NewKeyObject != NULL) if (end != NULL)
{ {
/* Return reference if found */ *end = 0;
ObReferenceObjectByPointer(NewKeyObject, }
STANDARD_RIGHTS_REQUIRED, wcstombs(cPath,(*Path)+1,wcslen((*Path)+1));
NULL, cPath[wcslen( (*Path)+1)]=0;
UserMode); FoundObject = CmiScanKeyList(ParsedKey,cPath);
*Path = NULL; if (FoundObject == NULL)
{
// return NewKeyObject; Status = CmiScanForSubKey(ParsedKey->RegistryFile,
//FIXME ParsedKey->KeyBlock,
return Status;
}
CurKeyBlock = CmiGetBlock(RegistryFile,
RegistryFile->HeaderBlock->RootKeyBlock);
/* Loop through each key level and find the needed subkey */
Remainder = (*Path) + 1;
while (NT_SUCCESS(Status) && *Remainder != 0)
{
NextSlash = wcschr(Remainder, L'\\');
/* Copy just the current subkey name to a buffer */
if (NextSlash != NULL)
{
wcstombs(CurKeyName, Remainder, NextSlash - Remainder);
CurKeyName[NextSlash - Remainder] = 0;
}
else
{
wcstombs(CurKeyName, Remainder, wcslen(Remainder) + 1);
}
/* Verify existance of CurKeyName */
Status = CmiScanForSubKey(RegistryFile,
CurKeyBlock,
&SubKeyBlock, &SubKeyBlock,
CurKeyName, cPath,
STANDARD_RIGHTS_REQUIRED); 0);
if (!NT_SUCCESS(Status)) if(!NT_SUCCESS(Status) || SubKeyBlock == NULL)
{ {
continue; if (end != NULL)
} {
if (SubKeyBlock == NULL) *end = '\\';
{ }
Status = STATUS_UNSUCCESSFUL; return STATUS_UNSUCCESSFUL;
continue; }
} /* Create new key object and put into linked list */
CmiReleaseBlock(RegistryFile, CurKeyBlock); FoundObject = ObCreateObject(&KeyHandle,
CurKeyBlock = SubKeyBlock; STANDARD_RIGHTS_REQUIRED,
NULL,
CmiKeyType);
if (FoundObject == NULL)
{
//FIXME : return the good error code
return STATUS_UNSUCCESSFUL;
}
FoundObject->Flags = 0;
FoundObject->Name = SubKeyBlock->Name;
FoundObject->NameSize = SubKeyBlock->NameSize;
FoundObject->KeyBlock = SubKeyBlock;
FoundObject->RegistryFile = ParsedKey->RegistryFile;
CmiAddKeyToList(ParsedKey,FoundObject);
}
ObReferenceObjectByPointer(FoundObject,
STANDARD_RIGHTS_REQUIRED,
NULL,
UserMode);
if (end != NULL)
{
*end = '\\';
*Path = end;
}
else
{
*Path = NULL;
}
*NextObject = FoundObject;
return STATUS_SUCCESS;
if (NextSlash != NULL)
{
Remainder = NextSlash + 1;
}
else
{
Remainder = NULL;
}
}
/* Create new key object and put into linked list */
NewKeyObject = ObCreateObject(&KeyHandle,
STANDARD_RIGHTS_REQUIRED,
NULL,
CmiKeyType);
if (NewKeyObject == NULL)
{
//FIXME : return the good error code
return STATUS_UNSUCCESSFUL;
}
NewKeyObject->Flags = 0;
NewKeyObject->Name = ExAllocatePool(NonPagedPool,
wcslen(*Path) * sizeof(WCHAR));
wcscpy(NewKeyObject->Name, (*Path) + 1);
NewKeyObject->KeyBlock = CurKeyBlock;
NewKeyObject->RegistryFile = RegistryFile;
CmiAddKeyToList(NewKeyObject);
*Path = (Remainder != NULL) ? Remainder - 1 : NULL;
NextObject = (PVOID)NewKeyObject;
return STATUS_SUCCESS;
} }
static VOID static VOID
@ -1710,7 +1786,7 @@ CmiBuildKeyPath(PWSTR *KeyPath, POBJECT_ATTRIBUTES ObjectAttributes)
KeyObject = (PKEY_OBJECT) ObjectBody; KeyObject = (PKEY_OBJECT) ObjectBody;
/* Add size of Name from RootDirectory object to KeyNameSize */ /* Add size of Name from RootDirectory object to KeyNameSize */
KeyNameSize = wcslen(KeyObject->Name) * sizeof(WCHAR); KeyNameSize = (KeyObject->NameSize) * sizeof(WCHAR);
/* Add 1 to KeyNamesize for '\\' */ /* Add 1 to KeyNamesize for '\\' */
KeyNameSize += sizeof(WCHAR); KeyNameSize += sizeof(WCHAR);
@ -1760,10 +1836,10 @@ CmiBuildKeyPath(PWSTR *KeyPath, POBJECT_ATTRIBUTES ObjectAttributes)
KeyObject = (PKEY_OBJECT) ObjectBody; KeyObject = (PKEY_OBJECT) ObjectBody;
/* Copy Name from RootDirectory object to KeyNameBuf */ /* Copy Name from RootDirectory object to KeyNameBuf */
wcscpy(KeyNameBuf, KeyObject->Name); mbstowcs(KeyNameBuf, KeyObject->Name,KeyObject->NameSize);
/* Append '\\' onto KeyNameBuf */ /* Append '\\' onto KeyNameBuf */
wcscat(KeyNameBuf, L"\\"); KeyNameBuf[KeyObject->NameSize]=0;
/* Append ObjectName onto KeyNameBuf */ /* Append ObjectName onto KeyNameBuf */
wcscat(KeyNameBuf, ObjectAttributes->ObjectName->Buffer); wcscat(KeyNameBuf, ObjectAttributes->ObjectName->Buffer);
@ -1781,13 +1857,25 @@ CmiBuildKeyPath(PWSTR *KeyPath, POBJECT_ATTRIBUTES ObjectAttributes)
} }
static VOID static VOID
CmiAddKeyToList(PKEY_OBJECT NewKey) CmiAddKeyToList(PKEY_OBJECT ParentKey,PKEY_OBJECT NewKey)
{ {
KIRQL OldIrql; KIRQL OldIrql;
KeAcquireSpinLock(&CmiKeyListLock, &OldIrql); KeAcquireSpinLock(&CmiKeyListLock, &OldIrql);
NewKey->NextKey = CmiKeyList; if (ParentKey->SizeOfSubKeys <= ParentKey->NumberOfSubKeys)
CmiKeyList = NewKey; {
PKEY_OBJECT *tmpSubKeys = ExAllocatePool(PagedPool
, (ParentKey->KeyBlock->NumberOfSubKeys+1) * sizeof(DWORD));
if(ParentKey->NumberOfSubKeys > 0)
memcpy(tmpSubKeys,ParentKey->SubKeys
,ParentKey->KeyBlock->NumberOfSubKeys*sizeof(DWORD));
if(ParentKey->SubKeys) ExFreePool(ParentKey->SubKeys);
ParentKey->SubKeys=tmpSubKeys;
ParentKey->SizeOfSubKeys = ParentKey->NumberOfSubKeys+1;
}
/* FIXME : please maintain the list in alphabetic order */
ParentKey->SubKeys[ParentKey->NumberOfSubKeys++] = NewKey;
NewKey->ParentKey = ParentKey;
KeReleaseSpinLock(&CmiKeyListLock, OldIrql); KeReleaseSpinLock(&CmiKeyListLock, OldIrql);
} }
@ -1795,43 +1883,48 @@ static VOID
CmiRemoveKeyFromList(PKEY_OBJECT KeyToRemove) CmiRemoveKeyFromList(PKEY_OBJECT KeyToRemove)
{ {
KIRQL OldIrql; KIRQL OldIrql;
PKEY_OBJECT CurKey; PKEY_OBJECT ParentKey;
DWORD Index;
ParentKey=KeyToRemove->ParentKey;
KeAcquireSpinLock(&CmiKeyListLock, &OldIrql); KeAcquireSpinLock(&CmiKeyListLock, &OldIrql);
if (CmiKeyList == KeyToRemove) for (Index=0; Index < ParentKey->NumberOfSubKeys; Index++)
{
if(ParentKey->SubKeys[Index] == KeyToRemove)
{ {
CmiKeyList = CmiKeyList->NextKey; memcpy(&ParentKey->SubKeys[Index]
} ,&ParentKey->SubKeys[Index+1]
else ,(ParentKey->NumberOfSubKeys-Index-1)*sizeof(PKEY_OBJECT));
{ ParentKey->NumberOfSubKeys--;
CurKey = CmiKeyList; break;
while (CurKey != NULL && CurKey->NextKey != KeyToRemove)
{
CurKey = CurKey->NextKey;
}
if (CurKey != NULL)
{
CurKey->NextKey = KeyToRemove->NextKey;
}
} }
}
KeReleaseSpinLock(&CmiKeyListLock, OldIrql); KeReleaseSpinLock(&CmiKeyListLock, OldIrql);
} }
static PKEY_OBJECT static PKEY_OBJECT
CmiScanKeyList(PWSTR KeyName) CmiScanKeyList(PKEY_OBJECT Parent,PCHAR KeyName)
{ {
KIRQL OldIrql; KIRQL OldIrql;
PKEY_OBJECT CurKey; PKEY_OBJECT CurKey;
DWORD Index;
WORD NameSize;
NameSize=strlen(KeyName);
KeAcquireSpinLock(&CmiKeyListLock, &OldIrql); KeAcquireSpinLock(&CmiKeyListLock, &OldIrql);
CurKey = CmiKeyList; for (Index=0; Index < Parent->NumberOfSubKeys; Index++)
while (CurKey != NULL && wcscmp(KeyName, CurKey->Name) != 0) {
CurKey=Parent->SubKeys[Index];
if( NameSize == CurKey->NameSize
&& !memcmp(KeyName,CurKey->Name,NameSize))
{ {
CurKey = CurKey->NextKey; KeReleaseSpinLock(&CmiKeyListLock, OldIrql);
return CurKey;
} }
}
KeReleaseSpinLock(&CmiKeyListLock, OldIrql); KeReleaseSpinLock(&CmiKeyListLock, OldIrql);
return CurKey; return NULL;
} }
static PREGISTRY_FILE static PREGISTRY_FILE
@ -2032,6 +2125,7 @@ CHECKPOINT;
return Status; return Status;
} }
#ifdef xxx
static NTSTATUS static NTSTATUS
CmiFindKey(IN PREGISTRY_FILE RegistryFile, CmiFindKey(IN PREGISTRY_FILE RegistryFile,
IN PWSTR KeyNameBuf, IN PWSTR KeyNameBuf,
@ -2107,6 +2201,7 @@ CmiFindKey(IN PREGISTRY_FILE RegistryFile,
return Status; return Status;
} }
#endif
static ULONG static ULONG
CmiGetMaxNameLength(PREGISTRY_FILE RegistryFile, CmiGetMaxNameLength(PREGISTRY_FILE RegistryFile,
@ -2250,28 +2345,27 @@ CmiScanForSubKey(IN PREGISTRY_FILE RegistryFile,
PKEY_BLOCK CurSubKeyBlock; PKEY_BLOCK CurSubKeyBlock;
WORD KeyLength = strlen(KeyName); WORD KeyLength = strlen(KeyName);
DPRINT("CmiScanForSubKey %s,file %x\n",KeyName,RegistryFile);
HashBlock = CmiGetBlock(RegistryFile, KeyBlock->HashTableOffset); HashBlock = CmiGetBlock(RegistryFile, KeyBlock->HashTableOffset);
*SubKeyBlock = NULL; *SubKeyBlock = NULL;
if (HashBlock == NULL) if (HashBlock == NULL)
{ {
return STATUS_SUCCESS; return STATUS_SUCCESS;
} }
DPRINT("hash=%x,hash.id=%x\n",HashBlock,HashBlock->SubBlockId); for (Idx = 0; Idx < HashBlock->HashTableSize; Idx++)
// for (Idx = 0; Idx < HashBlock->HashTableSize; Idx++) // for (Idx = 0; Idx < KeyBlock->NumberOfSubKeys; Idx++)
for (Idx = 0; Idx < KeyBlock->NumberOfSubKeys; Idx++)
{ {
DPRINT("&hash=%x,hash=%4.4s\n",&HashBlock->Table[Idx].HashValue,&HashBlock->Table[Idx].HashValue);
if (HashBlock->Table[Idx].KeyOffset != 0 && if (HashBlock->Table[Idx].KeyOffset != 0 &&
HashBlock->Table[Idx].KeyOffset != -1 && HashBlock->Table[Idx].KeyOffset != -1 &&
!strncmp(KeyName, (PCHAR) &HashBlock->Table[Idx].HashValue, 4)) !strncmp(KeyName, (PCHAR) &HashBlock->Table[Idx].HashValue, 4))
{ {
CHECKPOINT;
CurSubKeyBlock = CmiGetBlock(RegistryFile, CurSubKeyBlock = CmiGetBlock(RegistryFile,
HashBlock->Table[Idx].KeyOffset); HashBlock->Table[Idx].KeyOffset);
if ( CurSubKeyBlock->NameSize == KeyLength if ( CurSubKeyBlock->NameSize == KeyLength
&& !memcmp(KeyName, CurSubKeyBlock->Name, KeyLength)) && !memcmp(KeyName, CurSubKeyBlock->Name, KeyLength))
{ {
*SubKeyBlock = CurSubKeyBlock; *SubKeyBlock = CurSubKeyBlock;
DPRINT("CmiScanForSubKey : found %s\n",KeyName);
break; break;
} }
else else
@ -2280,7 +2374,6 @@ CHECKPOINT;
} }
} }
} }
CHECKPOINT;
CmiReleaseBlock(RegistryFile, HashBlock); CmiReleaseBlock(RegistryFile, HashBlock);
@ -2352,7 +2445,7 @@ CmiAddSubKey(PREGISTRY_FILE RegistryFile,
if (NT_SUCCESS(Status)) if (NT_SUCCESS(Status))
{ {
KeyBlock->NumberOfSubKeys++; KeyBlock->NumberOfSubKeys++;
*SubKeyBlock = NewKeyBlock; if(SubKeyBlock) *SubKeyBlock = NewKeyBlock;
} }
CmiReleaseBlock(RegistryFile, HashBlock); CmiReleaseBlock(RegistryFile, HashBlock);
@ -2362,7 +2455,7 @@ CmiAddSubKey(PREGISTRY_FILE RegistryFile,
static NTSTATUS static NTSTATUS
CmiScanKeyForValue(IN PREGISTRY_FILE RegistryFile, CmiScanKeyForValue(IN PREGISTRY_FILE RegistryFile,
IN PKEY_BLOCK KeyBlock, IN PKEY_BLOCK KeyBlock,
IN PWSTR ValueName, IN PCHAR ValueName,
OUT PVALUE_BLOCK *ValueBlock) OUT PVALUE_BLOCK *ValueBlock)
{ {
ULONG Idx; ULONG Idx;
@ -2381,7 +2474,8 @@ CmiScanKeyForValue(IN PREGISTRY_FILE RegistryFile,
CurValueBlock = CmiGetBlock(RegistryFile, CurValueBlock = CmiGetBlock(RegistryFile,
ValueListBlock->Values[Idx]); ValueListBlock->Values[Idx]);
if (CurValueBlock != NULL && if (CurValueBlock != NULL &&
!wcscmp(CurValueBlock->Name, ValueName)) CurValueBlock->NameSize == strlen(ValueName) &&
!memcmp(CurValueBlock->Name, ValueName,strlen(ValueName)))
{ {
*ValueBlock = CurValueBlock; *ValueBlock = CurValueBlock;
break; break;
@ -2430,7 +2524,7 @@ CmiGetValueFromKeyByIndex(IN PREGISTRY_FILE RegistryFile,
static NTSTATUS static NTSTATUS
CmiAddValueToKey(IN PREGISTRY_FILE RegistryFile, CmiAddValueToKey(IN PREGISTRY_FILE RegistryFile,
IN PKEY_BLOCK KeyBlock, IN PKEY_BLOCK KeyBlock,
IN PWSTR ValueNameBuf, IN PCHAR ValueNameBuf,
IN ULONG Type, IN ULONG Type,
IN PVOID Data, IN PVOID Data,
IN ULONG DataSize) IN ULONG DataSize)
@ -2499,7 +2593,7 @@ CmiAddValueToKey(IN PREGISTRY_FILE RegistryFile,
static NTSTATUS static NTSTATUS
CmiDeleteValueFromKey(IN PREGISTRY_FILE RegistryFile, CmiDeleteValueFromKey(IN PREGISTRY_FILE RegistryFile,
IN PKEY_BLOCK KeyBlock, IN PKEY_BLOCK KeyBlock,
IN PWSTR ValueName) IN PCHAR ValueName)
{ {
ULONG Idx; ULONG Idx;
PVALUE_LIST_BLOCK ValueListBlock; PVALUE_LIST_BLOCK ValueListBlock;
@ -2516,7 +2610,8 @@ CmiDeleteValueFromKey(IN PREGISTRY_FILE RegistryFile,
CurValueBlock = CmiGetBlock(RegistryFile, CurValueBlock = CmiGetBlock(RegistryFile,
ValueListBlock->Values[Idx]); ValueListBlock->Values[Idx]);
if (CurValueBlock != NULL && if (CurValueBlock != NULL &&
!wcscmp(CurValueBlock->Name, ValueName)) CurValueBlock->NameSize == strlen(ValueName) &&
!memcmp(CurValueBlock->Name, ValueName,strlen(ValueName)))
{ {
if (KeyBlock->NumberOfValues - 1 < Idx) if (KeyBlock->NumberOfValues - 1 < Idx)
{ {
@ -2720,7 +2815,7 @@ CmiDestroyHashTableBlock(PREGISTRY_FILE RegistryFile,
static NTSTATUS static NTSTATUS
CmiAllocateValueBlock(PREGISTRY_FILE RegistryFile, CmiAllocateValueBlock(PREGISTRY_FILE RegistryFile,
PVALUE_BLOCK *ValueBlock, PVALUE_BLOCK *ValueBlock,
IN PWSTR ValueNameBuf, IN PCHAR ValueNameBuf,
IN ULONG Type, IN ULONG Type,
IN PVOID Data, IN PVOID Data,
IN ULONG DataSize) IN ULONG DataSize)
@ -2735,7 +2830,7 @@ CmiAllocateValueBlock(PREGISTRY_FILE RegistryFile,
/* Handle volatile files first */ /* Handle volatile files first */
if (RegistryFile->Filename == NULL) if (RegistryFile->Filename == NULL)
{ {
NewValueSize = sizeof(VALUE_BLOCK) + wcslen(ValueNameBuf)* sizeof(WCHAR); NewValueSize = sizeof(VALUE_BLOCK) + strlen(ValueNameBuf);
NewValueBlock = ExAllocatePool(NonPagedPool, NewValueSize); NewValueBlock = ExAllocatePool(NonPagedPool, NewValueSize);
if (NewValueBlock == NULL) if (NewValueBlock == NULL)
{ {
@ -2745,8 +2840,8 @@ CmiAllocateValueBlock(PREGISTRY_FILE RegistryFile,
{ {
RtlZeroMemory(NewValueBlock, NewValueSize); RtlZeroMemory(NewValueBlock, NewValueSize);
NewValueBlock->SubBlockId = REG_VALUE_BLOCK_ID; NewValueBlock->SubBlockId = REG_VALUE_BLOCK_ID;
NewValueBlock->NameSize = wcslen(ValueNameBuf); NewValueBlock->NameSize = strlen(ValueNameBuf);
wcscpy(NewValueBlock->Name, ValueNameBuf); memcpy(NewValueBlock->Name, ValueNameBuf,strlen(ValueNameBuf));
NewValueBlock->DataType = Type; NewValueBlock->DataType = Type;
NewValueBlock->DataSize = DataSize; NewValueBlock->DataSize = DataSize;
Status = CmiAllocateBlock(RegistryFile, Status = CmiAllocateBlock(RegistryFile,
@ -2954,16 +3049,13 @@ CmiGetBlock(PREGISTRY_FILE RegistryFile,
RegistryFile->BlockListSize ++; RegistryFile->BlockListSize ++;
RegistryFile->BlockList [CurBlock] RegistryFile->BlockList [CurBlock]
= ExAllocatePool(NonPagedPool,tmpHeap.BlockSize); = ExAllocatePool(NonPagedPool,tmpHeap.BlockSize);
CHECKPOINT;
Status = ZwReadFile(RegistryFile->FileHandle, Status = ZwReadFile(RegistryFile->FileHandle,
0, 0, 0, 0, 0, 0, 0, 0,
RegistryFile->BlockList[CurBlock ], RegistryFile->BlockList[CurBlock ],
tmpHeap.BlockSize, tmpHeap.BlockSize,
&fileOffset, 0); &fileOffset, 0);
DPRINT(" read %d block file %x octets at %x, Status=%x\n",CurBlock,tmpHeap.BlockSize,fileOffset.u.LowPart,Status);
Block = ((char *)RegistryFile->BlockList[CurBlock] Block = ((char *)RegistryFile->BlockList[CurBlock]
+(BlockOffset - RegistryFile->BlockList[CurBlock]->BlockOffset)); +(BlockOffset - RegistryFile->BlockList[CurBlock]->BlockOffset));
DPRINT(" hbin at %x, block at %x\n",RegistryFile->BlockList[CurBlock],Block);
} }
return Block; return Block;