mirror of
https://github.com/winfsp/winfsp.git
synced 2025-04-22 00:13:01 -05:00
sys: dirctl: support directory marker as FUSE style next offset
This commit is contained in:
parent
847eab3da4
commit
5110b3c5a1
@ -96,7 +96,7 @@ FSP_FSCTL_STATIC_ASSERT(FSP_FSCTL_VOLUME_NAME_SIZEMAX <= 260 * sizeof(WCHAR),
|
||||
|
||||
/* marshalling */
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable:4200) /* zero-sized array in struct/union */
|
||||
#pragma warning(disable:4200 4201) /* zero-sized array in struct/union; nameless struct/union */
|
||||
enum
|
||||
{
|
||||
FspFsctlTransactReservedKind = 0,
|
||||
@ -175,7 +175,8 @@ enum
|
||||
UINT32 AllowOpenInKernelMode:1; /* allow kernel mode to open files when possible */\
|
||||
UINT32 CasePreservedExtendedAttributes:1; /* preserve case of EA (default is UPPERCASE) */\
|
||||
UINT32 WslFeatures:1; /* support features required for WSLinux */\
|
||||
UINT32 KmReservedFlags:5;\
|
||||
UINT32 DirectoryMarkerAsNextOffset:1; /* directory marker is next offset instead of last name */\
|
||||
UINT32 KmReservedFlags:4;\
|
||||
WCHAR Prefix[FSP_FSCTL_VOLUME_PREFIX_SIZE / sizeof(WCHAR)]; /* UNC prefix (\Server\Share) */\
|
||||
WCHAR FileSystemName[FSP_FSCTL_VOLUME_FSNAME_SIZE / sizeof(WCHAR)];
|
||||
#define FSP_FSCTL_VOLUME_PARAMS_V1_FIELD_DEFN\
|
||||
@ -242,8 +243,12 @@ typedef struct
|
||||
{
|
||||
UINT16 Size;
|
||||
FSP_FSCTL_FILE_INFO FileInfo;
|
||||
UINT8 Padding[24];
|
||||
/* make struct as big as FILE_ID_BOTH_DIR_INFORMATION; allows for in-place copying */
|
||||
union
|
||||
{
|
||||
UINT64 NextOffset;
|
||||
UINT8 Padding[24];
|
||||
/* make struct as big as FILE_ID_BOTH_DIR_INFORMATION; allows for in-place copying */
|
||||
} DUMMYUNIONNAME;
|
||||
WCHAR FileNameBuf[];
|
||||
} FSP_FSCTL_DIR_INFO;
|
||||
FSP_FSCTL_STATIC_ASSERT(104 == sizeof(FSP_FSCTL_DIR_INFO),
|
||||
|
@ -24,6 +24,7 @@
|
||||
static NTSTATUS FspFsvolQueryDirectoryCopy(
|
||||
PUNICODE_STRING DirectoryPattern, BOOLEAN CaseInsensitive,
|
||||
PUNICODE_STRING DirectoryMarker, PUNICODE_STRING DirectoryMarkerOut,
|
||||
PUINT64 DirectoryMarkerAsNextOffset,
|
||||
FILE_INFORMATION_CLASS FileInformationClass, BOOLEAN ReturnSingleEntry,
|
||||
BOOLEAN ReturnEaSize,
|
||||
FSP_FSCTL_DIR_INFO **PDirInfo, ULONG DirInfoSize,
|
||||
@ -88,6 +89,7 @@ enum
|
||||
static NTSTATUS FspFsvolQueryDirectoryCopy(
|
||||
PUNICODE_STRING DirectoryPattern, BOOLEAN CaseInsensitive,
|
||||
PUNICODE_STRING DirectoryMarker, PUNICODE_STRING DirectoryMarkerOut,
|
||||
PUINT64 DirectoryMarkerAsNextOffset,
|
||||
FILE_INFORMATION_CLASS FileInformationClass, BOOLEAN ReturnSingleEntry,
|
||||
BOOLEAN ReturnEaSize,
|
||||
FSP_FSCTL_DIR_INFO **PDirInfo, ULONG DirInfoSize,
|
||||
@ -130,6 +132,7 @@ static NTSTATUS FspFsvolQueryDirectoryCopy(
|
||||
PVOID PrevDestBuf = 0;
|
||||
ULONG BaseInfoLen, CopyLength;
|
||||
UNICODE_STRING FileName;
|
||||
UINT64 DirectoryNextOffset;
|
||||
|
||||
*PDestLen = 0;
|
||||
|
||||
@ -176,12 +179,21 @@ static NTSTATUS FspFsvolQueryDirectoryCopy(
|
||||
FileName.MaximumLength = (USHORT)(DirInfoSize - sizeof(FSP_FSCTL_DIR_INFO));
|
||||
FileName.Buffer = DirInfo->FileNameBuf;
|
||||
|
||||
DirectoryNextOffset = DirInfo->NextOffset;
|
||||
|
||||
if (0 != DirectoryMarker && 0 != DirectoryMarker->Buffer &&
|
||||
!DirectoryMarkerFound)
|
||||
{
|
||||
DirectoryMarkerFound = 0 == FspFileNameCompare(
|
||||
&FileName, DirectoryMarker, CaseInsensitive, 0);
|
||||
continue;
|
||||
if (0 == DirectoryMarkerAsNextOffset)
|
||||
{
|
||||
DirectoryMarkerFound = 0 == FspFileNameCompare(
|
||||
&FileName, DirectoryMarker, CaseInsensitive, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
ASSERT(sizeof(UINT64) == DirectoryMarker->Length);
|
||||
DirectoryMarkerFound = DirectoryNextOffset == *(PUINT64)DirectoryMarker->Buffer;
|
||||
}
|
||||
}
|
||||
|
||||
/* CopyLength is the same as FileName.Length except on STATUS_BUFFER_OVERFLOW */
|
||||
@ -272,8 +284,16 @@ static NTSTATUS FspFsvolQueryDirectoryCopy(
|
||||
break;
|
||||
}
|
||||
|
||||
DirectoryMarkerOut->Length = DirectoryMarkerOut->MaximumLength = FileName.Length;
|
||||
DirectoryMarkerOut->Buffer = (PVOID)((PUINT8)DestBuf + BaseInfoLen);
|
||||
if (0 == DirectoryMarkerAsNextOffset)
|
||||
{
|
||||
DirectoryMarkerOut->Length = DirectoryMarkerOut->MaximumLength = FileName.Length;
|
||||
DirectoryMarkerOut->Buffer = (PVOID)((PUINT8)DestBuf + BaseInfoLen);
|
||||
}
|
||||
else
|
||||
{
|
||||
DirectoryMarkerOut->Length = DirectoryMarkerOut->MaximumLength = sizeof(UINT64);
|
||||
DirectoryMarkerOut->Buffer = (PVOID)DirectoryMarkerAsNextOffset;
|
||||
}
|
||||
|
||||
DestBuf = (PVOID)((PUINT8)DestBuf +
|
||||
FSP_FSCTL_ALIGN_UP(BaseInfoLen + CopyLength, sizeof(LONGLONG)));
|
||||
@ -283,7 +303,15 @@ static NTSTATUS FspFsvolQueryDirectoryCopy(
|
||||
Loop = FALSE;
|
||||
}
|
||||
else
|
||||
*DirectoryMarkerOut = FileName;
|
||||
{
|
||||
if (0 == DirectoryMarkerAsNextOffset)
|
||||
*DirectoryMarkerOut = FileName;
|
||||
else
|
||||
{
|
||||
DirectoryMarkerOut->Length = DirectoryMarkerOut->MaximumLength = sizeof(UINT64);
|
||||
DirectoryMarkerOut->Buffer = (PVOID)DirectoryMarkerAsNextOffset;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
except (EXCEPTION_EXECUTE_HANDLER)
|
||||
@ -323,9 +351,12 @@ static NTSTATUS FspFsvolQueryDirectoryCopyCache(
|
||||
FileDesc->DirInfo = FileNode->NonPaged->DirInfo;
|
||||
|
||||
NTSTATUS Result;
|
||||
FSP_FSVOL_DEVICE_EXTENSION *FsvolDeviceExtension =
|
||||
FspFsvolDeviceExtension(FileNode->FsvolDeviceObject);
|
||||
BOOLEAN CaseInsensitive = !FileDesc->CaseSensitive;
|
||||
PUNICODE_STRING DirectoryPattern = &FileDesc->DirectoryPattern;
|
||||
UNICODE_STRING DirectoryMarker = FileDesc->DirectoryMarker;
|
||||
UINT64 DirectoryMarkerAsNextOffset = 0;
|
||||
PUINT8 DirInfoBgn = (PUINT8)DirInfo;
|
||||
PUINT8 DirInfoEnd = (PUINT8)DirInfo + DirInfoSize;
|
||||
|
||||
@ -334,8 +365,10 @@ static NTSTATUS FspFsvolQueryDirectoryCopyCache(
|
||||
|
||||
Result = FspFsvolQueryDirectoryCopy(DirectoryPattern, CaseInsensitive,
|
||||
0 != FileDesc->DirInfoCacheHint ? 0 : &FileDesc->DirectoryMarker, &DirectoryMarker,
|
||||
FsvolDeviceExtension->VolumeParams.DirectoryMarkerAsNextOffset ?
|
||||
&DirectoryMarkerAsNextOffset : 0,
|
||||
FileInformationClass, ReturnSingleEntry,
|
||||
!!FspFsvolDeviceExtension(FileNode->FsvolDeviceObject)->VolumeParams.ExtendedAttributes,
|
||||
!!FsvolDeviceExtension->VolumeParams.ExtendedAttributes,
|
||||
&DirInfo, DirInfoSize,
|
||||
DestBuf, PDestLen);
|
||||
|
||||
@ -366,10 +399,13 @@ static NTSTATUS FspFsvolQueryDirectoryCopyInPlace(
|
||||
PAGED_CODE();
|
||||
|
||||
NTSTATUS Result;
|
||||
FSP_FILE_NODE *FileNode = FileDesc->FileNode;
|
||||
FSP_FSVOL_DEVICE_EXTENSION *FsvolDeviceExtension =
|
||||
FspFsvolDeviceExtension(FileNode->FsvolDeviceObject);
|
||||
BOOLEAN CaseInsensitive = !FileDesc->CaseSensitive;
|
||||
PUNICODE_STRING DirectoryPattern = &FileDesc->DirectoryPattern;
|
||||
UNICODE_STRING DirectoryMarker = FileDesc->DirectoryMarker;
|
||||
FSP_FILE_NODE *FileNode = FileDesc->FileNode;
|
||||
UINT64 DirectoryMarkerAsNextOffset = 0;
|
||||
|
||||
FSP_FSCTL_STATIC_ASSERT(
|
||||
FIELD_OFFSET(FSP_FSCTL_DIR_INFO, FileNameBuf) >=
|
||||
@ -378,8 +414,10 @@ static NTSTATUS FspFsvolQueryDirectoryCopyInPlace(
|
||||
|
||||
Result = FspFsvolQueryDirectoryCopy(DirectoryPattern, CaseInsensitive,
|
||||
0, &DirectoryMarker,
|
||||
FsvolDeviceExtension->VolumeParams.DirectoryMarkerAsNextOffset ?
|
||||
&DirectoryMarkerAsNextOffset : 0,
|
||||
FileInformationClass, ReturnSingleEntry,
|
||||
!!FspFsvolDeviceExtension(FileNode->FsvolDeviceObject)->VolumeParams.ExtendedAttributes,
|
||||
!!FsvolDeviceExtension->VolumeParams.ExtendedAttributes,
|
||||
&DirInfo, DirInfoSize,
|
||||
DestBuf, PDestLen);
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user