Converted the Registry to Unicode.

Link default user hive to '\Registry\User\.Default'

svn path=/trunk/; revision=4798
This commit is contained in:
Eric Kohl 2003-05-29 14:09:41 +00:00
parent 7a7e93c4ab
commit 6d2758d3b7
4 changed files with 294 additions and 231 deletions

View file

@ -18,18 +18,20 @@
#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_USERS_KEY_NAME L"\\Registry\\User" #define REG_USER_KEY_NAME L"\\Registry\\User"
#define REG_USER_KEY_NAME L"\\Registry\\User\\CurrentUser" #define REG_DEFAULT_USER_KEY_NAME L"\\Registry\\User\\.Default"
#define REG_CURRENT_USER_KEY_NAME L"\\Registry\\User\\CurrentUser"
#define SYSTEM_REG_FILE L"\\SystemRoot\\System32\\Config\\SYSTEM" #define SYSTEM_REG_FILE L"\\SystemRoot\\System32\\Config\\SYSTEM"
#define SYSTEM_LOG_FILE L"\\SystemRoot\\System32\\Config\\SYSTEM.log" #define SYSTEM_LOG_FILE L"\\SystemRoot\\System32\\Config\\SYSTEM.log"
#define SOFTWARE_REG_FILE L"\\SystemRoot\\System32\\Config\\SOFTWARE" #define SOFTWARE_REG_FILE L"\\SystemRoot\\System32\\Config\\SOFTWARE"
#define USER_REG_FILE L"\\SystemRoot\\System32\\Config\\DEFAULT" #define DEFAULT_USER_REG_FILE L"\\SystemRoot\\System32\\Config\\DEFAULT"
#define SAM_REG_FILE L"\\SystemRoot\\System32\\Config\\SAM" #define SAM_REG_FILE L"\\SystemRoot\\System32\\Config\\SAM"
#define SEC_REG_FILE L"\\SystemRoot\\System32\\Config\\SECURITY" #define SEC_REG_FILE L"\\SystemRoot\\System32\\Config\\SECURITY"
#define REG_SYSTEM_FILE_NAME L"\\SYSTEM" #define REG_SYSTEM_FILE_NAME L"\\SYSTEM"
#define REG_SOFTWARE_FILE_NAME L"\\SOFTWARE" #define REG_SOFTWARE_FILE_NAME L"\\SOFTWARE"
#define REG_USER_FILE_NAME L"\\DEFAULT" #define REG_DEFAULT_USER_FILE_NAME L"\\DEFAULT"
#define REG_SAM_FILE_NAME L"\\SAM" #define REG_SAM_FILE_NAME L"\\SAM"
#define REG_SEC_FILE_NAME L"\\SECURITY" #define REG_SEC_FILE_NAME L"\\SECURITY"
@ -45,15 +47,6 @@
#define REG_VALUE_CELL_ID 0x6b76 #define REG_VALUE_CELL_ID 0x6b76
#define REG_HIVE_ID 0x66676572 #define REG_HIVE_ID 0x66676572
#define REGISTRY_FILE_MAGIC "REGEDIT4"
#define REG_MACHINE_STD_HANDLE_NAME "HKEY_LOCAL_MACHINE"
#define REG_CLASSES_STD_HANDLE_NAME "HKEY_CLASSES_ROOT"
#define REG_USERS_STD_HANDLE_NAME "HKEY_USERS"
#define REG_USER_STD_HANDLE_NAME "HKEY_CURRENT_USER"
#define REG_CONFIG_STD_HANDLE_NAME "HKEY_CURRENT_CONFIG"
#define REG_DYN_STD_HANDLE_NAME "HKEY_DYN_DATA"
#define MAX_REG_STD_HANDLE_NAME 19
// BLOCK_OFFSET = offset in file after header block // BLOCK_OFFSET = offset in file after header block
typedef ULONG BLOCK_OFFSET; typedef ULONG BLOCK_OFFSET;

View file

@ -245,16 +245,13 @@ NtDeleteKey(IN HANDLE KeyHandle)
NTSTATUS STDCALL NTSTATUS STDCALL
NtEnumerateKey( NtEnumerateKey(IN HANDLE KeyHandle,
IN HANDLE KeyHandle,
IN ULONG Index, IN ULONG Index,
IN KEY_INFORMATION_CLASS KeyInformationClass, IN KEY_INFORMATION_CLASS KeyInformationClass,
OUT PVOID KeyInformation, OUT PVOID KeyInformation,
IN ULONG Length, IN ULONG Length,
OUT PULONG ResultLength OUT PULONG ResultLength)
)
{ {
NTSTATUS Status;
PKEY_OBJECT KeyObject; PKEY_OBJECT KeyObject;
PREGISTRY_HIVE RegistryHive; PREGISTRY_HIVE RegistryHive;
PKEY_CELL KeyCell, SubKeyCell; PKEY_CELL KeyCell, SubKeyCell;
@ -262,7 +259,9 @@ NtEnumerateKey(
PKEY_BASIC_INFORMATION BasicInformation; PKEY_BASIC_INFORMATION BasicInformation;
PKEY_NODE_INFORMATION NodeInformation; PKEY_NODE_INFORMATION NodeInformation;
PKEY_FULL_INFORMATION FullInformation; PKEY_FULL_INFORMATION FullInformation;
PDATA_CELL pClassData; PDATA_CELL ClassData;
ULONG NameSize;
NTSTATUS Status;
DPRINT("KH %x I %d KIC %x KI %x L %d RL %x\n", DPRINT("KH %x I %d KIC %x KI %x L %d RL %x\n",
KeyHandle, KeyHandle,
@ -364,8 +363,13 @@ NtEnumerateKey(
{ {
case KeyBasicInformation: case KeyBasicInformation:
/* Check size of buffer */ /* Check size of buffer */
*ResultLength = sizeof(KEY_BASIC_INFORMATION) + NameSize = SubKeyCell->NameSize;
(SubKeyCell->NameSize ) * sizeof(WCHAR); if (SubKeyCell->Flags & REG_KEY_NAME_PACKED)
{
NameSize *= sizeof(WCHAR);
}
*ResultLength = sizeof(KEY_BASIC_INFORMATION) + NameSize;
if (Length < *ResultLength) if (Length < *ResultLength)
{ {
Status = STATUS_BUFFER_OVERFLOW; Status = STATUS_BUFFER_OVERFLOW;
@ -377,18 +381,36 @@ NtEnumerateKey(
BasicInformation->LastWriteTime.u.LowPart = SubKeyCell->LastWriteTime.dwLowDateTime; BasicInformation->LastWriteTime.u.LowPart = SubKeyCell->LastWriteTime.dwLowDateTime;
BasicInformation->LastWriteTime.u.HighPart = SubKeyCell->LastWriteTime.dwHighDateTime; BasicInformation->LastWriteTime.u.HighPart = SubKeyCell->LastWriteTime.dwHighDateTime;
BasicInformation->TitleIndex = Index; BasicInformation->TitleIndex = Index;
BasicInformation->NameLength = SubKeyCell->NameSize * sizeof(WCHAR); BasicInformation->NameLength = NameSize;
mbstowcs(BasicInformation->Name,
if (SubKeyCell->Flags & REG_KEY_NAME_PACKED)
{
CmiCopyPackedName(BasicInformation->Name,
SubKeyCell->Name, SubKeyCell->Name,
SubKeyCell->NameSize * 2); SubKeyCell->NameSize);
}
else
{
RtlCopyMemory(BasicInformation->Name,
SubKeyCell->Name,
SubKeyCell->NameSize);
}
} }
break; break;
case KeyNodeInformation: case KeyNodeInformation:
/* Check size of buffer */ /* Check size of buffer */
if (SubKeyCell->Flags & REG_KEY_NAME_PACKED)
{
NameSize = SubKeyCell->NameSize * sizeof(WCHAR);
}
else
{
NameSize = SubKeyCell->NameSize;
}
*ResultLength = sizeof(KEY_NODE_INFORMATION) + *ResultLength = sizeof(KEY_NODE_INFORMATION) +
SubKeyCell->NameSize * sizeof(WCHAR) + NameSize + SubKeyCell->ClassSize;
SubKeyCell->ClassSize;
if (Length < *ResultLength) if (Length < *ResultLength)
{ {
Status = STATUS_BUFFER_OVERFLOW; Status = STATUS_BUFFER_OVERFLOW;
@ -400,36 +422,47 @@ NtEnumerateKey(
NodeInformation->LastWriteTime.u.LowPart = SubKeyCell->LastWriteTime.dwLowDateTime; NodeInformation->LastWriteTime.u.LowPart = SubKeyCell->LastWriteTime.dwLowDateTime;
NodeInformation->LastWriteTime.u.HighPart = SubKeyCell->LastWriteTime.dwHighDateTime; NodeInformation->LastWriteTime.u.HighPart = SubKeyCell->LastWriteTime.dwHighDateTime;
NodeInformation->TitleIndex = Index; NodeInformation->TitleIndex = Index;
NodeInformation->ClassOffset = sizeof(KEY_NODE_INFORMATION) + NodeInformation->ClassOffset = sizeof(KEY_NODE_INFORMATION) + NameSize;
SubKeyCell->NameSize * sizeof(WCHAR);
NodeInformation->ClassLength = SubKeyCell->ClassSize; NodeInformation->ClassLength = SubKeyCell->ClassSize;
NodeInformation->NameLength = SubKeyCell->NameSize * sizeof(WCHAR); NodeInformation->NameLength = NameSize;
mbstowcs(NodeInformation->Name,
if (SubKeyCell->Flags & REG_KEY_NAME_PACKED)
{
CmiCopyPackedName(BasicInformation->Name,
SubKeyCell->Name, SubKeyCell->Name,
SubKeyCell->NameSize * 2); SubKeyCell->NameSize);
}
else
{
RtlCopyMemory(BasicInformation->Name,
SubKeyCell->Name,
SubKeyCell->NameSize);
}
if (SubKeyCell->ClassSize != 0) if (SubKeyCell->ClassSize != 0)
{ {
pClassData=CmiGetBlock(KeyObject->RegistryHive, ClassData=CmiGetBlock(KeyObject->RegistryHive,
SubKeyCell->ClassNameOffset, SubKeyCell->ClassNameOffset,
NULL); NULL);
wcsncpy(NodeInformation->Name + SubKeyCell->NameSize , wcsncpy(NodeInformation->Name + SubKeyCell->NameSize,
(PWCHAR) pClassData->Data, (PWCHAR)ClassData->Data,
SubKeyCell->ClassSize); SubKeyCell->ClassSize);
} }
} }
break; break;
case KeyFullInformation: case KeyFullInformation:
/* check size of buffer */ /* Check size of buffer */
*ResultLength = sizeof(KEY_FULL_INFORMATION) + *ResultLength = sizeof(KEY_FULL_INFORMATION) +
SubKeyCell->ClassSize; SubKeyCell->ClassSize;
if (Length < *ResultLength) if (Length < *ResultLength)
{ {
Status = STATUS_BUFFER_OVERFLOW; Status = STATUS_BUFFER_OVERFLOW;
} }
else else
{ {
/* fill buffer with requested info */ /* Fill buffer with requested info */
FullInformation = (PKEY_FULL_INFORMATION) KeyInformation; FullInformation = (PKEY_FULL_INFORMATION) KeyInformation;
FullInformation->LastWriteTime.u.LowPart = SubKeyCell->LastWriteTime.dwLowDateTime; FullInformation->LastWriteTime.u.LowPart = SubKeyCell->LastWriteTime.dwLowDateTime;
FullInformation->LastWriteTime.u.HighPart = SubKeyCell->LastWriteTime.dwHighDateTime; FullInformation->LastWriteTime.u.HighPart = SubKeyCell->LastWriteTime.dwHighDateTime;
@ -449,11 +482,11 @@ NtEnumerateKey(
CmiGetMaxValueDataLength(RegistryHive, SubKeyCell); CmiGetMaxValueDataLength(RegistryHive, SubKeyCell);
if (SubKeyCell->ClassSize != 0) if (SubKeyCell->ClassSize != 0)
{ {
pClassData = CmiGetBlock(KeyObject->RegistryHive, ClassData = CmiGetBlock(KeyObject->RegistryHive,
SubKeyCell->ClassNameOffset, SubKeyCell->ClassNameOffset,
NULL); NULL);
wcsncpy(FullInformation->Class, wcsncpy(FullInformation->Class,
(PWCHAR) pClassData->Data, (PWCHAR)ClassData->Data,
SubKeyCell->ClassSize); SubKeyCell->ClassSize);
} }
} }
@ -802,7 +835,7 @@ NtQueryKey(IN HANDLE KeyHandle,
PKEY_NODE_INFORMATION NodeInformation; PKEY_NODE_INFORMATION NodeInformation;
PKEY_FULL_INFORMATION FullInformation; PKEY_FULL_INFORMATION FullInformation;
PREGISTRY_HIVE RegistryHive; PREGISTRY_HIVE RegistryHive;
PDATA_CELL pClassData; PDATA_CELL ClassData;
PKEY_OBJECT KeyObject; PKEY_OBJECT KeyObject;
PKEY_CELL KeyCell; PKEY_CELL KeyCell;
NTSTATUS Status; NTSTATUS Status;
@ -840,8 +873,10 @@ NtQueryKey(IN HANDLE KeyHandle,
{ {
case KeyBasicInformation: case KeyBasicInformation:
/* Check size of buffer */ /* Check size of buffer */
if (Length < sizeof(KEY_BASIC_INFORMATION) + *ResultLength = sizeof(KEY_BASIC_INFORMATION) +
KeyObject->Name.Length) KeyObject->Name.Length;
if (Length < *ResultLength)
{ {
Status = STATUS_BUFFER_OVERFLOW; Status = STATUS_BUFFER_OVERFLOW;
} }
@ -856,16 +891,15 @@ NtQueryKey(IN HANDLE KeyHandle,
RtlCopyMemory(BasicInformation->Name, RtlCopyMemory(BasicInformation->Name,
KeyObject->Name.Buffer, KeyObject->Name.Buffer,
KeyObject->Name.Length); KeyObject->Name.Length);
*ResultLength = sizeof(KEY_BASIC_INFORMATION) +
KeyObject->Name.Length;
} }
break; break;
case KeyNodeInformation: case KeyNodeInformation:
/* Check size of buffer */ /* Check size of buffer */
if (Length < sizeof(KEY_NODE_INFORMATION) *ResultLength = sizeof(KEY_NODE_INFORMATION) +
+ KeyObject->Name.Length KeyObject->Name.Length + KeyCell->ClassSize;
+ KeyCell->ClassSize)
if (Length < *ResultLength)
{ {
Status = STATUS_BUFFER_OVERFLOW; Status = STATUS_BUFFER_OVERFLOW;
} }
@ -886,22 +920,22 @@ NtQueryKey(IN HANDLE KeyHandle,
if (KeyCell->ClassSize != 0) if (KeyCell->ClassSize != 0)
{ {
pClassData = CmiGetBlock(KeyObject->RegistryHive, ClassData = CmiGetBlock(KeyObject->RegistryHive,
KeyCell->ClassNameOffset, KeyCell->ClassNameOffset,
NULL); NULL);
wcsncpy(NodeInformation->Name + KeyObject->Name.Length, wcsncpy(NodeInformation->Name + KeyObject->Name.Length,
(PWCHAR)pClassData->Data, (PWCHAR)ClassData->Data,
KeyCell->ClassSize); KeyCell->ClassSize);
} }
*ResultLength = sizeof(KEY_NODE_INFORMATION)
+ KeyObject->Name.Length
+ KeyCell->ClassSize;
} }
break; break;
case KeyFullInformation: case KeyFullInformation:
/* Check size of buffer */ /* Check size of buffer */
if (Length < sizeof(KEY_FULL_INFORMATION) + KeyCell->ClassSize) *ResultLength = sizeof(KEY_FULL_INFORMATION) +
KeyCell->ClassSize;
if (Length < *ResultLength)
{ {
Status = STATUS_BUFFER_OVERFLOW; Status = STATUS_BUFFER_OVERFLOW;
} }
@ -926,14 +960,13 @@ NtQueryKey(IN HANDLE KeyHandle,
CmiGetMaxValueDataLength(RegistryHive, KeyCell); CmiGetMaxValueDataLength(RegistryHive, KeyCell);
if (KeyCell->ClassSize != 0) if (KeyCell->ClassSize != 0)
{ {
pClassData=CmiGetBlock(KeyObject->RegistryHive, ClassData=CmiGetBlock(KeyObject->RegistryHive,
KeyCell->ClassNameOffset, KeyCell->ClassNameOffset,
NULL); NULL);
wcsncpy(FullInformation->Class, wcsncpy(FullInformation->Class,
(PWCHAR)pClassData->Data, (PWCHAR)ClassData->Data,
KeyCell->ClassSize); KeyCell->ClassSize);
} }
*ResultLength = sizeof(KEY_FULL_INFORMATION) + KeyCell->ClassSize;
} }
break; break;
} }

View file

@ -2099,22 +2099,44 @@ CmiAddSubKey(PREGISTRY_HIVE RegistryHive,
NTSTATUS Status; NTSTATUS Status;
USHORT NameSize; USHORT NameSize;
PWSTR NamePtr; PWSTR NamePtr;
BOOLEAN Packable;
ULONG i;
KeyCell = Parent->KeyCell; KeyCell = Parent->KeyCell;
VERIFY_KEY_CELL(KeyCell); VERIFY_KEY_CELL(KeyCell);
/* Skip leading backslash */
if (SubKeyName->Buffer[0] == L'\\') if (SubKeyName->Buffer[0] == L'\\')
{ {
NamePtr = &SubKeyName->Buffer[1]; NamePtr = &SubKeyName->Buffer[1];
NameSize = SubKeyName->Length / 2 - 1; NameSize = SubKeyName->Length - sizeof(WCHAR);
} }
else else
{ {
NamePtr = SubKeyName->Buffer; NamePtr = SubKeyName->Buffer;
NameSize = SubKeyName->Length / 2; NameSize = SubKeyName->Length;
} }
/* Check whether key name can be packed */
Packable = TRUE;
for (i = 0; i < NameSize / sizeof(WCHAR); i++)
{
if (NamePtr[i] & 0xFF00)
{
Packable = FALSE;
break;
}
}
/* Adjust name size */
if (Packable)
{
NameSize = NameSize / sizeof(WCHAR);
}
DPRINT("Key %S Length %lu %s\n", NamePtr, NameSize, (Packable)?"True":"False");
Status = STATUS_SUCCESS; Status = STATUS_SUCCESS;
NewBlockSize = sizeof(KEY_CELL) + NameSize; NewBlockSize = sizeof(KEY_CELL) + NameSize;
@ -2130,7 +2152,7 @@ CmiAddSubKey(PREGISTRY_HIVE RegistryHive,
{ {
NewKeyCell->Id = REG_KEY_CELL_ID; NewKeyCell->Id = REG_KEY_CELL_ID;
NewKeyCell->Flags = 0; NewKeyCell->Flags = 0;
ZwQuerySystemTime((PTIME) &NewKeyCell->LastWriteTime); NtQuerySystemTime((PTIME) &NewKeyCell->LastWriteTime);
NewKeyCell->ParentKeyOffset = -1; NewKeyCell->ParentKeyOffset = -1;
NewKeyCell->NumberOfSubKeys = 0; NewKeyCell->NumberOfSubKeys = 0;
NewKeyCell->HashTableOffset = -1; NewKeyCell->HashTableOffset = -1;
@ -2139,9 +2161,22 @@ CmiAddSubKey(PREGISTRY_HIVE RegistryHive,
NewKeyCell->SecurityKeyOffset = -1; NewKeyCell->SecurityKeyOffset = -1;
NewKeyCell->ClassNameOffset = -1; NewKeyCell->ClassNameOffset = -1;
NewKeyCell->Flags |= REG_KEY_NAME_PACKED; /* Pack the key name */
NewKeyCell->NameSize = NameSize; NewKeyCell->NameSize = NameSize;
wcstombs(NewKeyCell->Name, NamePtr, NameSize); if (Packable)
{
NewKeyCell->Flags |= REG_KEY_NAME_PACKED;
for (i = 0; i < NameSize; i++)
{
NewKeyCell->Name[i] = (CHAR)(NamePtr[i] & 0x00FF);
}
}
else
{
RtlCopyMemory(NewKeyCell->Name,
NamePtr,
NameSize);
}
VERIFY_KEY_CELL(NewKeyCell); VERIFY_KEY_CELL(NewKeyCell);
@ -2151,10 +2186,12 @@ CmiAddSubKey(PREGISTRY_HIVE RegistryHive,
NewKeyCell->ClassSize = Class->Length + sizeof(WCHAR); NewKeyCell->ClassSize = Class->Length + sizeof(WCHAR);
Status = CmiAllocateBlock(RegistryHive, Status = CmiAllocateBlock(RegistryHive,
(PVOID) &pClass, (PVOID)&pClass,
NewKeyCell->ClassSize, NewKeyCell->ClassSize,
&NewKeyCell->ClassNameOffset); &NewKeyCell->ClassNameOffset);
wcsncpy((PWSTR) pClass->Data, Class->Buffer, Class->Length); wcsncpy((PWSTR)pClass->Data,
Class->Buffer,
Class->Length);
((PWSTR) (pClass->Data))[Class->Length] = 0; ((PWSTR) (pClass->Data))[Class->Length] = 0;
} }
} }
@ -3424,17 +3461,17 @@ CmiGetPackedNameLength(IN PUNICODE_STRING Name,
if (Packable != NULL) if (Packable != NULL)
*Packable = TRUE; *Packable = TRUE;
for (i = 0; i < Name->Length; i++) for (i = 0; i < Name->Length / sizeof(WCHAR); i++)
{ {
if (Name->Buffer[i] > 0xFF) if (Name->Buffer[i] & 0xFF00)
{ {
if (Packable != NULL) if (Packable != NULL)
*Packable = FALSE; *Packable = FALSE;
return(Name->Length); return Name->Length;
} }
} }
return(Name->Length / sizeof(WCHAR)); return (Name->Length / sizeof(WCHAR));
} }
@ -3525,7 +3562,7 @@ CmiCompareKeyNames(PUNICODE_STRING KeyName,
PWCHAR UnicodeName; PWCHAR UnicodeName;
USHORT i; USHORT i;
DPRINT1("Flags: %hx\n", KeyCell->Flags); DPRINT("Flags: %hx\n", KeyCell->Flags);
if (KeyCell->Flags & REG_KEY_NAME_PACKED) if (KeyCell->Flags & REG_KEY_NAME_PACKED)
{ {
@ -3562,7 +3599,7 @@ CmiCompareKeyNamesI(PUNICODE_STRING KeyName,
PWCHAR UnicodeName; PWCHAR UnicodeName;
USHORT i; USHORT i;
DPRINT1("Flags: %hx\n", KeyCell->Flags); DPRINT("Flags: %hx\n", KeyCell->Flags);
if (KeyCell->Flags & REG_KEY_NAME_PACKED) if (KeyCell->Flags & REG_KEY_NAME_PACKED)
{ {

View file

@ -1,4 +1,4 @@
/* $Id: registry.c,v 1.97 2003/05/28 16:09:51 ekohl Exp $ /* $Id: registry.c,v 1.98 2003/05/29 14:09:41 ekohl Exp $
* *
* COPYRIGHT: See COPYING in the top level directory * COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS kernel * PROJECT: ReactOS kernel
@ -874,11 +874,11 @@ CmiInitHives(BOOLEAN SetupBoot)
} }
/* Connect the DEFAULT hive */ /* Connect the DEFAULT hive */
wcscpy(EndPtr, REG_USER_FILE_NAME); wcscpy(EndPtr, REG_DEFAULT_USER_FILE_NAME);
DPRINT ("ConfigPath: %S\n", ConfigPath); DPRINT ("ConfigPath: %S\n", ConfigPath);
RtlInitUnicodeString (&KeyName, RtlInitUnicodeString (&KeyName,
REG_USER_KEY_NAME); REG_DEFAULT_USER_KEY_NAME);
Status = CmiInitializeHive(ConfigPath, Status = CmiInitializeHive(ConfigPath,
&KeyName, &KeyName,
SetupBoot); SetupBoot);