Index: drivers/video/videoprt/videoprt.c =================================================================== --- drivers/video/videoprt/videoprt.c (revision 51594) +++ drivers/video/videoprt/videoprt.c (working copy) @@ -21,6 +21,7 @@ #include "videoprt.h" +#include #include /* GLOBAL VARIABLES ***********************************************************/ @@ -78,48 +79,36 @@ IN PCUNICODE_STRING DriverRegistryPath, OUT PUNICODE_STRING DeviceRegistryPath) { - static WCHAR RegistryMachineSystem[] = L"\\REGISTRY\\MACHINE\\SYSTEM\\"; - static WCHAR CurrentControlSet[] = L"CURRENTCONTROLSET\\"; - static WCHAR ControlSet[] = L"CONTROLSET"; - static WCHAR Insert1[] = L"Hardware Profiles\\Current\\System\\CurrentControlSet\\"; - static WCHAR Insert2[] = L"\\Device0"; + static const WCHAR RegistryMachineSystem[] = L"\\REGISTRY\\MACHINE\\SYSTEM\\"; + static const WCHAR CurrentControlSet[] = L"CURRENTCONTROLSET\\"; + static const WCHAR ControlSet[] = L"CONTROLSET"; + static const WCHAR Insert1[] = L"Hardware Profiles\\Current\\System\\CurrentControlSet\\"; + static const WCHAR Insert2[] = L"\\Device0"; BOOLEAN Valid; UNICODE_STRING AfterControlSet; + NTSTATUS Status; AfterControlSet = *DriverRegistryPath; /* Check if path begins with \\REGISTRY\\MACHINE\\SYSTEM\\ */ - Valid = (DriverRegistryPath->Length > sizeof(RegistryMachineSystem) && - 0 == _wcsnicmp(DriverRegistryPath->Buffer, RegistryMachineSystem, - wcslen(RegistryMachineSystem))); + Valid = RosUnicodeStringStartsWithStringSkip(&AfterControlSet, RegistryMachineSystem, TRUE); if (Valid) { - AfterControlSet.Buffer += wcslen(RegistryMachineSystem); - AfterControlSet.Length -= sizeof(RegistryMachineSystem) - sizeof(UNICODE_NULL); - /* Check if path contains CURRENTCONTROLSET */ - if (AfterControlSet.Length > sizeof(CurrentControlSet) && - 0 == _wcsnicmp(AfterControlSet.Buffer, CurrentControlSet, wcslen(CurrentControlSet))) + if (RosUnicodeStringStartsWithStringSkip(&AfterControlSet, CurrentControlSet, TRUE)) { - AfterControlSet.Buffer += wcslen(CurrentControlSet); - AfterControlSet.Length -= sizeof(CurrentControlSet) - sizeof(UNICODE_NULL); + Valid = TRUE; } /* Check if path contains CONTROLSETnum */ - else if (AfterControlSet.Length > sizeof(ControlSet) && - 0 == _wcsnicmp(AfterControlSet.Buffer, ControlSet, wcslen(ControlSet))) + else if (RosUnicodeStringStartsWithStringSkip(&AfterControlSet, ControlSet, TRUE)) { - AfterControlSet.Buffer += wcslen(ControlSet); - AfterControlSet.Length -= sizeof(ControlSet) - sizeof(UNICODE_NULL); while (AfterControlSet.Length > 0 && *AfterControlSet.Buffer >= L'0' && *AfterControlSet.Buffer <= L'9') { - AfterControlSet.Buffer++; - AfterControlSet.Length -= sizeof(WCHAR); + RosUnicodeStringSkipChar(&AfterControlSet); } Valid = (AfterControlSet.Length > 0 && L'\\' == *AfterControlSet.Buffer); - AfterControlSet.Buffer++; - AfterControlSet.Length -= sizeof(WCHAR); - AfterControlSet.MaximumLength = AfterControlSet.Length; + RosUnicodeStringSkipChar(&AfterControlSet); } else { @@ -129,17 +118,15 @@ if (Valid) { - DeviceRegistryPath->MaximumLength = DriverRegistryPath->Length + sizeof(Insert1) + sizeof(Insert2); - DeviceRegistryPath->Buffer = ExAllocatePoolWithTag(PagedPool, - DeviceRegistryPath->MaximumLength, - TAG_VIDEO_PORT); - if (DeviceRegistryPath->Buffer != NULL) + Status = RosUnicodeStringAllocateWithTag( + PagedPool, + DeviceRegistryPath, + DriverRegistryPath->Length + sizeof(Insert1) + sizeof(Insert2), + TAG_VIDEO_PORT); + if (NT_SUCCESS(Status)) { /* Build device path */ - wcsncpy(DeviceRegistryPath->Buffer, - DriverRegistryPath->Buffer, - AfterControlSet.Buffer - DriverRegistryPath->Buffer); - DeviceRegistryPath->Length = (AfterControlSet.Buffer - DriverRegistryPath->Buffer) * sizeof(WCHAR); + RosUnicodeStringCchCopyN(DeviceRegistryPath, DriverRegistryPath, AfterControlSet.Buffer - DriverRegistryPath->Buffer); RtlAppendUnicodeToString(DeviceRegistryPath, Insert1); RtlAppendUnicodeStringToString(DeviceRegistryPath, &AfterControlSet); RtlAppendUnicodeToString(DeviceRegistryPath, Insert2); @@ -163,14 +150,14 @@ /* If path doesn't point to *ControlSet*, use DriverRegistryPath directly */ if (!Valid) { - DeviceRegistryPath->MaximumLength = DriverRegistryPath->Length + sizeof(Insert2); - DeviceRegistryPath->Buffer = ExAllocatePoolWithTag( - NonPagedPool, - DeviceRegistryPath->MaximumLength, - TAG_VIDEO_PORT); + Status = RosUnicodeStringAllocateWithTag( + NonPagedPool, + DeviceRegistryPath, + DriverRegistryPath->Length + sizeof(Insert2), + TAG_VIDEO_PORT); - if (!DeviceRegistryPath->Buffer) - return STATUS_NO_MEMORY; + if (!NT_SUCCESS(Status)) + return Status; RtlCopyUnicodeString(DeviceRegistryPath, DriverRegistryPath); RtlAppendUnicodeToString(DeviceRegistryPath, Insert2); Index: include/ddk/rosstrsafe.h =================================================================== --- include/ddk/rosstrsafe.h (revision 0) +++ include/ddk/rosstrsafe.h (revision 0) @@ -0,0 +1,209 @@ +/* + * PROJECT: ReactOS + * LICENSE: GPLv2+ - See COPYING in the top level directory + * PURPOSE: ReactOS common string functions library + * PROGRAMMER: Thomas Faber + */ + +#ifndef _ROSSTRSAFE_H_INCLUDED_ +#define _ROSSTRSAFE_H_INCLUDED_ + +/* FIXME: add RosAnsiString* (possibly by recursive include) */ +/* FIXME: make this stuff work in usermode? */ + +#include + +#define ROSSTRSAFEAPI_BOOLEAN static __inline BOOLEAN NTAPI +#define ROSSTRSAFEAPI_NTSTATUS static __inline NTSTATUS NTAPI +#define ROSSTRSAFEAPI_VOID static __inline VOID NTAPI + +/* work around incomplete ntstrsafe.h -- part of "Safe String Functions for UNICODE_STRING Structures", + see http://msdn.microsoft.com/en-us/library/ff563644(v=VS.85).aspx */ +#ifndef NTSTRSAFE_UNICODE_STRING_MAX_CCH +#define NTSTRSAFE_UNICODE_STRING_MAX_CCH 32767 +#endif /* !defined NTSTRSAFE_UNICODE_STRING_MAX_CCH */ + +ROSSTRSAFEAPI_NTSTATUS +RosUnicodeStringValidate( + IN PCUNICODE_STRING String, + IN ULONG Flags) +{ + NTSTATUS Status = STATUS_SUCCESS; + +#ifdef DBG + if (Flags & ~STRSAFE_IGNORE_NULLS) + Status = STATUS_INVALID_PARAMETER; + + else if (String == NULL && (Flags & STRSAFE_IGNORE_NULLS) == 0) + Status = STATUS_INVALID_PARAMETER; + + else if (String->Buffer == NULL && + (String->MaximumLength != 0 || String->Length != 0)) + Status = STATUS_INVALID_PARAMETER; + + else if (String->Length > String->MaximumLength) + Status = STATUS_INVALID_PARAMETER; + + else if (String->Length % sizeof String->Buffer[0] || + String->MaximumLength % sizeof String->Buffer[0]) + Status = STATUS_INVALID_PARAMETER; + + else if (String->MaximumLength > NTSTRSAFE_UNICODE_STRING_MAX_CCH * sizeof String->Buffer[0]) + Status = STATUS_INVALID_PARAMETER; +#else /* if !defined DBG */ + UNREFERENCED_PARAMETER(String); + UNREFERENCED_PARAMETER(Flags); +#endif /* !defined DBG */ + + return Status; +} + +ROSSTRSAFEAPI_VOID +RosUnicodeStringInitEmptyFromBuffer( + OUT PUNICODE_STRING String, + IN PWSTR Buffer, + IN USHORT MaximumLength) +{ + String->Buffer = Buffer; + String->MaximumLength = MaximumLength; + String->Length = 0; +} + +ROSSTRSAFEAPI_NTSTATUS +RosUnicodeStringAllocateWithTag( + IN POOL_TYPE PoolType, + OUT PUNICODE_STRING String, + IN USHORT MaximumLength, + IN ULONG Tag) +{ + PVOID Buffer = ExAllocatePoolWithTag(PoolType, MaximumLength, Tag); + if (!Buffer) + return STATUS_NO_MEMORY; + + RosUnicodeStringInitEmptyFromBuffer(String, Buffer, MaximumLength); + return STATUS_SUCCESS; +} + +ROSSTRSAFEAPI_NTSTATUS +RosUnicodeStringAllocate( + IN POOL_TYPE PoolType, + OUT PUNICODE_STRING String, + IN USHORT MaximumLength) +{ + return RosUnicodeStringAllocateWithTag(PoolType, String, MaximumLength, 'ASUR'); +} + +ROSSTRSAFEAPI_NTSTATUS +RosUnicodeStringCbCopyN( + OUT PUNICODE_STRING DestinationString, + IN PCUNICODE_STRING SourceString, + IN USHORT Length) +{ + ASSERT(NT_SUCCESS(RosUnicodeStringValidate(SourceString, 0))); + + if (DestinationString->MaximumLength < Length) + return STATUS_BUFFER_TOO_SMALL; + + if (SourceString->Length < Length) + Length = SourceString->Length; + + DestinationString->Length = Length; + RtlCopyMemory(DestinationString->Buffer, + SourceString->Buffer, + Length); + + return STATUS_SUCCESS; +} + +ROSSTRSAFEAPI_NTSTATUS +RosUnicodeStringCchCopyN( + OUT PUNICODE_STRING DestinationString, + IN PCUNICODE_STRING SourceString, + IN USHORT Length) +{ + return RosUnicodeStringCbCopyN(DestinationString, SourceString, Length * sizeof DestinationString->Buffer[0]); +} + +ROSSTRSAFEAPI_BOOLEAN +RosUnicodeStringStartsWith( + IN PCUNICODE_STRING Haystack, + IN PCUNICODE_STRING Needle, + IN BOOLEAN CaseInSensitive) +{ + UNICODE_STRING HaystackStart; + + PAGED_CODE(); + + ASSERT(NT_SUCCESS(RosUnicodeStringValidate(Haystack, 0))); + ASSERT(NT_SUCCESS(RosUnicodeStringValidate(Needle, 0))); + + if (Haystack->Length < Needle->Length) + return FALSE; + + HaystackStart = *Haystack; + HaystackStart.Length = Needle->Length; + + return RtlCompareUnicodeString(&HaystackStart, Needle, CaseInSensitive) == 0; +} + +ROSSTRSAFEAPI_BOOLEAN +RosUnicodeStringStartsWithString( + IN PCUNICODE_STRING Haystack, + IN PCWSTR NeedleString, + IN BOOLEAN CaseInSensitive) +{ + UNICODE_STRING Needle; + + PAGED_CODE(); + + ASSERT(NT_SUCCESS(RosUnicodeStringValidate(Haystack, 0))); + + RtlInitUnicodeString(&Needle, NeedleString); + + return RosUnicodeStringStartsWith(Haystack, &Needle, CaseInSensitive); +} + +ROSSTRSAFEAPI_BOOLEAN +RosUnicodeStringStartsWithStringSkip( + IN OUT PUNICODE_STRING Haystack, + IN PCWSTR NeedleString, + IN BOOLEAN CaseInSensitive) +{ + UNICODE_STRING Needle; + + PAGED_CODE(); + + ASSERT(NT_SUCCESS(RosUnicodeStringValidate(Haystack, 0))); + + RtlInitUnicodeString(&Needle, NeedleString); + + if (!RosUnicodeStringStartsWith(Haystack, &Needle, CaseInSensitive)) + return FALSE; + + Haystack->Buffer += Needle.Length / sizeof Needle.Buffer[0]; + Haystack->Length -= Needle.Length; + Haystack->MaximumLength -= Needle.Length; + + return TRUE; +} + +ROSSTRSAFEAPI_VOID +RosUnicodeStringSkipChars( + IN OUT PUNICODE_STRING String, + IN USHORT NumberOfCharsToSkip) +{ + ASSERT(NT_SUCCESS(RosUnicodeStringValidate(String, 0))); + ASSERT(String->Length >= NumberOfCharsToSkip); + String->Buffer += NumberOfCharsToSkip; + String->Length -= NumberOfCharsToSkip * sizeof String->Buffer[0]; + String->MaximumLength -= NumberOfCharsToSkip * sizeof String->Buffer[0]; +} + +ROSSTRSAFEAPI_VOID +RosUnicodeStringSkipChar( + IN OUT PUNICODE_STRING String) +{ + RosUnicodeStringSkipChars(String, 1); +} + +#endif /* !defined _ROSSTRSAFE_H_INCLUDED_ */ Property changes on: include\ddk\rosstrsafe.h ___________________________________________________________________ Added: svn:eol-style + native