mirror of
https://github.com/reactos/reactos.git
synced 2025-08-03 14:05:42 +00:00
Implemented [Nt/Zw]QueryMultipleValueKey().
svn path=/trunk/; revision=2607
This commit is contained in:
parent
52d2359910
commit
1d0d9fbf9f
3 changed files with 175 additions and 83 deletions
|
@ -14,7 +14,7 @@ typedef enum _KEY_INFORMATION_CLASS
|
|||
KeyFullInformation
|
||||
} KEY_INFORMATION_CLASS;
|
||||
|
||||
typedef struct _KEY_BASIC_INFORMATION
|
||||
typedef struct _KEY_BASIC_INFORMATION
|
||||
{
|
||||
LARGE_INTEGER LastWriteTime;
|
||||
ULONG TitleIndex;
|
||||
|
@ -22,7 +22,7 @@ typedef struct _KEY_BASIC_INFORMATION
|
|||
WCHAR Name[1];
|
||||
} KEY_BASIC_INFORMATION, *PKEY_BASIC_INFORMATION;
|
||||
|
||||
typedef struct _KEY_FULL_INFORMATION
|
||||
typedef struct _KEY_FULL_INFORMATION
|
||||
{
|
||||
LARGE_INTEGER LastWriteTime;
|
||||
ULONG TitleIndex;
|
||||
|
@ -37,7 +37,7 @@ typedef struct _KEY_FULL_INFORMATION
|
|||
WCHAR Class[1];
|
||||
} KEY_FULL_INFORMATION, *PKEY_FULL_INFORMATION;
|
||||
|
||||
typedef struct _KEY_NODE_INFORMATION
|
||||
typedef struct _KEY_NODE_INFORMATION
|
||||
{
|
||||
LARGE_INTEGER LastWriteTime;
|
||||
ULONG TitleIndex;
|
||||
|
@ -61,7 +61,7 @@ typedef enum _KEY_VALUE_INFORMATION_CLASS
|
|||
KeyValuePartialInformation
|
||||
} KEY_VALUE_INFORMATION_CLASS;
|
||||
|
||||
typedef struct _KEY_VALUE_BASIC_INFORMATION
|
||||
typedef struct _KEY_VALUE_BASIC_INFORMATION
|
||||
{
|
||||
ULONG TitleIndex;
|
||||
ULONG Type;
|
||||
|
@ -69,7 +69,7 @@ typedef struct _KEY_VALUE_BASIC_INFORMATION
|
|||
WCHAR Name[1];
|
||||
} KEY_VALUE_BASIC_INFORMATION, *PKEY_VALUE_BASIC_INFORMATION;
|
||||
|
||||
typedef struct _KEY_VALUE_FULL_INFORMATION
|
||||
typedef struct _KEY_VALUE_FULL_INFORMATION
|
||||
{
|
||||
ULONG TitleIndex;
|
||||
ULONG Type;
|
||||
|
@ -79,7 +79,7 @@ typedef struct _KEY_VALUE_FULL_INFORMATION
|
|||
WCHAR Name[1];
|
||||
} KEY_VALUE_FULL_INFORMATION, *PKEY_VALUE_FULL_INFORMATION;
|
||||
|
||||
typedef struct _KEY_VALUE_PARTIAL_INFORMATION
|
||||
typedef struct _KEY_VALUE_PARTIAL_INFORMATION
|
||||
{
|
||||
ULONG TitleIndex;
|
||||
ULONG Type;
|
||||
|
@ -91,4 +91,13 @@ typedef struct _KEY_VALUE_PARTIAL_INFORMATION
|
|||
#define REG_OPTION_BACKUP_RESTORE 0x00000004
|
||||
|
||||
|
||||
/* used by [Nt/Zw]QueryMultipleValueKey */
|
||||
|
||||
typedef struct _KEY_VALUE_ENTRY
|
||||
{
|
||||
PUNICODE_STRING ValueName;
|
||||
ULONG DataLength;
|
||||
ULONG DataOffset;
|
||||
ULONG Type;
|
||||
} KEY_VALUE_ENTRY, *PKEY_VALUE_ENTRY;
|
||||
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
|
||||
/* $Id: zw.h,v 1.48 2001/11/20 02:29:43 dwelch Exp $
|
||||
/* $Id: zw.h,v 1.49 2002/02/06 01:22:32 ekohl Exp $
|
||||
*
|
||||
* COPYRIGHT: See COPYING in the top level directory
|
||||
* PROJECT: ReactOS kernel
|
||||
|
@ -3075,7 +3075,7 @@ NtQueryKey(
|
|||
IN KEY_INFORMATION_CLASS KeyInformationClass,
|
||||
OUT PVOID KeyInformation,
|
||||
IN ULONG Length,
|
||||
OUT PULONG ResultLength
|
||||
OUT PULONG ResultLength
|
||||
);
|
||||
|
||||
NTSTATUS
|
||||
|
@ -3085,7 +3085,7 @@ ZwQueryKey(
|
|||
IN KEY_INFORMATION_CLASS KeyInformationClass,
|
||||
OUT PVOID KeyInformation,
|
||||
IN ULONG Length,
|
||||
OUT PULONG ResultLength
|
||||
OUT PULONG ResultLength
|
||||
);
|
||||
|
||||
|
||||
|
@ -3094,24 +3094,24 @@ ZwQueryKey(
|
|||
NTSTATUS
|
||||
STDCALL
|
||||
NtQueryMultipleValueKey(
|
||||
HANDLE KeyHandle,
|
||||
PWVALENT ListOfValuesToQuery,
|
||||
ULONG NumberOfItems,
|
||||
PVOID MultipleValueInformation,
|
||||
ULONG Length,
|
||||
PULONG ReturnLength
|
||||
);
|
||||
IN HANDLE KeyHandle,
|
||||
IN OUT PKEY_VALUE_ENTRY ValueList,
|
||||
IN ULONG NumberOfValues,
|
||||
OUT PVOID Buffer,
|
||||
IN OUT PULONG Length,
|
||||
OUT PULONG ReturnLength
|
||||
);
|
||||
|
||||
NTSTATUS
|
||||
STDCALL
|
||||
ZwQueryMultipleValueKey(
|
||||
HANDLE KeyHandle,
|
||||
PWVALENT ListOfValuesToQuery,
|
||||
ULONG NumberOfItems,
|
||||
PVOID MultipleValueInformation,
|
||||
ULONG Length,
|
||||
PULONG ReturnLength
|
||||
);
|
||||
IN HANDLE KeyHandle,
|
||||
IN OUT PKEY_VALUE_ENTRY ValueList,
|
||||
IN ULONG NumberOfValues,
|
||||
OUT PVOID Buffer,
|
||||
IN OUT PULONG Length,
|
||||
OUT PULONG ReturnLength
|
||||
);
|
||||
|
||||
/*
|
||||
* FUNCTION: Queries the information of a mutant object.
|
||||
|
|
|
@ -704,15 +704,12 @@ DPRINT("NTOpenKey2 : after ObFindObject\n");
|
|||
}
|
||||
|
||||
|
||||
NTSTATUS
|
||||
STDCALL
|
||||
NtQueryKey (
|
||||
IN HANDLE KeyHandle,
|
||||
IN KEY_INFORMATION_CLASS KeyInformationClass,
|
||||
OUT PVOID KeyInformation,
|
||||
IN ULONG Length,
|
||||
OUT PULONG ResultLength
|
||||
)
|
||||
NTSTATUS STDCALL
|
||||
NtQueryKey(IN HANDLE KeyHandle,
|
||||
IN KEY_INFORMATION_CLASS KeyInformationClass,
|
||||
OUT PVOID KeyInformation,
|
||||
IN ULONG Length,
|
||||
OUT PULONG ResultLength)
|
||||
{
|
||||
NTSTATUS Status;
|
||||
PKEY_OBJECT KeyObject;
|
||||
|
@ -1136,19 +1133,17 @@ NtSetValueKey (
|
|||
return Status;
|
||||
}
|
||||
|
||||
NTSTATUS
|
||||
STDCALL
|
||||
NtDeleteValueKey (
|
||||
IN HANDLE KeyHandle,
|
||||
IN PUNICODE_STRING ValueName
|
||||
)
|
||||
|
||||
NTSTATUS STDCALL
|
||||
NtDeleteValueKey(IN HANDLE KeyHandle,
|
||||
IN PUNICODE_STRING ValueName)
|
||||
{
|
||||
NTSTATUS Status;
|
||||
PKEY_OBJECT KeyObject;
|
||||
PREGISTRY_FILE RegistryFile;
|
||||
PKEY_BLOCK KeyBlock;
|
||||
char ValueName2[MAX_PATH];
|
||||
// KIRQL OldIrql;
|
||||
NTSTATUS Status;
|
||||
PKEY_OBJECT KeyObject;
|
||||
PREGISTRY_FILE RegistryFile;
|
||||
PKEY_BLOCK KeyBlock;
|
||||
char ValueName2[MAX_PATH];
|
||||
// KIRQL OldIrql;
|
||||
|
||||
wcstombs(ValueName2,ValueName->Buffer,ValueName->Length>>1);
|
||||
ValueName2[ValueName->Length>>1]=0;
|
||||
|
@ -1178,26 +1173,21 @@ NtDeleteValueKey (
|
|||
return Status;
|
||||
}
|
||||
|
||||
NTSTATUS
|
||||
STDCALL
|
||||
NtLoadKey (
|
||||
PHANDLE KeyHandle,
|
||||
POBJECT_ATTRIBUTES ObjectAttributes
|
||||
)
|
||||
|
||||
NTSTATUS STDCALL
|
||||
NtLoadKey(PHANDLE KeyHandle,
|
||||
POBJECT_ATTRIBUTES ObjectAttributes)
|
||||
{
|
||||
return NtLoadKey2(KeyHandle,
|
||||
ObjectAttributes,
|
||||
0);
|
||||
return(NtLoadKey2(KeyHandle,
|
||||
ObjectAttributes,
|
||||
0));
|
||||
}
|
||||
|
||||
|
||||
NTSTATUS
|
||||
STDCALL
|
||||
NtLoadKey2 (
|
||||
PHANDLE KeyHandle,
|
||||
POBJECT_ATTRIBUTES ObjectAttributes,
|
||||
ULONG Unknown3
|
||||
)
|
||||
NTSTATUS STDCALL
|
||||
NtLoadKey2(IN PHANDLE KeyHandle,
|
||||
IN POBJECT_ATTRIBUTES ObjectAttributes,
|
||||
IN ULONG Flags)
|
||||
{
|
||||
UNIMPLEMENTED;
|
||||
}
|
||||
|
@ -1222,18 +1212,118 @@ NtNotifyChangeKey (
|
|||
}
|
||||
|
||||
|
||||
NTSTATUS
|
||||
STDCALL
|
||||
NtQueryMultipleValueKey (
|
||||
IN HANDLE KeyHandle,
|
||||
IN PWVALENT ListOfValuesToQuery,
|
||||
IN ULONG NumberOfItems,
|
||||
OUT PVOID MultipleValueInformation,
|
||||
IN ULONG Length,
|
||||
OUT PULONG ReturnLength
|
||||
)
|
||||
NTSTATUS STDCALL
|
||||
NtQueryMultipleValueKey(IN HANDLE KeyHandle,
|
||||
IN OUT PKEY_VALUE_ENTRY ValueList,
|
||||
IN ULONG NumberOfValues,
|
||||
OUT PVOID Buffer,
|
||||
IN OUT PULONG Length,
|
||||
OUT PULONG ReturnLength)
|
||||
{
|
||||
UNIMPLEMENTED;
|
||||
PKEY_OBJECT KeyObject;
|
||||
PREGISTRY_FILE RegistryFile;
|
||||
PKEY_BLOCK KeyBlock;
|
||||
PVALUE_BLOCK ValueBlock;
|
||||
PDATA_BLOCK DataBlock;
|
||||
UCHAR ValueName[MAX_PATH];
|
||||
PUCHAR DataPtr;
|
||||
ULONG BufferLength;
|
||||
ULONG i;
|
||||
NTSTATUS Status;
|
||||
|
||||
/* Verify that the handle is valid and is a registry key */
|
||||
Status = ObReferenceObjectByHandle(KeyHandle,
|
||||
KEY_QUERY_VALUE,
|
||||
CmiKeyType,
|
||||
UserMode,
|
||||
(PVOID *)&KeyObject,
|
||||
NULL);
|
||||
if (!NT_SUCCESS(Status))
|
||||
{
|
||||
DPRINT("ObReferenceObjectByHandle() failed with status %x\n", Status);
|
||||
return(Status);
|
||||
}
|
||||
|
||||
/* Get pointer to KeyBlock */
|
||||
KeyBlock = KeyObject->KeyBlock;
|
||||
RegistryFile = KeyObject->RegistryFile;
|
||||
|
||||
DataPtr = (PUCHAR)Buffer;
|
||||
|
||||
for (i = 0; i < NumberOfValues; i++)
|
||||
{
|
||||
wcstombs(ValueName,
|
||||
ValueList[i].ValueName->Buffer,
|
||||
ValueList[i].ValueName->Length >> 1);
|
||||
ValueName[ValueList[i].ValueName->Length >> 1] = 0;
|
||||
|
||||
DPRINT("ValueName: '%s'\n", ValueName);
|
||||
|
||||
/* Get Value block of interest */
|
||||
Status = CmiScanKeyForValue(RegistryFile,
|
||||
KeyBlock,
|
||||
ValueName,
|
||||
&ValueBlock,
|
||||
NULL);
|
||||
if (!NT_SUCCESS(Status))
|
||||
{
|
||||
DPRINT("CmiScanKeyForValue() failed with status %x\n", Status);
|
||||
break;
|
||||
}
|
||||
else if (ValueBlock == NULL)
|
||||
{
|
||||
Status = STATUS_OBJECT_NAME_NOT_FOUND;
|
||||
break;
|
||||
}
|
||||
|
||||
BufferLength = (BufferLength + 3) & 0xfffffffc;
|
||||
|
||||
if (BufferLength + (ValueBlock->DataSize & LONG_MAX) <= *Length)
|
||||
{
|
||||
DataPtr = (PUCHAR)(((ULONG)DataPtr + 3) & 0xfffffffc);
|
||||
|
||||
ValueList[i].Type = ValueBlock->DataType;
|
||||
ValueList[i].DataLength = ValueBlock->DataSize & LONG_MAX;
|
||||
ValueList[i].DataOffset = (ULONG)DataPtr - (ULONG)Buffer;
|
||||
|
||||
if (ValueBlock->DataSize >0)
|
||||
{
|
||||
DataBlock = CmiGetBlock(RegistryFile,
|
||||
ValueBlock->DataOffset,
|
||||
NULL);
|
||||
RtlCopyMemory(DataPtr,
|
||||
DataBlock->Data,
|
||||
ValueBlock->DataSize & LONG_MAX);
|
||||
CmiReleaseBlock(RegistryFile,
|
||||
DataBlock);
|
||||
}
|
||||
else
|
||||
{
|
||||
RtlCopyMemory(DataPtr,
|
||||
&ValueBlock->DataOffset,
|
||||
ValueBlock->DataSize & LONG_MAX);
|
||||
}
|
||||
|
||||
DataPtr += ValueBlock->DataSize & LONG_MAX;
|
||||
}
|
||||
else
|
||||
{
|
||||
Status = STATUS_BUFFER_TOO_SMALL;
|
||||
}
|
||||
|
||||
BufferLength += ValueBlock->DataSize & LONG_MAX;
|
||||
}
|
||||
|
||||
if (NT_SUCCESS(Status))
|
||||
*Length = BufferLength;
|
||||
|
||||
*ReturnLength = BufferLength;
|
||||
|
||||
ObDereferenceObject(KeyObject);
|
||||
|
||||
DPRINT("Return Status 0x%X\n", Status);
|
||||
|
||||
return(Status);
|
||||
}
|
||||
|
||||
|
||||
|
@ -1285,22 +1375,15 @@ NtSetInformationKey (
|
|||
}
|
||||
|
||||
|
||||
NTSTATUS
|
||||
STDCALL
|
||||
NtUnloadKey (
|
||||
HANDLE KeyHandle
|
||||
)
|
||||
NTSTATUS STDCALL
|
||||
NtUnloadKey(IN HANDLE KeyHandle)
|
||||
{
|
||||
UNIMPLEMENTED;
|
||||
}
|
||||
|
||||
|
||||
NTSTATUS
|
||||
STDCALL
|
||||
NtInitializeRegistry (
|
||||
BOOLEAN SetUpBoot
|
||||
)
|
||||
NTSTATUS STDCALL
|
||||
NtInitializeRegistry(IN BOOLEAN SetUpBoot)
|
||||
{
|
||||
// UNIMPLEMENTED;
|
||||
return STATUS_SUCCESS;
|
||||
return(STATUS_SUCCESS);
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue