mirror of
https://github.com/reactos/reactos.git
synced 2025-08-05 16:23:01 +00:00
[RTL]
- Rewrite RtlFindCharInUnicodeString. Fixes timeout in ntdll:rtlstr test. svn path=/trunk/; revision=54091
This commit is contained in:
parent
b2d43ccd3c
commit
bdd81004f4
3 changed files with 64 additions and 77 deletions
|
@ -2026,7 +2026,7 @@ NTSTATUS
|
||||||
NTAPI
|
NTAPI
|
||||||
RtlFindCharInUnicodeString(
|
RtlFindCharInUnicodeString(
|
||||||
IN ULONG Flags,
|
IN ULONG Flags,
|
||||||
IN PUNICODE_STRING SearchString,
|
IN PCUNICODE_STRING SearchString,
|
||||||
IN PCUNICODE_STRING MatchString,
|
IN PCUNICODE_STRING MatchString,
|
||||||
OUT PUSHORT Position
|
OUT PUSHORT Position
|
||||||
);
|
);
|
||||||
|
|
|
@ -242,6 +242,8 @@ C_ASSERT(HEAP_CREATE_VALID_MASK == 0x0007F0FF);
|
||||||
//
|
//
|
||||||
// RtlFindCharInUnicodeString Flags
|
// RtlFindCharInUnicodeString Flags
|
||||||
//
|
//
|
||||||
|
#define RTL_FIND_CHAR_IN_UNICODE_STRING_START_AT_END 1
|
||||||
|
#define RTL_FIND_CHAR_IN_UNICODE_STRING_COMPLEMENT_CHAR_SET 2
|
||||||
#define RTL_FIND_CHAR_IN_UNICODE_STRING_CASE_INSENSITIVE 4
|
#define RTL_FIND_CHAR_IN_UNICODE_STRING_CASE_INSENSITIVE 4
|
||||||
|
|
||||||
//
|
//
|
||||||
|
|
|
@ -2486,6 +2486,31 @@ RtlpEnsureBufferSize(ULONG Unknown1, ULONG Unknown2, ULONG Unknown3)
|
||||||
return STATUS_NOT_IMPLEMENTED;
|
return STATUS_NOT_IMPLEMENTED;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static
|
||||||
|
BOOLEAN
|
||||||
|
RtlpIsCharInUnicodeString(
|
||||||
|
IN WCHAR Char,
|
||||||
|
IN PCUNICODE_STRING MatchString,
|
||||||
|
IN BOOLEAN CaseInSensitive)
|
||||||
|
{
|
||||||
|
USHORT i;
|
||||||
|
|
||||||
|
if (CaseInSensitive)
|
||||||
|
Char = RtlUpcaseUnicodeChar(Char);
|
||||||
|
|
||||||
|
for (i = 0; i < MatchString->Length / sizeof(WCHAR); i++)
|
||||||
|
{
|
||||||
|
WCHAR OtherChar = MatchString->Buffer[i];
|
||||||
|
if (CaseInSensitive)
|
||||||
|
OtherChar = RtlUpcaseUnicodeChar(OtherChar);
|
||||||
|
|
||||||
|
if (Char == OtherChar)
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* @implemented
|
* @implemented
|
||||||
*/
|
*/
|
||||||
|
@ -2493,94 +2518,54 @@ NTSTATUS
|
||||||
NTAPI
|
NTAPI
|
||||||
RtlFindCharInUnicodeString(
|
RtlFindCharInUnicodeString(
|
||||||
IN ULONG Flags,
|
IN ULONG Flags,
|
||||||
IN PUNICODE_STRING SearchString,
|
IN PCUNICODE_STRING SearchString,
|
||||||
IN PCUNICODE_STRING MatchString,
|
IN PCUNICODE_STRING MatchString,
|
||||||
OUT PUSHORT Position)
|
OUT PUSHORT Position)
|
||||||
{
|
{
|
||||||
USHORT i, j;
|
BOOLEAN Found;
|
||||||
|
const BOOLEAN WantToFind = (Flags & RTL_FIND_CHAR_IN_UNICODE_STRING_COMPLEMENT_CHAR_SET) == 0;
|
||||||
|
const BOOLEAN CaseInSensitive = (Flags & RTL_FIND_CHAR_IN_UNICODE_STRING_CASE_INSENSITIVE) != 0;
|
||||||
|
INT Length;
|
||||||
|
INT i;
|
||||||
|
|
||||||
switch (Flags)
|
DPRINT("RtlFindCharInUnicodeString(%u, '%wZ', '%wZ', %p)\n",
|
||||||
|
Flags, SearchString, MatchString, Position);
|
||||||
|
|
||||||
|
/* Parameter checks */
|
||||||
|
if (Position == NULL)
|
||||||
|
return STATUS_INVALID_PARAMETER;
|
||||||
|
|
||||||
|
*Position = 0;
|
||||||
|
|
||||||
|
if (Flags & ~(RTL_FIND_CHAR_IN_UNICODE_STRING_START_AT_END |
|
||||||
|
RTL_FIND_CHAR_IN_UNICODE_STRING_COMPLEMENT_CHAR_SET |
|
||||||
|
RTL_FIND_CHAR_IN_UNICODE_STRING_CASE_INSENSITIVE))
|
||||||
|
return STATUS_INVALID_PARAMETER;
|
||||||
|
|
||||||
|
/* Search */
|
||||||
|
Length = SearchString->Length / sizeof(WCHAR);
|
||||||
|
if (Flags & RTL_FIND_CHAR_IN_UNICODE_STRING_START_AT_END)
|
||||||
{
|
{
|
||||||
case 0:
|
for (i = Length - 1; i >= 0; i--)
|
||||||
{
|
{
|
||||||
for (i = 0; i < SearchString->Length / sizeof(WCHAR); i++)
|
Found = RtlpIsCharInUnicodeString(SearchString->Buffer[i], MatchString, CaseInSensitive);
|
||||||
|
if (Found == WantToFind)
|
||||||
{
|
{
|
||||||
for (j = 0; j < MatchString->Length / sizeof(WCHAR); j++)
|
*Position = i * sizeof(WCHAR);
|
||||||
{
|
return STATUS_SUCCESS;
|
||||||
if (SearchString->Buffer[i] == MatchString->Buffer[j])
|
|
||||||
{
|
|
||||||
*Position = (i + 1) * sizeof(WCHAR);
|
|
||||||
return STATUS_SUCCESS;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
*Position = 0;
|
|
||||||
return STATUS_NOT_FOUND;
|
|
||||||
}
|
}
|
||||||
|
}
|
||||||
case 1:
|
else
|
||||||
|
{
|
||||||
|
for (i = 0; i < Length; i++)
|
||||||
{
|
{
|
||||||
for (i = SearchString->Length / sizeof(WCHAR) - 1; (i + 1) > 0; i--)
|
Found = RtlpIsCharInUnicodeString(SearchString->Buffer[i], MatchString, CaseInSensitive);
|
||||||
|
if (Found == WantToFind)
|
||||||
{
|
{
|
||||||
for (j = 0; j < MatchString->Length / sizeof(WCHAR); j++)
|
*Position = (i + 1) * sizeof(WCHAR);
|
||||||
{
|
return STATUS_SUCCESS;
|
||||||
if (SearchString->Buffer[i] == MatchString->Buffer[j])
|
|
||||||
{
|
|
||||||
*Position = i * sizeof(WCHAR);
|
|
||||||
return STATUS_SUCCESS;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
*Position = 0;
|
|
||||||
return STATUS_NOT_FOUND;
|
|
||||||
}
|
|
||||||
|
|
||||||
case 2:
|
|
||||||
{
|
|
||||||
for (i = 0; i < SearchString->Length / sizeof(WCHAR); i++)
|
|
||||||
{
|
|
||||||
j = 0;
|
|
||||||
|
|
||||||
while (j < MatchString->Length / sizeof(WCHAR) &&
|
|
||||||
SearchString->Buffer[i] != MatchString->Buffer[j])
|
|
||||||
{
|
|
||||||
j++;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (j >= MatchString->Length / sizeof(WCHAR))
|
|
||||||
{
|
|
||||||
*Position = (i + 1) * sizeof(WCHAR);
|
|
||||||
return STATUS_SUCCESS;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
*Position = 0;
|
|
||||||
return STATUS_NOT_FOUND;
|
|
||||||
}
|
|
||||||
|
|
||||||
case 3:
|
|
||||||
{
|
|
||||||
for (i = SearchString->Length / sizeof(WCHAR) - 1; (i + 1) > 0; i--)
|
|
||||||
{
|
|
||||||
j = 0;
|
|
||||||
|
|
||||||
while (j < MatchString->Length / sizeof(WCHAR) &&
|
|
||||||
SearchString->Buffer[i] != MatchString->Buffer[j])
|
|
||||||
{
|
|
||||||
j++;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (j >= MatchString->Length / sizeof(WCHAR))
|
|
||||||
{
|
|
||||||
*Position = i * sizeof(WCHAR);
|
|
||||||
return STATUS_SUCCESS;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
*Position = 0;
|
|
||||||
return STATUS_NOT_FOUND;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue