mirror of
https://github.com/reactos/reactos.git
synced 2024-12-28 01:55:19 +00:00
[NTFS] Apply fix from 52f0726
: allow partial info copy on dir enumeration on first entry return.
This is assorted with misc fixes to make this code closer to what we currently have in FastFAT. This also allows fixing a memory leak in case of single entry return. CORE-13367
This commit is contained in:
parent
1014d50a4b
commit
7bea4ec07e
1 changed files with 202 additions and 104 deletions
|
@ -60,18 +60,32 @@ NtfsGetFileSize(PDEVICE_EXTENSION DeviceExt,
|
|||
}
|
||||
|
||||
|
||||
#define ULONG_ROUND_UP(x) ROUND_UP((x), (sizeof(ULONG)))
|
||||
|
||||
|
||||
static NTSTATUS
|
||||
NtfsGetNamesInformation(PDEVICE_EXTENSION DeviceExt,
|
||||
PFILE_RECORD_HEADER FileRecord,
|
||||
ULONGLONG MFTIndex,
|
||||
PFILE_NAMES_INFORMATION Info,
|
||||
ULONG BufferLength)
|
||||
ULONG BufferLength,
|
||||
PULONG Written,
|
||||
BOOLEAN First)
|
||||
{
|
||||
ULONG Length;
|
||||
NTSTATUS Status;
|
||||
ULONG BytesToCopy = 0;
|
||||
PFILENAME_ATTRIBUTE FileName;
|
||||
|
||||
DPRINT("NtfsGetNamesInformation() called\n");
|
||||
|
||||
*Written = 0;
|
||||
Status = STATUS_BUFFER_OVERFLOW;
|
||||
if (FIELD_OFFSET(FILE_NAMES_INFORMATION, FileName) > BufferLength)
|
||||
{
|
||||
return Status;
|
||||
}
|
||||
|
||||
FileName = GetBestFileNameFromRecord(DeviceExt, FileRecord);
|
||||
if (FileName == NULL)
|
||||
{
|
||||
|
@ -81,15 +95,28 @@ NtfsGetNamesInformation(PDEVICE_EXTENSION DeviceExt,
|
|||
}
|
||||
|
||||
Length = FileName->NameLength * sizeof (WCHAR);
|
||||
if ((sizeof(FILE_NAMES_INFORMATION) + Length) > BufferLength)
|
||||
return(STATUS_BUFFER_OVERFLOW);
|
||||
if (First || (BufferLength >= FIELD_OFFSET(FILE_NAMES_INFORMATION, FileName) + Length))
|
||||
{
|
||||
Info->FileNameLength = Length;
|
||||
|
||||
Info->FileNameLength = Length;
|
||||
Info->NextEntryOffset =
|
||||
ROUND_UP(sizeof(FILE_NAMES_INFORMATION) + Length, sizeof(ULONG));
|
||||
RtlCopyMemory(Info->FileName, FileName->Name, Length);
|
||||
*Written = FIELD_OFFSET(FILE_NAMES_INFORMATION, FileName);
|
||||
Info->NextEntryOffset = 0;
|
||||
if (BufferLength > FIELD_OFFSET(FILE_NAMES_INFORMATION, FileName))
|
||||
{
|
||||
BytesToCopy = min(Length, BufferLength - FIELD_OFFSET(FILE_NAMES_INFORMATION, FileName));
|
||||
RtlCopyMemory(Info->FileName, FileName->Name, BytesToCopy);
|
||||
*Written += BytesToCopy;
|
||||
|
||||
return(STATUS_SUCCESS);
|
||||
if (BytesToCopy == Length)
|
||||
{
|
||||
Info->NextEntryOffset = ULONG_ROUND_UP(sizeof(FILE_NAMES_INFORMATION) +
|
||||
BytesToCopy);
|
||||
Status = STATUS_SUCCESS;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
||||
|
@ -98,14 +125,25 @@ NtfsGetDirectoryInformation(PDEVICE_EXTENSION DeviceExt,
|
|||
PFILE_RECORD_HEADER FileRecord,
|
||||
ULONGLONG MFTIndex,
|
||||
PFILE_DIRECTORY_INFORMATION Info,
|
||||
ULONG BufferLength)
|
||||
ULONG BufferLength,
|
||||
PULONG Written,
|
||||
BOOLEAN First)
|
||||
{
|
||||
ULONG Length;
|
||||
NTSTATUS Status;
|
||||
ULONG BytesToCopy = 0;
|
||||
PFILENAME_ATTRIBUTE FileName;
|
||||
PSTANDARD_INFORMATION StdInfo;
|
||||
|
||||
DPRINT("NtfsGetDirectoryInformation() called\n");
|
||||
|
||||
*Written = 0;
|
||||
Status = STATUS_BUFFER_OVERFLOW;
|
||||
if (FIELD_OFFSET(FILE_DIRECTORY_INFORMATION, FileName) > BufferLength)
|
||||
{
|
||||
return Status;
|
||||
}
|
||||
|
||||
FileName = GetBestFileNameFromRecord(DeviceExt, FileRecord);
|
||||
if (FileName == NULL)
|
||||
{
|
||||
|
@ -118,27 +156,40 @@ NtfsGetDirectoryInformation(PDEVICE_EXTENSION DeviceExt,
|
|||
ASSERT(StdInfo != NULL);
|
||||
|
||||
Length = FileName->NameLength * sizeof (WCHAR);
|
||||
if ((sizeof(FILE_DIRECTORY_INFORMATION) + Length) > BufferLength)
|
||||
return(STATUS_BUFFER_OVERFLOW);
|
||||
if (First || (BufferLength >= FIELD_OFFSET(FILE_DIRECTORY_INFORMATION, FileName) + Length))
|
||||
{
|
||||
Info->FileNameLength = Length;
|
||||
|
||||
Info->FileNameLength = Length;
|
||||
Info->NextEntryOffset =
|
||||
ROUND_UP(sizeof(FILE_DIRECTORY_INFORMATION) + Length, sizeof(ULONG));
|
||||
RtlCopyMemory(Info->FileName, FileName->Name, Length);
|
||||
*Written = FIELD_OFFSET(FILE_DIRECTORY_INFORMATION, FileName);
|
||||
Info->NextEntryOffset = 0;
|
||||
if (BufferLength > FIELD_OFFSET(FILE_DIRECTORY_INFORMATION, FileName))
|
||||
{
|
||||
BytesToCopy = min(Length, BufferLength - FIELD_OFFSET(FILE_DIRECTORY_INFORMATION, FileName));
|
||||
RtlCopyMemory(Info->FileName, FileName->Name, BytesToCopy);
|
||||
*Written += BytesToCopy;
|
||||
|
||||
Info->CreationTime.QuadPart = FileName->CreationTime;
|
||||
Info->LastAccessTime.QuadPart = FileName->LastAccessTime;
|
||||
Info->LastWriteTime.QuadPart = FileName->LastWriteTime;
|
||||
Info->ChangeTime.QuadPart = FileName->ChangeTime;
|
||||
if (BytesToCopy == Length)
|
||||
{
|
||||
Info->NextEntryOffset = ULONG_ROUND_UP(sizeof(FILE_DIRECTORY_INFORMATION) +
|
||||
BytesToCopy);
|
||||
Status = STATUS_SUCCESS;
|
||||
}
|
||||
}
|
||||
|
||||
/* Convert file flags */
|
||||
NtfsFileFlagsToAttributes(FileName->FileAttributes | StdInfo->FileAttribute, &Info->FileAttributes);
|
||||
Info->CreationTime.QuadPart = FileName->CreationTime;
|
||||
Info->LastAccessTime.QuadPart = FileName->LastAccessTime;
|
||||
Info->LastWriteTime.QuadPart = FileName->LastWriteTime;
|
||||
Info->ChangeTime.QuadPart = FileName->ChangeTime;
|
||||
|
||||
Info->EndOfFile.QuadPart = NtfsGetFileSize(DeviceExt, FileRecord, L"", 0, (PULONGLONG)&Info->AllocationSize.QuadPart);
|
||||
/* Convert file flags */
|
||||
NtfsFileFlagsToAttributes(FileName->FileAttributes | StdInfo->FileAttribute, &Info->FileAttributes);
|
||||
|
||||
Info->FileIndex = MFTIndex;
|
||||
Info->EndOfFile.QuadPart = NtfsGetFileSize(DeviceExt, FileRecord, L"", 0, (PULONGLONG)&Info->AllocationSize.QuadPart);
|
||||
|
||||
return STATUS_SUCCESS;
|
||||
Info->FileIndex = MFTIndex;
|
||||
}
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
||||
|
@ -147,14 +198,25 @@ NtfsGetFullDirectoryInformation(PDEVICE_EXTENSION DeviceExt,
|
|||
PFILE_RECORD_HEADER FileRecord,
|
||||
ULONGLONG MFTIndex,
|
||||
PFILE_FULL_DIRECTORY_INFORMATION Info,
|
||||
ULONG BufferLength)
|
||||
ULONG BufferLength,
|
||||
PULONG Written,
|
||||
BOOLEAN First)
|
||||
{
|
||||
ULONG Length;
|
||||
NTSTATUS Status;
|
||||
ULONG BytesToCopy = 0;
|
||||
PFILENAME_ATTRIBUTE FileName;
|
||||
PSTANDARD_INFORMATION StdInfo;
|
||||
|
||||
DPRINT("NtfsGetFullDirectoryInformation() called\n");
|
||||
|
||||
*Written = 0;
|
||||
Status = STATUS_BUFFER_OVERFLOW;
|
||||
if (FIELD_OFFSET(FILE_FULL_DIR_INFORMATION, FileName) > BufferLength)
|
||||
{
|
||||
return Status;
|
||||
}
|
||||
|
||||
FileName = GetBestFileNameFromRecord(DeviceExt, FileRecord);
|
||||
if (FileName == NULL)
|
||||
{
|
||||
|
@ -167,28 +229,41 @@ NtfsGetFullDirectoryInformation(PDEVICE_EXTENSION DeviceExt,
|
|||
ASSERT(StdInfo != NULL);
|
||||
|
||||
Length = FileName->NameLength * sizeof (WCHAR);
|
||||
if ((sizeof(FILE_FULL_DIRECTORY_INFORMATION) + Length) > BufferLength)
|
||||
return(STATUS_BUFFER_OVERFLOW);
|
||||
if (First || (BufferLength >= FIELD_OFFSET(FILE_FULL_DIR_INFORMATION, FileName) + Length))
|
||||
{
|
||||
Info->FileNameLength = Length;
|
||||
|
||||
Info->FileNameLength = Length;
|
||||
Info->NextEntryOffset =
|
||||
ROUND_UP(sizeof(FILE_FULL_DIRECTORY_INFORMATION) + Length, sizeof(ULONG));
|
||||
RtlCopyMemory(Info->FileName, FileName->Name, Length);
|
||||
*Written = FIELD_OFFSET(FILE_FULL_DIR_INFORMATION, FileName);
|
||||
Info->NextEntryOffset = 0;
|
||||
if (BufferLength > FIELD_OFFSET(FILE_FULL_DIR_INFORMATION, FileName))
|
||||
{
|
||||
BytesToCopy = min(Length, BufferLength - FIELD_OFFSET(FILE_FULL_DIR_INFORMATION, FileName));
|
||||
RtlCopyMemory(Info->FileName, FileName->Name, BytesToCopy);
|
||||
*Written += BytesToCopy;
|
||||
|
||||
Info->CreationTime.QuadPart = FileName->CreationTime;
|
||||
Info->LastAccessTime.QuadPart = FileName->LastAccessTime;
|
||||
Info->LastWriteTime.QuadPart = FileName->LastWriteTime;
|
||||
Info->ChangeTime.QuadPart = FileName->ChangeTime;
|
||||
if (BytesToCopy == Length)
|
||||
{
|
||||
Info->NextEntryOffset = ULONG_ROUND_UP(sizeof(FILE_FULL_DIR_INFORMATION) +
|
||||
BytesToCopy);
|
||||
Status = STATUS_SUCCESS;
|
||||
}
|
||||
}
|
||||
|
||||
/* Convert file flags */
|
||||
NtfsFileFlagsToAttributes(FileName->FileAttributes | StdInfo->FileAttribute, &Info->FileAttributes);
|
||||
Info->CreationTime.QuadPart = FileName->CreationTime;
|
||||
Info->LastAccessTime.QuadPart = FileName->LastAccessTime;
|
||||
Info->LastWriteTime.QuadPart = FileName->LastWriteTime;
|
||||
Info->ChangeTime.QuadPart = FileName->ChangeTime;
|
||||
|
||||
Info->EndOfFile.QuadPart = NtfsGetFileSize(DeviceExt, FileRecord, L"", 0, (PULONGLONG)&Info->AllocationSize.QuadPart);
|
||||
/* Convert file flags */
|
||||
NtfsFileFlagsToAttributes(FileName->FileAttributes | StdInfo->FileAttribute, &Info->FileAttributes);
|
||||
|
||||
Info->FileIndex = MFTIndex;
|
||||
Info->EaSize = 0;
|
||||
Info->EndOfFile.QuadPart = NtfsGetFileSize(DeviceExt, FileRecord, L"", 0, (PULONGLONG)&Info->AllocationSize.QuadPart);
|
||||
|
||||
return STATUS_SUCCESS;
|
||||
Info->FileIndex = MFTIndex;
|
||||
Info->EaSize = 0;
|
||||
}
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
||||
|
@ -197,14 +272,25 @@ NtfsGetBothDirectoryInformation(PDEVICE_EXTENSION DeviceExt,
|
|||
PFILE_RECORD_HEADER FileRecord,
|
||||
ULONGLONG MFTIndex,
|
||||
PFILE_BOTH_DIR_INFORMATION Info,
|
||||
ULONG BufferLength)
|
||||
ULONG BufferLength,
|
||||
PULONG Written,
|
||||
BOOLEAN First)
|
||||
{
|
||||
ULONG Length;
|
||||
NTSTATUS Status;
|
||||
ULONG BytesToCopy = 0;
|
||||
PFILENAME_ATTRIBUTE FileName, ShortFileName;
|
||||
PSTANDARD_INFORMATION StdInfo;
|
||||
|
||||
DPRINT("NtfsGetBothDirectoryInformation() called\n");
|
||||
|
||||
*Written = 0;
|
||||
Status = STATUS_BUFFER_OVERFLOW;
|
||||
if (FIELD_OFFSET(FILE_BOTH_DIR_INFORMATION, FileName) > BufferLength)
|
||||
{
|
||||
return Status;
|
||||
}
|
||||
|
||||
FileName = GetBestFileNameFromRecord(DeviceExt, FileRecord);
|
||||
if (FileName == NULL)
|
||||
{
|
||||
|
@ -218,41 +304,54 @@ NtfsGetBothDirectoryInformation(PDEVICE_EXTENSION DeviceExt,
|
|||
ASSERT(StdInfo != NULL);
|
||||
|
||||
Length = FileName->NameLength * sizeof (WCHAR);
|
||||
if ((sizeof(FILE_BOTH_DIR_INFORMATION) + Length) > BufferLength)
|
||||
return(STATUS_BUFFER_OVERFLOW);
|
||||
|
||||
Info->FileNameLength = Length;
|
||||
Info->NextEntryOffset =
|
||||
ROUND_UP(sizeof(FILE_BOTH_DIR_INFORMATION) + Length, sizeof(ULONG));
|
||||
RtlCopyMemory(Info->FileName, FileName->Name, Length);
|
||||
|
||||
if (ShortFileName)
|
||||
if (First || (BufferLength >= FIELD_OFFSET(FILE_BOTH_DIR_INFORMATION, FileName) + Length))
|
||||
{
|
||||
/* Should we upcase the filename? */
|
||||
ASSERT(ShortFileName->NameLength <= ARRAYSIZE(Info->ShortName));
|
||||
Info->ShortNameLength = ShortFileName->NameLength * sizeof(WCHAR);
|
||||
RtlCopyMemory(Info->ShortName, ShortFileName->Name, Info->ShortNameLength);
|
||||
}
|
||||
else
|
||||
{
|
||||
Info->ShortName[0] = 0;
|
||||
Info->ShortNameLength = 0;
|
||||
Info->FileNameLength = Length;
|
||||
|
||||
*Written = FIELD_OFFSET(FILE_BOTH_DIR_INFORMATION, FileName);
|
||||
Info->NextEntryOffset = 0;
|
||||
if (BufferLength > FIELD_OFFSET(FILE_BOTH_DIR_INFORMATION, FileName))
|
||||
{
|
||||
BytesToCopy = min(Length, BufferLength - FIELD_OFFSET(FILE_BOTH_DIR_INFORMATION, FileName));
|
||||
RtlCopyMemory(Info->FileName, FileName->Name, BytesToCopy);
|
||||
*Written += BytesToCopy;
|
||||
|
||||
if (BytesToCopy == Length)
|
||||
{
|
||||
Info->NextEntryOffset = ULONG_ROUND_UP(sizeof(FILE_BOTH_DIR_INFORMATION) +
|
||||
BytesToCopy);
|
||||
Status = STATUS_SUCCESS;
|
||||
}
|
||||
}
|
||||
|
||||
if (ShortFileName)
|
||||
{
|
||||
/* Should we upcase the filename? */
|
||||
ASSERT(ShortFileName->NameLength <= ARRAYSIZE(Info->ShortName));
|
||||
Info->ShortNameLength = ShortFileName->NameLength * sizeof(WCHAR);
|
||||
RtlCopyMemory(Info->ShortName, ShortFileName->Name, Info->ShortNameLength);
|
||||
}
|
||||
else
|
||||
{
|
||||
Info->ShortName[0] = 0;
|
||||
Info->ShortNameLength = 0;
|
||||
}
|
||||
|
||||
Info->CreationTime.QuadPart = FileName->CreationTime;
|
||||
Info->LastAccessTime.QuadPart = FileName->LastAccessTime;
|
||||
Info->LastWriteTime.QuadPart = FileName->LastWriteTime;
|
||||
Info->ChangeTime.QuadPart = FileName->ChangeTime;
|
||||
|
||||
/* Convert file flags */
|
||||
NtfsFileFlagsToAttributes(FileName->FileAttributes | StdInfo->FileAttribute, &Info->FileAttributes);
|
||||
|
||||
Info->EndOfFile.QuadPart = NtfsGetFileSize(DeviceExt, FileRecord, L"", 0, (PULONGLONG)&Info->AllocationSize.QuadPart);
|
||||
|
||||
Info->FileIndex = MFTIndex;
|
||||
Info->EaSize = 0;
|
||||
}
|
||||
|
||||
Info->CreationTime.QuadPart = FileName->CreationTime;
|
||||
Info->LastAccessTime.QuadPart = FileName->LastAccessTime;
|
||||
Info->LastWriteTime.QuadPart = FileName->LastWriteTime;
|
||||
Info->ChangeTime.QuadPart = FileName->ChangeTime;
|
||||
|
||||
/* Convert file flags */
|
||||
NtfsFileFlagsToAttributes(FileName->FileAttributes | StdInfo->FileAttribute, &Info->FileAttributes);
|
||||
|
||||
Info->EndOfFile.QuadPart = NtfsGetFileSize(DeviceExt, FileRecord, L"", 0, (PULONGLONG)&Info->AllocationSize.QuadPart);
|
||||
|
||||
Info->FileIndex = MFTIndex;
|
||||
Info->EaSize = 0;
|
||||
|
||||
return STATUS_SUCCESS;
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
||||
|
@ -277,6 +376,7 @@ NtfsQueryDirectory(PNTFS_IRP_CONTEXT IrpContext)
|
|||
PFILE_RECORD_HEADER FileRecord;
|
||||
ULONGLONG MFTRecord, OldMFTRecord = 0;
|
||||
UNICODE_STRING Pattern;
|
||||
ULONG Written;
|
||||
|
||||
DPRINT1("NtfsQueryDirectory() called\n");
|
||||
|
||||
|
@ -350,7 +450,7 @@ NtfsQueryDirectory(PNTFS_IRP_CONTEXT IrpContext)
|
|||
/* Determine directory index */
|
||||
if (Stack->Flags & SL_INDEX_SPECIFIED)
|
||||
{
|
||||
Ccb->Entry = Ccb->CurrentByteOffset.u.LowPart;
|
||||
Ccb->Entry = FileIndex;
|
||||
}
|
||||
else if (First || (Stack->Flags & SL_RESTART_SCAN))
|
||||
{
|
||||
|
@ -369,6 +469,7 @@ NtfsQueryDirectory(PNTFS_IRP_CONTEXT IrpContext)
|
|||
return STATUS_PENDING;
|
||||
}
|
||||
|
||||
Written = 0;
|
||||
while (Status == STATUS_SUCCESS && BufferLength > 0)
|
||||
{
|
||||
Status = NtfsFindFileAt(DeviceExtension,
|
||||
|
@ -400,7 +501,9 @@ NtfsQueryDirectory(PNTFS_IRP_CONTEXT IrpContext)
|
|||
FileRecord,
|
||||
MFTRecord,
|
||||
(PFILE_NAMES_INFORMATION)Buffer,
|
||||
BufferLength);
|
||||
BufferLength,
|
||||
&Written,
|
||||
Buffer0 == NULL);
|
||||
break;
|
||||
|
||||
case FileDirectoryInformation:
|
||||
|
@ -408,7 +511,9 @@ NtfsQueryDirectory(PNTFS_IRP_CONTEXT IrpContext)
|
|||
FileRecord,
|
||||
MFTRecord,
|
||||
(PFILE_DIRECTORY_INFORMATION)Buffer,
|
||||
BufferLength);
|
||||
BufferLength,
|
||||
&Written,
|
||||
Buffer0 == NULL);
|
||||
break;
|
||||
|
||||
case FileFullDirectoryInformation:
|
||||
|
@ -416,7 +521,9 @@ NtfsQueryDirectory(PNTFS_IRP_CONTEXT IrpContext)
|
|||
FileRecord,
|
||||
MFTRecord,
|
||||
(PFILE_FULL_DIRECTORY_INFORMATION)Buffer,
|
||||
BufferLength);
|
||||
BufferLength,
|
||||
&Written,
|
||||
Buffer0 == NULL);
|
||||
break;
|
||||
|
||||
case FileBothDirectoryInformation:
|
||||
|
@ -424,66 +531,57 @@ NtfsQueryDirectory(PNTFS_IRP_CONTEXT IrpContext)
|
|||
FileRecord,
|
||||
MFTRecord,
|
||||
(PFILE_BOTH_DIR_INFORMATION)Buffer,
|
||||
BufferLength);
|
||||
BufferLength,
|
||||
&Written,
|
||||
Buffer0 == NULL);
|
||||
break;
|
||||
|
||||
default:
|
||||
Status = STATUS_INVALID_INFO_CLASS;
|
||||
}
|
||||
|
||||
if (Status == STATUS_BUFFER_OVERFLOW)
|
||||
if (Status == STATUS_BUFFER_OVERFLOW || Status == STATUS_INVALID_INFO_CLASS)
|
||||
{
|
||||
if (Buffer0)
|
||||
{
|
||||
Buffer0->NextEntryOffset = 0;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Buffer0)
|
||||
{
|
||||
Buffer0->NextEntryOffset = 0;
|
||||
}
|
||||
|
||||
if (First)
|
||||
{
|
||||
Status = STATUS_NO_SUCH_FILE;
|
||||
}
|
||||
else
|
||||
{
|
||||
Status = STATUS_NO_MORE_FILES;
|
||||
}
|
||||
Status = (First ? STATUS_NO_SUCH_FILE : STATUS_NO_MORE_FILES);
|
||||
break;
|
||||
}
|
||||
|
||||
Buffer0 = (PFILE_NAMES_INFORMATION)Buffer;
|
||||
Buffer0->FileIndex = FileIndex++;
|
||||
Ccb->Entry++;
|
||||
BufferLength -= Buffer0->NextEntryOffset;
|
||||
|
||||
ExFreeToNPagedLookasideList(&DeviceExtension->FileRecLookasideList, FileRecord);
|
||||
|
||||
if (Stack->Flags & SL_RETURN_SINGLE_ENTRY)
|
||||
{
|
||||
break;
|
||||
}
|
||||
BufferLength -= Buffer0->NextEntryOffset;
|
||||
|
||||
Buffer += Buffer0->NextEntryOffset;
|
||||
ExFreeToNPagedLookasideList(&DeviceExtension->FileRecLookasideList, FileRecord);
|
||||
}
|
||||
|
||||
if (Buffer0)
|
||||
{
|
||||
Buffer0->NextEntryOffset = 0;
|
||||
Status = STATUS_SUCCESS;
|
||||
IrpContext->Irp->IoStatus.Information = Stack->Parameters.QueryDirectory.Length - BufferLength;
|
||||
}
|
||||
else
|
||||
{
|
||||
ASSERT(Status != STATUS_SUCCESS || BufferLength == 0);
|
||||
ASSERT(Written <= Stack->Parameters.QueryDirectory.Length);
|
||||
IrpContext->Irp->IoStatus.Information = Written;
|
||||
}
|
||||
|
||||
ExReleaseResourceLite(&DeviceExtension->DirResource);
|
||||
ExReleaseResourceLite(&Fcb->MainResource);
|
||||
|
||||
if (FileIndex > 0)
|
||||
{
|
||||
Status = STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue