Implemented RtlGenerate8dot3Name() and RtlIsNameLegalDOS8Dot3().

svn path=/trunk/; revision=3001
This commit is contained in:
Eric Kohl 2002-06-05 16:53:36 +00:00
parent 3d3be3df27
commit 9078342c24
11 changed files with 534 additions and 96 deletions

View file

@ -1,4 +1,4 @@
/* $Id: rtl.h,v 1.60 2002/02/20 20:09:52 ekohl Exp $
/* $Id: rtl.h,v 1.61 2002/06/05 16:49:56 ekohl Exp $
*
*/
@ -646,6 +646,10 @@ RtlCopyMemory (
#define RtlCopyBytes RtlCopyMemory
VOID STDCALL
RtlCopyLuid(IN PLUID LuidDest,
IN PLUID LuidSrc);
VOID
STDCALL
RtlCopyString (
@ -781,6 +785,10 @@ RtlEnlargedUnsignedMultiply (
ULONG Multiplier
);
BOOLEAN STDCALL
RtlEqualLuid(IN PLUID Luid1,
IN PLUID Luid2);
BOOLEAN
STDCALL
RtlEqualString (
@ -938,6 +946,12 @@ RtlFreeUnicodeString (
PUNICODE_STRING UnicodeString
);
VOID STDCALL
RtlGenerate8dot3Name(IN PUNICODE_STRING Name,
IN BOOLEAN AllowExtendedCharacters,
IN OUT PGENERATE_NAME_CONTEXT Context,
OUT PUNICODE_STRING Name8dot3);
VOID
RtlGetCallersAddress (
PVOID * CallersAddress
@ -1069,13 +1083,10 @@ RtlIsGenericTableEmpty (
IN PRTL_GENERIC_TABLE Table
);
BOOLEAN
STDCALL
RtlIsNameLegalDOS8Dot3 (
IN PUNICODE_STRING UnicodeName,
IN OUT PANSI_STRING AnsiName,
IN OUT PBOOLEAN SpacesFound
);
BOOLEAN STDCALL
RtlIsNameLegalDOS8Dot3(IN PUNICODE_STRING UnicodeName,
IN PANSI_STRING AnsiName,
OUT PBOOLEAN SpacesFound);
LARGE_INTEGER
STDCALL

View file

@ -1,4 +1,4 @@
/* $Id: rtltypes.h,v 1.1 2002/01/14 01:41:08 ekohl Exp $
/* $Id: rtltypes.h,v 1.2 2002/06/05 16:49:57 ekohl Exp $
*
*/
@ -170,4 +170,15 @@ typedef struct _RTL_QUERY_REGISTRY_TABLE
} RTL_QUERY_REGISTRY_TABLE, *PRTL_QUERY_REGISTRY_TABLE;
typedef struct _GENERATE_NAME_CONTEXT
{
USHORT Checksum;
BOOLEAN CheckSumInserted;
UCHAR NameLength;
WCHAR NameBuffer[8];
ULONG ExtensionLength;
WCHAR ExtensionBuffer[4];
ULONG LastIndexValue;
} GENERATE_NAME_CONTEXT, *PGENERATE_NAME_CONTEXT;
#endif /* __DDK_RTLTYPES_H */

View file

@ -1,4 +1,4 @@
; $Id: ntdll.def,v 1.82 2001/12/02 23:34:41 dwelch Exp $
; $Id: ntdll.def,v 1.83 2002/06/05 16:51:20 ekohl Exp $
;
; ReactOS Operating System
;
@ -412,7 +412,7 @@ RtlFreeOemString@4
RtlFreeSid@4
RtlFreeUnicodeString@4
RtlFreeUserThreadStack@8
;RtlGenerate8dot3Name
RtlGenerate8dot3Name@16
RtlGetAce@12
;RtlGetCallersAddress
;RtlGetCompressionWorkSpaceSize

View file

@ -1,4 +1,4 @@
; $Id: ntdll.edf,v 1.71 2001/12/02 23:34:41 dwelch Exp $
; $Id: ntdll.edf,v 1.72 2002/06/05 16:51:20 ekohl Exp $
;
; ReactOS Operating System
;
@ -411,7 +411,7 @@ RtlFreeHeap=RtlFreeHeap@12
RtlFreeSid=RtlFreeSid@4
RtlFreeUnicodeString=RtlFreeUnicodeString@4
RtlFreeUserThreadStack=RtlFreeUserThreadStack@8
;RtlGenerate8dot3Name
RtlGenerate8dot3Name=RtlGenerate8dot3Name@16
RtlGetAce=RtlGetAce@12
;RtlGetCallersAddress
;RtlGetCompressionWorkSpaceSize

View file

@ -1,4 +1,4 @@
# $Id: makefile,v 1.70 2002/02/25 21:51:43 phreak Exp $
# $Id: makefile,v 1.71 2002/06/05 16:51:41 ekohl Exp $
PATH_TO_TOP = ../..
@ -31,7 +31,7 @@ RTL_OBJECTS = rtl/critical.o rtl/error.o rtl/heap.o rtl/largeint.o \
rtl/access.o rtl/apc.o rtl/callback.o rtl/luid.o rtl/misc.o \
rtl/registry.o rtl/exception.o rtl/intrlck.o rtl/resource.o \
rtl/handle.o rtl/atom.o rtl/message.o rtl/timezone.o \
rtl/propvar.o rtl/security.o
rtl/propvar.o rtl/security.o rtl/dos8dot3.o
STDIO_OBJECTS = stdio/sprintf.o stdio/swprintf.o

View file

@ -0,0 +1,245 @@
/*
* ReactOS kernel
* Copyright (C) 2002 ReactOS Team
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* $Id: dos8dot3.c,v 1.1 2002/06/05 16:50:43 ekohl Exp $
*
* COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS system libraries
* FILE: lib/ntdll/rtl/dos8dot3.c
* PURPOSE: Short name (8.3 name) functions
* PROGRAMMER: Eric Kohl
*/
/* INCLUDES ******************************************************************/
#include <ddk/ntddk.h>
#include <ntos/minmax.h>
//#define NDEBUG
#include <ntdll/ntdll.h>
/* CONSTANTS *****************************************************************/
const PWCHAR RtlpShortIllegals = L" ;+=[]',\"*\\<>/?:|";
/* FUNCTIONS *****************************************************************/
static BOOLEAN
RtlpIsShortIllegal(WCHAR Char)
{
int i;
for (i = 0; RtlpShortIllegals[i]; i++)
{
if (Char == RtlpShortIllegals[i])
return(TRUE);
}
return(FALSE);
}
VOID STDCALL
RtlGenerate8dot3Name(IN PUNICODE_STRING Name,
IN BOOLEAN AllowExtendedCharacters,
IN OUT PGENERATE_NAME_CONTEXT Context,
OUT PUNICODE_STRING Name8dot3)
{
WCHAR NameBuffer[8];
WCHAR ExtBuffer[4];
USHORT StrLength;
USHORT NameLength;
USHORT ExtLength;
USHORT CopyLength;
USHORT DotPos;
USHORT i, j;
USHORT CurrentIndex;
memset(NameBuffer, 0, sizeof(NameBuffer));
memset(ExtBuffer, 0, sizeof(ExtBuffer));
StrLength = Name->Length / sizeof(WCHAR);
DPRINT("StrLength: %hu\n", StrLength);
/* Find last dot in Name */
DotPos = 0;
for (i = 0; i < StrLength; i++)
{
if (Name->Buffer[i] == L'.')
{
DotPos = i;
}
}
if (DotPos == 0)
{
DotPos = i;
}
DPRINT("DotPos: %hu\n", DotPos);
/* Copy name (6 valid characters max) */
for (i = 0, NameLength = 0; NameLength < 6 && i < DotPos; i++)
{
if ((!RtlpIsShortIllegal(Name->Buffer[i])) &&
(Name->Buffer[i] != L'.'))
{
NameBuffer[NameLength++] = RtlUpcaseUnicodeChar(Name->Buffer[i]);
}
}
DPRINT("NameBuffer: '%.08S'\n", NameBuffer);
DPRINT("NameLength: %hu\n", NameLength);
/* Copy extension (4 valid characters max) */
if (DotPos < StrLength)
{
for (i = DotPos, ExtLength = 0; ExtLength < 4 && i < StrLength; i++)
{
if (!RtlpIsShortIllegal(Name->Buffer[i]))
{
ExtBuffer[ExtLength++] = RtlUpcaseUnicodeChar(Name->Buffer[i]);
}
}
}
DPRINT("ExtBuffer: '%.04S'\n", ExtBuffer);
DPRINT("ExtLength: %hu\n", ExtLength);
CopyLength = min(NameLength, (CurrentIndex < 10) ? 6 : 5);
if ((Context->NameLength == CopyLength) &&
(wcsncmp(Context->NameBuffer, NameBuffer, CopyLength) == 0) &&
(Context->ExtensionLength = ExtLength) &&
(wcsncmp(Context->ExtensionBuffer, ExtBuffer, ExtLength) == 0))
CurrentIndex = Context->LastIndexValue + 1;
else
CurrentIndex = 1;
DPRINT("CurrentIndex: %hu\n", CurrentIndex);
/* Build the short name */
for (i = 0; i < CopyLength; i++)
{
Name8dot3->Buffer[i] = NameBuffer[i];
}
Name8dot3->Buffer[i++] = L'~';
if (CurrentIndex >= 10)
Name8dot3->Buffer[i++] = (CurrentIndex / 10) + L'0';
Name8dot3->Buffer[i++] = (CurrentIndex % 10) + L'0';
for (j = 0; j < ExtLength; i++, j++)
{
Name8dot3->Buffer[i] = ExtBuffer[j];
}
Name8dot3->Length = i * sizeof(WCHAR);
DPRINT("Name8dot3: '%wZ'\n", Name8dot3);
/* Update context */
Context->NameLength = CopyLength;
for (i = 0; i < CopyLength; i++)
{
Context->NameBuffer[i] = NameBuffer[i];
}
Context->ExtensionLength = ExtLength;
for (i = 0; i < ExtLength; i++)
{
Context->ExtensionBuffer[i] = ExtBuffer[i];
}
Context->LastIndexValue = CurrentIndex;
}
BOOLEAN STDCALL
RtlIsNameLegalDOS8Dot3(IN PUNICODE_STRING UnicodeName,
IN PANSI_STRING AnsiName,
OUT PBOOLEAN SpacesFound)
{
PANSI_STRING name = AnsiName;
ANSI_STRING DummyString;
CHAR Buffer[12];
char *str;
ULONG Length;
ULONG i;
NTSTATUS Status;
BOOLEAN HasSpace = FALSE;
BOOLEAN HasDot = FALSE;
if (UnicodeName->Length > 24)
{
return(FALSE); /* name too long */
}
if (!name)
{
name = &DummyString;
name->Length = 0;
name->MaximumLength = 12;
name->Buffer = Buffer;
}
Status = RtlUpcaseUnicodeStringToCountedOemString(name,
UnicodeName,
FALSE);
if (!NT_SUCCESS(Status))
{
return(FALSE);
}
Length = name->Length;
str = name->Buffer;
if (!(Length == 1 && *str == '.') &&
!(Length == 2 && *str == '.' && *(str + 1) == '.'))
{
for (i = 0; i < Length; i++, str++)
{
switch (*str)
{
case ' ':
HasSpace = TRUE;
break;
case '.':
if ((HasDot) || /* two dots */
(!i) || /* point is first char */
(i + 1 == Length) ||/* point is last char */
(Length - i > 4)) /* more than 3 chars of extension */
return(FALSE);
HasDot = TRUE;
break;
}
}
}
if (SpacesFound)
*SpacesFound = HasSpace;
return(TRUE);
}
/* EOF */

View file

@ -1,4 +1,4 @@
/* $Id: path.c,v 1.11 2001/06/12 12:29:40 ekohl Exp $
/* $Id: path.c,v 1.12 2002/06/05 16:50:43 ekohl Exp $
*
* COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS system libraries
@ -799,79 +799,8 @@ RtlDosSearchPath_U (
}
BOOLEAN
STDCALL
RtlIsNameLegalDOS8Dot3 (
PUNICODE_STRING UnicodeName,
PANSI_STRING AnsiName,
PBOOLEAN SpacesFound
)
{
PANSI_STRING name = AnsiName;
ANSI_STRING DummyString;
CHAR Buffer[12];
char *str;
ULONG Length;
ULONG i;
NTSTATUS Status;
BOOLEAN HasSpace = FALSE;
BOOLEAN HasDot = FALSE;
if (UnicodeName->Length > 24)
return FALSE; /* name too long */
if (!name)
{
name = &DummyString;
name->Length = 0;
name->MaximumLength = 12;
name->Buffer = Buffer;
}
Status = RtlUpcaseUnicodeStringToCountedOemString (name,
UnicodeName,
FALSE);
if (!NT_SUCCESS(Status))
return FALSE;
Length = name->Length;
str = name->Buffer;
if (!(Length == 1 && *str == '.') &&
!(Length == 2 && *str == '.' && *(str + 1) == '.'))
{
for (i = 0; i < Length; i++, str++)
{
switch (*str)
{
case ' ':
HasSpace = TRUE;
break;
case '.':
if ((HasDot) || /* two points */
(!i) || /* point is first char */
(i + 1 == Length) ||/* point is last char */
(Length - i > 4)) /* more than 3 chars of extension */
return FALSE;
HasDot = TRUE;
break;
}
}
}
if (SpacesFound)
*SpacesFound = HasSpace;
return TRUE;
}
BOOLEAN
STDCALL
RtlDoesFileExists_U (
IN PWSTR FileName
)
BOOLEAN STDCALL
RtlDoesFileExists_U(IN PWSTR FileName)
{
UNICODE_STRING NtFileName;
OBJECT_ATTRIBUTES Attr;

View file

@ -1,4 +1,4 @@
# $Id: Makefile,v 1.68 2002/05/05 14:57:42 chorns Exp $
# $Id: Makefile,v 1.69 2002/06/05 16:53:36 ekohl Exp $
#
# ReactOS Operating System
#
@ -83,6 +83,7 @@ OBJECTS_RTL = \
rtl/atom.o \
rtl/bitmap.o \
rtl/ctype.o \
rtl/dos8dot3.o \
rtl/error.o \
rtl/handle.o \
rtl/largeint.o \

View file

@ -1,4 +1,4 @@
; $Id: ntoskrnl.def,v 1.133 2002/05/02 23:45:32 dwelch Exp $
; $Id: ntoskrnl.def,v 1.134 2002/06/05 16:53:36 ekohl Exp $
;
; reactos/ntoskrnl/ntoskrnl.def
;
@ -731,7 +731,7 @@ RtlFreeAnsiString@4
;RtlFreeHeap
RtlFreeOemString@4
RtlFreeUnicodeString@4
;RtlGenerate8dot3Name
RtlGenerate8dot3Name@16
;RtlGetCallersAddress
;RtlGetCompressionWorkSpaceSize
RtlGetDaclSecurityDescriptor@16
@ -752,7 +752,7 @@ RtlInitializeSid@12
;RtlInsertUnicodePrefix
RtlIntegerToChar@16
RtlIntegerToUnicodeString@12
;RtlIsNameLegalDOS8Dot3
RtlIsNameLegalDOS8Dot3@12
RtlLargeIntegerAdd@16
RtlLargeIntegerArithmeticShift@12
RtlLargeIntegerDivide@20

View file

@ -1,4 +1,4 @@
; $Id: ntoskrnl.edf,v 1.119 2002/05/02 23:45:32 dwelch Exp $
; $Id: ntoskrnl.edf,v 1.120 2002/06/05 16:53:36 ekohl Exp $
;
; reactos/ntoskrnl/ntoskrnl.def
;
@ -731,7 +731,7 @@ RtlFreeAnsiString=RtlFreeAnsiString@4
;RtlFreeHeap
RtlFreeOemString=RtlFreeOemString@4
RtlFreeUnicodeString=RtlFreeUnicodeString@4
;RtlGenerate8dot3Name
RtlGenerate8dot3Name=RtlGenerate8dot3Name@16
;RtlGetCallersAddress
;RtlGetCompressionWorkSpaceSize
RtlGetDaclSecurityDescriptor=RtlGetDaclSecurityDescriptor@16
@ -752,7 +752,7 @@ RtlInitializeSid=RtlInitializeSid@12
;RtlInsertUnicodePrefix
RtlIntegerToChar=RtlIntegerToChar@16
RtlIntegerToUnicodeString=RtlIntegerToUnicodeString@12
;RtlIsNameLegalDOS8Dot3
RtlIsNameLegalDOS8Dot3=RtlIsNameLegalDOS8Dot3@12
RtlLargeIntegerAdd=RtlLargeIntegerAdd@16
RtlLargeIntegerArithmeticShift=RtlLargeIntegerArithmeticShift@12
RtlLargeIntegerDivide=RtlLargeIntegerDivide@20

View file

@ -0,0 +1,241 @@
/*
* ReactOS kernel
* Copyright (C) 2002 ReactOS Team
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* $Id: dos8dot3.c,v 1.1 2002/06/05 16:52:43 ekohl Exp $
*
* COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS kernel
* FILE: ntoskrnl/rtl/dos8dot3.c
* PURPOSE: Short name (8.3 name) functions
* PROGRAMMER: Eric Kohl
*/
/* INCLUDES ******************************************************************/
#include <ddk/ntddk.h>
#include <ntos/minmax.h>
#define NDEBUG
#include <internal/debug.h>
/* CONSTANTS *****************************************************************/
const PWCHAR RtlpShortIllegals = L" ;+=[]',\"*\\<>/?:|";
/* FUNCTIONS *****************************************************************/
static BOOLEAN
RtlpIsShortIllegal(WCHAR Char)
{
int i;
for (i = 0; RtlpShortIllegals[i]; i++)
{
if (Char == RtlpShortIllegals[i])
return(TRUE);
}
return(FALSE);
}
VOID STDCALL
RtlGenerate8dot3Name(IN PUNICODE_STRING Name,
IN BOOLEAN AllowExtendedCharacters,
IN OUT PGENERATE_NAME_CONTEXT Context,
OUT PUNICODE_STRING Name8dot3)
{
WCHAR NameBuffer[8];
WCHAR ExtBuffer[4];
USHORT StrLength;
USHORT NameLength;
USHORT ExtLength;
USHORT CopyLength;
USHORT DotPos;
USHORT i, j;
USHORT CurrentIndex;
memset(NameBuffer, 0, sizeof(NameBuffer));
memset(ExtBuffer, 0, sizeof(ExtBuffer));
StrLength = Name->Length / sizeof(WCHAR);
DPRINT("StrLength: %hu\n", StrLength);
/* Find last dot in Name */
DotPos = 0;
for (i = 0; i < StrLength; i++)
{
if (Name->Buffer[i] == L'.')
{
DotPos = i;
}
}
if (DotPos == 0)
{
DotPos = i;
}
DPRINT("DotPos: %hu\n", DotPos);
/* Copy name (6 valid characters max) */
for (i = 0, NameLength = 0; NameLength < 6 && i < DotPos; i++)
{
if ((!RtlpIsShortIllegal(Name->Buffer[i])) &&
(Name->Buffer[i] != L'.'))
{
NameBuffer[NameLength++] = RtlUpcaseUnicodeChar(Name->Buffer[i]);
}
}
DPRINT("NameBuffer: '%.08S'\n", NameBuffer);
DPRINT("NameLength: %hu\n", NameLength);
/* Copy extension (4 valid characters max) */
if (DotPos < StrLength)
{
for (i = DotPos, ExtLength = 0; ExtLength < 4 && i < StrLength; i++)
{
if (!RtlpIsShortIllegal(Name->Buffer[i]))
{
ExtBuffer[ExtLength++] = RtlUpcaseUnicodeChar(Name->Buffer[i]);
}
}
}
DPRINT("ExtBuffer: '%.04S'\n", ExtBuffer);
DPRINT("ExtLength: %hu\n", ExtLength);
/* Determine next index */
CopyLength = min(NameLength, (CurrentIndex < 10) ? 6 : 5);
if ((Context->NameLength == CopyLength) &&
(wcsncmp(Context->NameBuffer, NameBuffer, CopyLength) == 0) &&
(Context->ExtensionLength = ExtLength) &&
(wcsncmp(Context->ExtensionBuffer, ExtBuffer, ExtLength) == 0))
CurrentIndex = Context->LastIndexValue + 1;
else
CurrentIndex = 1;
DPRINT("CurrentIndex: %hu\n", CurrentIndex);
/* Build the short name */
for (i = 0; i < CopyLength; i++)
{
Name8dot3->Buffer[i] = NameBuffer[i];
}
Name8dot3->Buffer[i++] = L'~';
if (CurrentIndex >= 10)
Name8dot3->Buffer[i++] = (CurrentIndex / 10) + L'0';
Name8dot3->Buffer[i++] = (CurrentIndex % 10) + L'0';
for (j = 0; j < ExtLength; i++, j++)
{
Name8dot3->Buffer[i] = ExtBuffer[j];
}
Name8dot3->Length = i * sizeof(WCHAR);
DPRINT("Name8dot3: '%wZ'\n", Name8dot3);
/* Update context */
Context->NameLength = CopyLength;
for (i = 0; i < CopyLength; i++)
{
Context->NameBuffer[i] = NameBuffer[i];
}
Context->ExtensionLength = ExtLength;
for (i = 0; i < ExtLength; i++)
{
Context->ExtensionBuffer[i] = ExtBuffer[i];
}
Context->LastIndexValue = CurrentIndex;
}
BOOLEAN STDCALL
RtlIsNameLegalDOS8Dot3(IN PUNICODE_STRING UnicodeName,
IN PANSI_STRING AnsiName,
OUT PBOOLEAN SpacesFound)
{
PANSI_STRING name = AnsiName;
ANSI_STRING DummyString;
CHAR Buffer[12];
char *str;
ULONG Length;
ULONG i;
NTSTATUS Status;
BOOLEAN HasSpace = FALSE;
BOOLEAN HasDot = FALSE;
if (UnicodeName->Length > 24)
{
return(FALSE); /* name too long */
}
if (!name)
{
name = &DummyString;
name->Length = 0;
name->MaximumLength = 12;
name->Buffer = Buffer;
}
Status = RtlUpcaseUnicodeStringToCountedOemString(name,
UnicodeName,
FALSE);
if (!NT_SUCCESS(Status))
{
return(FALSE);
}
Length = name->Length;
str = name->Buffer;
if (!(Length == 1 && *str == '.') &&
!(Length == 2 && *str == '.' && *(str + 1) == '.'))
{
for (i = 0; i < Length; i++, str++)
{
switch (*str)
{
case ' ':
HasSpace = TRUE;
break;
case '.':
if ((HasDot) || /* two dots */
(!i) || /* point is first char */
(i + 1 == Length) ||/* point is last char */
(Length - i > 4)) /* more than 3 chars of extension */
return(FALSE);
HasDot = TRUE;
break;
}
}
}
if (SpacesFound)
*SpacesFound = HasSpace;
return(TRUE);
}
/* EOF */