[NTOSKRNL]

- Make ObpParseSymbolicLink properly handle the case when target path has a trailing path separator. Based on findings by Samarunraj.
See issue #993 for more details.

svn path=/trunk/; revision=51665
This commit is contained in:
Aleksey Bragin 2011-05-10 15:09:36 +00:00
parent 1335fefcd9
commit 5f617a7c44

View file

@ -374,7 +374,7 @@ ObpParseSymbolicLink(IN PVOID ParsedObject,
POBJECT_SYMBOLIC_LINK SymlinkObject = (POBJECT_SYMBOLIC_LINK)ParsedObject; POBJECT_SYMBOLIC_LINK SymlinkObject = (POBJECT_SYMBOLIC_LINK)ParsedObject;
PUNICODE_STRING TargetPath; PUNICODE_STRING TargetPath;
PWSTR NewTargetPath; PWSTR NewTargetPath;
ULONG LengthUsed, MaximumLength; ULONG LengthUsed, MaximumLength, TempLength;
NTSTATUS Status; NTSTATUS Status;
PAGED_CODE(); PAGED_CODE();
@ -411,9 +411,39 @@ ObpParseSymbolicLink(IN PVOID ParsedObject,
return STATUS_OBJECT_TYPE_MISMATCH; return STATUS_OBJECT_TYPE_MISMATCH;
} }
/* Check if this symlink is bound to a specific object */
if (SymlinkObject->LinkTargetObject)
{
UNIMPLEMENTED;
}
/* Set the target path and length */ /* Set the target path and length */
TargetPath = &SymlinkObject->LinkTarget; TargetPath = &SymlinkObject->LinkTarget;
LengthUsed = TargetPath->Length + RemainingName->Length; TempLength = TargetPath->Length;
/*
* Strip off the extra trailing '\', if we don't do this we will end up
* adding a extra '\' between TargetPath and RemainingName
* causing caller's like ObpLookupObjectName() to fail.
*/
if (TempLength && RemainingName->Length)
{
/* The target and remaining names aren't empty, so check for slashes */
if ((TargetPath->Buffer[TempLength / sizeof(WCHAR) - 1] ==
OBJ_NAME_PATH_SEPARATOR) &&
(RemainingName->Buffer[0] == OBJ_NAME_PATH_SEPARATOR))
{
/* Reduce the length by one to cut off the extra '\' */
TempLength -= sizeof(OBJ_NAME_PATH_SEPARATOR);
}
}
/* Calculate the new length */
LengthUsed = TempLength + RemainingName->Length;
/* Check if it's not too much */
if (LengthUsed > 0xFFF0)
return STATUS_NAME_TOO_LONG;
/* Optimization: check if the new name is shorter */ /* Optimization: check if the new name is shorter */
if (FullPath->MaximumLength <= LengthUsed) if (FullPath->MaximumLength <= LengthUsed)
@ -436,13 +466,13 @@ ObpParseSymbolicLink(IN PVOID ParsedObject,
if (RemainingName->Length) if (RemainingName->Length)
{ {
/* Copy the new path */ /* Copy the new path */
RtlMoveMemory((PVOID)((ULONG_PTR)NewTargetPath + TargetPath->Length), RtlMoveMemory((PVOID)((ULONG_PTR)NewTargetPath + TempLength),
RemainingName->Buffer, RemainingName->Buffer,
RemainingName->Length); RemainingName->Length);
} }
/* Copy the target path and null-terminate it */ /* Copy the target path and null-terminate it */
RtlCopyMemory(NewTargetPath, TargetPath->Buffer, TargetPath->Length); RtlCopyMemory(NewTargetPath, TargetPath->Buffer, TempLength);
NewTargetPath[LengthUsed / sizeof(WCHAR)] = UNICODE_NULL; NewTargetPath[LengthUsed / sizeof(WCHAR)] = UNICODE_NULL;
/* If the optimization didn't work, free the old buffer */ /* If the optimization didn't work, free the old buffer */