mirror of
https://github.com/reactos/reactos.git
synced 2025-08-07 05:52:57 +00:00
[CMAKE]
- Sync with trunk head (r50270) - This also reverts r49298. svn path=/branches/cmake-bringup/; revision=50271
This commit is contained in:
commit
6c0c23cb53
482 changed files with 40346 additions and 24711 deletions
|
@ -152,7 +152,7 @@ VfatSetBasicInformation(PFILE_OBJECT FileObject,
|
|||
ASSERT(NULL != DeviceExt);
|
||||
ASSERT(NULL != BasicInfo);
|
||||
/* Check volume label bit */
|
||||
ASSERT(0 == (*FCB->Attributes & 0x08));
|
||||
ASSERT(0 == (*FCB->Attributes & _A_VOLID));
|
||||
|
||||
if (FCB->Flags & FCB_IS_FATX_ENTRY)
|
||||
{
|
||||
|
|
|
@ -123,7 +123,6 @@ VfatReadFileData (PVFAT_IRP_CONTEXT IrpContext,
|
|||
PDEVICE_EXTENSION DeviceExt;
|
||||
BOOLEAN First = TRUE;
|
||||
PVFATFCB Fcb;
|
||||
PVFATCCB Ccb;
|
||||
NTSTATUS Status;
|
||||
ULONG BytesDone;
|
||||
ULONG BytesPerSector;
|
||||
|
@ -145,7 +144,6 @@ VfatReadFileData (PVFAT_IRP_CONTEXT IrpContext,
|
|||
|
||||
*LengthRead = 0;
|
||||
|
||||
Ccb = (PVFATCCB)IrpContext->FileObject->FsContext2;
|
||||
Fcb = IrpContext->FileObject->FsContext;
|
||||
BytesPerSector = DeviceExt->FatInfo.BytesPerSector;
|
||||
BytesPerCluster = DeviceExt->FatInfo.BytesPerCluster;
|
||||
|
@ -328,7 +326,6 @@ VfatWriteFileData(PVFAT_IRP_CONTEXT IrpContext,
|
|||
{
|
||||
PDEVICE_EXTENSION DeviceExt;
|
||||
PVFATFCB Fcb;
|
||||
PVFATCCB Ccb;
|
||||
ULONG Count;
|
||||
ULONG FirstCluster;
|
||||
ULONG CurrentCluster;
|
||||
|
@ -352,7 +349,6 @@ VfatWriteFileData(PVFAT_IRP_CONTEXT IrpContext,
|
|||
ASSERT(IrpContext->FileObject);
|
||||
ASSERT(IrpContext->FileObject->FsContext2 != NULL);
|
||||
|
||||
Ccb = (PVFATCCB)IrpContext->FileObject->FsContext2;
|
||||
Fcb = IrpContext->FileObject->FsContext;
|
||||
BytesPerCluster = DeviceExt->FatInfo.BytesPerCluster;
|
||||
BytesPerSector = DeviceExt->FatInfo.BytesPerSector;
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
#include <bugcodes.h>
|
||||
#include <ntdddisk.h>
|
||||
#include <debug.h>
|
||||
#include <dos.h>
|
||||
|
||||
#define USE_ROS_CC_AND_FS
|
||||
|
||||
|
|
|
@ -216,13 +216,21 @@ FsdSetFsLabelInformation(PDEVICE_OBJECT DeviceObject,
|
|||
{
|
||||
RtlCopyMemory(VolumeLabelDirEntry.FatX.Filename, cString, LabelLen);
|
||||
memset(&VolumeLabelDirEntry.FatX.Filename[LabelLen], ' ', 42 - LabelLen);
|
||||
VolumeLabelDirEntry.FatX.Attrib = 0x08;
|
||||
VolumeLabelDirEntry.FatX.Attrib = _A_VOLID;
|
||||
}
|
||||
else
|
||||
{
|
||||
RtlCopyMemory(VolumeLabelDirEntry.Fat.Filename, cString, LabelLen);
|
||||
memset(&VolumeLabelDirEntry.Fat.Filename[LabelLen], ' ', 11 - LabelLen);
|
||||
VolumeLabelDirEntry.Fat.Attrib = 0x08;
|
||||
RtlCopyMemory(VolumeLabelDirEntry.Fat.Filename, cString, max(sizeof(VolumeLabelDirEntry.Fat.Filename), LabelLen));
|
||||
if (LabelLen > sizeof(VolumeLabelDirEntry.Fat.Filename))
|
||||
{
|
||||
memset(VolumeLabelDirEntry.Fat.Ext, ' ', sizeof(VolumeLabelDirEntry.Fat.Ext));
|
||||
RtlCopyMemory(VolumeLabelDirEntry.Fat.Ext, cString + sizeof(VolumeLabelDirEntry.Fat.Filename), LabelLen - sizeof(VolumeLabelDirEntry.Fat.Filename));
|
||||
}
|
||||
else
|
||||
{
|
||||
memset(&VolumeLabelDirEntry.Fat.Filename[LabelLen], ' ', sizeof(VolumeLabelDirEntry.Fat.Filename) - LabelLen);
|
||||
}
|
||||
VolumeLabelDirEntry.Fat.Attrib = _A_VOLID;
|
||||
}
|
||||
|
||||
pRootFcb = vfatOpenRootFCB(DeviceExt);
|
||||
|
|
|
@ -221,7 +221,8 @@ FatiCleanup(PFAT_IRP_CONTEXT IrpContext, PIRP Irp)
|
|||
Fcb->Condition == FcbGood)
|
||||
{
|
||||
/* Yes, a delayed one */
|
||||
SetFlag(Fcb->State, FCB_STATE_DELAY_CLOSE);
|
||||
//SetFlag(Fcb->State, FCB_STATE_DELAY_CLOSE);
|
||||
DPRINT1("Setting a delay on close for some reason for FCB %p, FF handle %p, file name '%wZ'\n", Fcb, Fcb->FatHandle, &Fcb->FullFileName);
|
||||
}
|
||||
|
||||
/* Unlock all file locks */
|
||||
|
|
|
@ -493,7 +493,7 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
|||
BOOLEAN OpenDirectory;
|
||||
BOOLEAN IsPagingFile;
|
||||
BOOLEAN OpenTargetDirectory;
|
||||
BOOLEAN DirectoryFile;
|
||||
BOOLEAN IsDirectoryFile;
|
||||
BOOLEAN NonDirectoryFile;
|
||||
BOOLEAN NoEaKnowledge;
|
||||
BOOLEAN DeleteOnClose;
|
||||
|
@ -522,7 +522,7 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
|||
NTSTATUS Status;
|
||||
IO_STATUS_BLOCK Iosb;
|
||||
PIO_STACK_LOCATION IrpSp;
|
||||
BOOLEAN EndBackslash = FALSE, OpenedAsDos;
|
||||
BOOLEAN EndBackslash = FALSE, OpenedAsDos, FirstRun = TRUE;
|
||||
UNICODE_STRING RemainingPart, FirstName, NextName, FileNameUpcased;
|
||||
OEM_STRING AnsiFirstName;
|
||||
FF_ERROR FfError;
|
||||
|
@ -592,6 +592,13 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
|||
if (RelatedFO)
|
||||
FileObject->Vpb = RelatedFO->Vpb;
|
||||
|
||||
/* Reject open by id */
|
||||
if (Options & FILE_OPEN_BY_FILE_ID)
|
||||
{
|
||||
FatCompleteRequest(IrpContext, Irp, STATUS_INVALID_PARAMETER);
|
||||
return STATUS_INVALID_PARAMETER;
|
||||
}
|
||||
|
||||
/* Prepare file attributes mask */
|
||||
FileAttributes &= (FILE_ATTRIBUTE_READONLY |
|
||||
FILE_ATTRIBUTE_HIDDEN |
|
||||
|
@ -602,7 +609,7 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
|||
Vcb = &((PVOLUME_DEVICE_OBJECT)IrpSp->DeviceObject)->Vcb;
|
||||
|
||||
/* Get options */
|
||||
DirectoryFile = BooleanFlagOn(Options, FILE_DIRECTORY_FILE);
|
||||
IsDirectoryFile = BooleanFlagOn(Options, FILE_DIRECTORY_FILE);
|
||||
NonDirectoryFile = BooleanFlagOn(Options, FILE_NON_DIRECTORY_FILE);
|
||||
SequentialOnly = BooleanFlagOn(Options, FILE_SEQUENTIAL_ONLY);
|
||||
NoIntermediateBuffering = BooleanFlagOn(Options, FILE_NO_INTERMEDIATE_BUFFERING);
|
||||
|
@ -617,17 +624,17 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
|||
CreateDisposition = (Options >> 24) & 0x000000ff;
|
||||
|
||||
/* Get Create/Open directory flags based on it */
|
||||
CreateDirectory = (BOOLEAN)(DirectoryFile &&
|
||||
CreateDirectory = (BOOLEAN)(IsDirectoryFile &&
|
||||
((CreateDisposition == FILE_CREATE) ||
|
||||
(CreateDisposition == FILE_OPEN_IF)));
|
||||
|
||||
OpenDirectory = (BOOLEAN)(DirectoryFile &&
|
||||
OpenDirectory = (BOOLEAN)(IsDirectoryFile &&
|
||||
((CreateDisposition == FILE_OPEN) ||
|
||||
(CreateDisposition == FILE_OPEN_IF)));
|
||||
|
||||
/* Validate parameters: directory/nondirectory mismatch and
|
||||
AllocationSize being more than 4GB */
|
||||
if ((DirectoryFile && NonDirectoryFile) ||
|
||||
if ((IsDirectoryFile && NonDirectoryFile) ||
|
||||
Irp->Overlay.AllocationSize.HighPart != 0)
|
||||
{
|
||||
FatCompleteRequest(IrpContext, Irp, STATUS_INVALID_PARAMETER);
|
||||
|
@ -652,12 +659,22 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
|||
DPRINT1("This volume is locked\n");
|
||||
Status = STATUS_ACCESS_DENIED;
|
||||
|
||||
/* Set volume dismount status */
|
||||
if (Vcb->Condition != VcbGood)
|
||||
Status = STATUS_VOLUME_DISMOUNTED;
|
||||
|
||||
/* Cleanup and return */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
FatCompleteRequest(IrpContext, Irp, Status);
|
||||
return Status;
|
||||
}
|
||||
|
||||
// TODO: Check if the volume is write protected and disallow DELETE_ON_CLOSE
|
||||
/* Check if the volume is write protected and disallow DELETE_ON_CLOSE */
|
||||
if (DeleteOnClose & FlagOn(Vcb->State, VCB_STATE_FLAG_WRITE_PROTECTED))
|
||||
{
|
||||
ASSERT(FALSE);
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
// TODO: Make sure EAs aren't supported on FAT32
|
||||
|
||||
|
@ -669,9 +686,9 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
|||
FatDecodeFileObject(RelatedFO, &DecodedVcb, &Fcb, &Ccb) == UserVolumeOpen)
|
||||
{
|
||||
/* Check parameters */
|
||||
if (DirectoryFile || OpenTargetDirectory)
|
||||
if (IsDirectoryFile || OpenTargetDirectory)
|
||||
{
|
||||
Status = DirectoryFile ? STATUS_NOT_A_DIRECTORY : STATUS_INVALID_PARAMETER;
|
||||
Status = IsDirectoryFile ? STATUS_NOT_A_DIRECTORY : STATUS_INVALID_PARAMETER;
|
||||
|
||||
/* Unlock VCB */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
|
@ -716,18 +733,24 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
|||
{
|
||||
DPRINT1("Invalid file object!\n");
|
||||
|
||||
Status = STATUS_OBJECT_PATH_NOT_FOUND;
|
||||
|
||||
/* Cleanup and return */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
return STATUS_OBJECT_PATH_NOT_FOUND;
|
||||
FatCompleteRequest(IrpContext, Irp, Status);
|
||||
return Status;
|
||||
}
|
||||
|
||||
/* File path must be relative */
|
||||
if (FileName.Length != 0 &&
|
||||
FileName.Buffer[0] == L'\\')
|
||||
{
|
||||
Status = STATUS_OBJECT_NAME_INVALID;
|
||||
|
||||
/* The name is absolute, fail */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
return STATUS_OBJECT_NAME_INVALID;
|
||||
FatCompleteRequest(IrpContext, Irp, Status);
|
||||
return Status;
|
||||
}
|
||||
|
||||
/* Make sure volume is the same */
|
||||
|
@ -751,18 +774,34 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
|||
if (NonDirectoryFile)
|
||||
{
|
||||
DPRINT1("Trying to open root dir as a file\n");
|
||||
Status = STATUS_FILE_IS_A_DIRECTORY;
|
||||
|
||||
/* Cleanup and return */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
return STATUS_FILE_IS_A_DIRECTORY;
|
||||
FatCompleteRequest(IrpContext, Irp, Status);
|
||||
return Status;
|
||||
}
|
||||
|
||||
/* Check for target directory on a root dir */
|
||||
if (OpenTargetDirectory)
|
||||
{
|
||||
Status = STATUS_INVALID_PARAMETER;
|
||||
|
||||
/* Cleanup and return */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
FatCompleteRequest(IrpContext, Irp, Status);
|
||||
return Status;
|
||||
}
|
||||
|
||||
/* Check delete on close on a root dir */
|
||||
if (DeleteOnClose)
|
||||
{
|
||||
Status = STATUS_CANNOT_DELETE;
|
||||
|
||||
/* Cleanup and return */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
return STATUS_CANNOT_DELETE;
|
||||
FatCompleteRequest(IrpContext, Irp, Status);
|
||||
return Status;
|
||||
}
|
||||
|
||||
/* Call root directory open routine */
|
||||
|
@ -777,6 +816,7 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
|||
|
||||
/* Cleanup and return */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
FatCompleteRequest(IrpContext, Irp, Iosb.Status);
|
||||
return Iosb.Status;
|
||||
}
|
||||
else
|
||||
|
@ -910,6 +950,27 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
|||
}
|
||||
}
|
||||
|
||||
/* Treat page file in a special way */
|
||||
if (IsPagingFile)
|
||||
{
|
||||
UNIMPLEMENTED;
|
||||
// FIXME: System file too
|
||||
}
|
||||
|
||||
/* Make sure there is no pending delete on a higher-level FCB */
|
||||
if (Fcb->State & FCB_STATE_DELETE_ON_CLOSE)
|
||||
{
|
||||
Iosb.Status = STATUS_DELETE_PENDING;
|
||||
|
||||
/* Cleanup and return */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
|
||||
/* Complete the request */
|
||||
FatCompleteRequest(IrpContext, Irp, Iosb.Status);
|
||||
|
||||
return Iosb.Status;
|
||||
}
|
||||
|
||||
/* We have a valid FCB now */
|
||||
if (!RemainingPart.Length)
|
||||
{
|
||||
|
@ -1038,23 +1099,37 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
|||
ParentDcb = Fcb;
|
||||
while (TRUE)
|
||||
{
|
||||
FsRtlDissectName(RemainingPart, &FirstName, &RemainingPart);
|
||||
|
||||
/* Check for validity */
|
||||
if ((RemainingPart.Length && RemainingPart.Buffer[0] == L'\\') ||
|
||||
(NextName.Length > 255 * sizeof(WCHAR)))
|
||||
if (FirstRun)
|
||||
{
|
||||
/* The name is invalid */
|
||||
DPRINT1("Invalid name found\n");
|
||||
Iosb.Status = STATUS_OBJECT_NAME_INVALID;
|
||||
ASSERT(FALSE);
|
||||
}
|
||||
RemainingPart = NextName;
|
||||
if (AnsiFirstName.Length)
|
||||
Status = STATUS_SUCCESS;
|
||||
else
|
||||
Status = STATUS_UNMAPPABLE_CHARACTER;
|
||||
|
||||
/* Convert the name to ANSI */
|
||||
AnsiFirstName.Buffer = ExAllocatePool(PagedPool, FirstName.Length);
|
||||
AnsiFirstName.Length = 0;
|
||||
AnsiFirstName.MaximumLength = FirstName.Length;
|
||||
Status = RtlUpcaseUnicodeStringToCountedOemString(&AnsiFirstName, &FirstName, FALSE);
|
||||
/* First run init is done */
|
||||
FirstRun = FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
FsRtlDissectName(RemainingPart, &FirstName, &RemainingPart);
|
||||
|
||||
/* Check for validity */
|
||||
if ((RemainingPart.Length && RemainingPart.Buffer[0] == L'\\') ||
|
||||
(NextName.Length > 255 * sizeof(WCHAR)))
|
||||
{
|
||||
/* The name is invalid */
|
||||
DPRINT1("Invalid name found\n");
|
||||
Iosb.Status = STATUS_OBJECT_NAME_INVALID;
|
||||
ASSERT(FALSE);
|
||||
}
|
||||
|
||||
/* Convert the name to ANSI */
|
||||
AnsiFirstName.Buffer = ExAllocatePool(PagedPool, FirstName.Length);
|
||||
AnsiFirstName.Length = 0;
|
||||
AnsiFirstName.MaximumLength = FirstName.Length;
|
||||
Status = RtlUpcaseUnicodeStringToCountedOemString(&AnsiFirstName, &FirstName, FALSE);
|
||||
}
|
||||
|
||||
if (!NT_SUCCESS(Status))
|
||||
{
|
||||
|
@ -1086,91 +1161,127 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
|||
UNIMPLEMENTED;
|
||||
}
|
||||
|
||||
/* Check, if path is a directory or a file */
|
||||
if (FfError == FF_ERR_FILE_OBJECT_IS_A_DIR)
|
||||
/* Check, if path is a existing directory or file */
|
||||
if (FfError == FF_ERR_FILE_OBJECT_IS_A_DIR ||
|
||||
FfError == FF_ERR_FILE_ALREADY_OPEN ||
|
||||
FfError == FF_ERR_NONE)
|
||||
{
|
||||
if (NonDirectoryFile)
|
||||
if (FfError == FF_ERR_FILE_OBJECT_IS_A_DIR)
|
||||
{
|
||||
DPRINT1("Can't open dir as a file\n");
|
||||
if (NonDirectoryFile)
|
||||
{
|
||||
DPRINT1("Can't open dir as a file\n");
|
||||
|
||||
/* Unlock VCB */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
|
||||
/* Complete the request */
|
||||
Iosb.Status = STATUS_FILE_IS_A_DIRECTORY;
|
||||
FatCompleteRequest(IrpContext, Irp, Iosb.Status);
|
||||
return Iosb.Status;
|
||||
}
|
||||
|
||||
/* Open this directory */
|
||||
Iosb = FatiOpenExistingDir(IrpContext,
|
||||
FileObject,
|
||||
Vcb,
|
||||
ParentDcb,
|
||||
DesiredAccess,
|
||||
ShareAccess,
|
||||
AllocationSize,
|
||||
EaBuffer,
|
||||
EaLength,
|
||||
FileAttributes,
|
||||
CreateDisposition,
|
||||
DeleteOnClose);
|
||||
|
||||
Irp->IoStatus.Information = Iosb.Information;
|
||||
|
||||
/* Unlock VCB */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
|
||||
/* Complete the request */
|
||||
Iosb.Status = STATUS_FILE_IS_A_DIRECTORY;
|
||||
FatCompleteRequest(IrpContext, Irp, Iosb.Status);
|
||||
|
||||
return Iosb.Status;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* This is opening an existing file */
|
||||
if (OpenDirectory)
|
||||
{
|
||||
/* But caller wanted a dir */
|
||||
Status = STATUS_NOT_A_DIRECTORY;
|
||||
|
||||
/* Open this directory */
|
||||
Iosb = FatiOpenExistingDir(IrpContext,
|
||||
FileObject,
|
||||
Vcb,
|
||||
ParentDcb,
|
||||
DesiredAccess,
|
||||
ShareAccess,
|
||||
AllocationSize,
|
||||
EaBuffer,
|
||||
EaLength,
|
||||
FileAttributes,
|
||||
CreateDisposition,
|
||||
DeleteOnClose);
|
||||
/* Unlock VCB */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
|
||||
Irp->IoStatus.Information = Iosb.Information;
|
||||
/* Complete the request */
|
||||
FatCompleteRequest(IrpContext, Irp, Status);
|
||||
|
||||
/* Unlock VCB */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
return Status;
|
||||
}
|
||||
|
||||
/* Complete the request */
|
||||
FatCompleteRequest(IrpContext, Irp, Iosb.Status);
|
||||
/* If end backslash here, then it's definately not permitted,
|
||||
since we're opening files here */
|
||||
if (EndBackslash)
|
||||
{
|
||||
/* Unlock VCB */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
|
||||
return Iosb.Status;
|
||||
/* Complete the request */
|
||||
Iosb.Status = STATUS_OBJECT_NAME_INVALID;
|
||||
FatCompleteRequest(IrpContext, Irp, Iosb.Status);
|
||||
return Iosb.Status;
|
||||
}
|
||||
|
||||
/* Try to open the file */
|
||||
Iosb = FatiOpenExistingFile(IrpContext,
|
||||
FileObject,
|
||||
Vcb,
|
||||
ParentDcb,
|
||||
DesiredAccess,
|
||||
ShareAccess,
|
||||
AllocationSize,
|
||||
EaBuffer,
|
||||
EaLength,
|
||||
FileAttributes,
|
||||
CreateDisposition,
|
||||
FALSE,
|
||||
DeleteOnClose,
|
||||
OpenedAsDos);
|
||||
|
||||
/* In case of success set cache supported flag */
|
||||
if (NT_SUCCESS(Iosb.Status) && !NoIntermediateBuffering)
|
||||
{
|
||||
SetFlag(FileObject->Flags, FO_CACHE_SUPPORTED);
|
||||
}
|
||||
|
||||
Irp->IoStatus.Information = Iosb.Information;
|
||||
|
||||
/* Unlock VCB */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
|
||||
/* Complete the request */
|
||||
FatCompleteRequest(IrpContext, Irp, Iosb.Status);
|
||||
|
||||
return Iosb.Status;
|
||||
}
|
||||
}
|
||||
|
||||
/* If end backslash here, then it's definately not permitted,
|
||||
since we're opening files here */
|
||||
if (EndBackslash)
|
||||
{
|
||||
/* Unlock VCB */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
/* We come here only in the case when a new file is created */
|
||||
//ASSERT(FALSE);
|
||||
DPRINT1("TODO: Create a new file/directory, called '%wZ'\n", &IrpSp->FileObject->FileName);
|
||||
|
||||
/* Complete the request */
|
||||
Iosb.Status = STATUS_OBJECT_NAME_INVALID;
|
||||
FatCompleteRequest(IrpContext, Irp, Iosb.Status);
|
||||
return Iosb.Status;
|
||||
}
|
||||
|
||||
/* Try to open the file */
|
||||
Iosb = FatiOpenExistingFile(IrpContext,
|
||||
FileObject,
|
||||
Vcb,
|
||||
ParentDcb,
|
||||
DesiredAccess,
|
||||
ShareAccess,
|
||||
AllocationSize,
|
||||
EaBuffer,
|
||||
EaLength,
|
||||
FileAttributes,
|
||||
CreateDisposition,
|
||||
FALSE,
|
||||
DeleteOnClose,
|
||||
OpenedAsDos);
|
||||
|
||||
/* In case of success set cache supported flag */
|
||||
if (NT_SUCCESS(Iosb.Status) && !NoIntermediateBuffering)
|
||||
{
|
||||
SetFlag(FileObject->Flags, FO_CACHE_SUPPORTED);
|
||||
}
|
||||
|
||||
Irp->IoStatus.Information = Iosb.Information;
|
||||
Status = STATUS_NOT_IMPLEMENTED;
|
||||
|
||||
/* Unlock VCB */
|
||||
FatReleaseVcb(IrpContext, Vcb);
|
||||
|
||||
/* Complete the request */
|
||||
FatCompleteRequest(IrpContext, Irp, Iosb.Status);
|
||||
FatCompleteRequest(IrpContext, Irp, Status);
|
||||
|
||||
return Iosb.Status;
|
||||
return Status;
|
||||
}
|
||||
|
||||
NTSTATUS
|
||||
|
|
|
@ -80,7 +80,7 @@ typedef struct _FAT_PAGE_CONTEXT
|
|||
CcUnpinData((xContext)->Bcb); \
|
||||
(xContext)->Bcb = NULL; \
|
||||
} \
|
||||
|
||||
|
||||
#define FatPinEndOfPage(xContext, xType) \
|
||||
Add2Ptr((xContext)->Buffer, (xContext)->ValidLength, xType)
|
||||
|
||||
|
|
|
@ -36,7 +36,7 @@ FatiRead(PFAT_IRP_CONTEXT IrpContext)
|
|||
FatCompleteRequest(IrpContext, IrpContext->Irp, STATUS_SUCCESS);
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
OpenType = FatDecodeFileObject(FileObject, &Vcb, &Fcb, &Ccb);
|
||||
|
||||
DPRINT("FatiRead() Fcb %p, Name %wZ, Offset %d, Length %d, Handle %p\n",
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
|
||||
list(APPEND SOURCE
|
||||
create.c
|
||||
dirctl.c
|
||||
finfo.c
|
||||
fsctrl.c
|
||||
npfs.c
|
||||
|
@ -10,9 +11,9 @@ list(APPEND SOURCE
|
|||
|
||||
add_library(npfs SHARED ${CMAKE_CURRENT_BINARY_DIR}/npfs_npfs.h.gch ${SOURCE})
|
||||
|
||||
target_link_libraries(npfs ${PSEH_LIB})
|
||||
|
||||
set_module_type(npfs kernelmodedriver)
|
||||
add_importlibs(npfs ntoskrnl hal)
|
||||
|
||||
add_pch(npfs ${CMAKE_CURRENT_SOURCE_DIR}/npfs.h ${SOURCE})
|
||||
|
||||
add_cab_target(npfs 2)
|
||||
|
|
|
@ -121,6 +121,8 @@ NpfsOpenFileSystem(PNPFS_FCB Fcb,
|
|||
return;
|
||||
}
|
||||
|
||||
RtlZeroMemory(Ccb, sizeof(NPFS_CCB));
|
||||
|
||||
Ccb->Type = CCB_DEVICE;
|
||||
Ccb->Fcb = Fcb;
|
||||
|
||||
|
@ -150,6 +152,8 @@ NpfsOpenRootDirectory(PNPFS_FCB Fcb,
|
|||
return;
|
||||
}
|
||||
|
||||
RtlZeroMemory(Ccb, sizeof(NPFS_CCB));
|
||||
|
||||
Ccb->Type = CCB_DIRECTORY;
|
||||
Ccb->Fcb = Fcb;
|
||||
|
||||
|
@ -221,7 +225,8 @@ NpfsCreate(PDEVICE_OBJECT DeviceObject,
|
|||
}
|
||||
|
||||
/* Open the root directory */
|
||||
if (FileName->Length == 2 && FileName->Buffer[0] == L'\\' && RelatedFileObject == NULL)
|
||||
if ((FileName->Length == 2 && FileName->Buffer[0] == L'\\' && RelatedFileObject == NULL) ||
|
||||
(FileName->Length == 0 && ((PNPFS_CCB)RelatedFileObject->FsContext2)->Type == CCB_DIRECTORY))
|
||||
{
|
||||
DPRINT("Open the root directory\n");
|
||||
|
||||
|
@ -880,6 +885,9 @@ NpfsClose(PDEVICE_OBJECT DeviceObject,
|
|||
{
|
||||
DPRINT("Closing the root directory!\n");
|
||||
|
||||
if (Ccb->u.Directory.SearchPattern.Buffer != NULL)
|
||||
ExFreePool(Ccb->u.Directory.SearchPattern.Buffer);
|
||||
|
||||
ExFreePool(Ccb);
|
||||
FileObject->FsContext = NULL;
|
||||
FileObject->FsContext2 = NULL;
|
||||
|
|
284
drivers/filesystems/npfs/dirctl.c
Normal file
284
drivers/filesystems/npfs/dirctl.c
Normal file
|
@ -0,0 +1,284 @@
|
|||
/*
|
||||
* COPYRIGHT: See COPYING in the top level directory
|
||||
* PROJECT: ReactOS kernel
|
||||
* FILE: drivers/filesastems/npfs/dirctl.c
|
||||
* PURPOSE: Named pipe filesystem
|
||||
* PROGRAMMER: Eric Kohl
|
||||
*/
|
||||
|
||||
/* INCLUDES ******************************************************************/
|
||||
|
||||
#include "npfs.h"
|
||||
|
||||
#define NDEBUG
|
||||
#include <debug.h>
|
||||
|
||||
/* FUNCTIONS *****************************************************************/
|
||||
|
||||
static NTSTATUS
|
||||
NpfsQueryDirectory(PNPFS_CCB Ccb,
|
||||
PIRP Irp,
|
||||
PULONG Size)
|
||||
{
|
||||
PIO_STACK_LOCATION Stack;
|
||||
LONG BufferLength = 0;
|
||||
PUNICODE_STRING SearchPattern = NULL;
|
||||
FILE_INFORMATION_CLASS FileInformationClass;
|
||||
ULONG FileIndex = 0;
|
||||
PUCHAR Buffer = NULL;
|
||||
BOOLEAN First = FALSE;
|
||||
PLIST_ENTRY CurrentEntry;
|
||||
PNPFS_VCB Vcb;
|
||||
PNPFS_FCB PipeFcb;
|
||||
ULONG PipeIndex;
|
||||
BOOLEAN Found = FALSE;
|
||||
NTSTATUS Status = STATUS_SUCCESS;
|
||||
PFILE_NAMES_INFORMATION NamesBuffer;
|
||||
PFILE_DIRECTORY_INFORMATION DirectoryBuffer;
|
||||
PFILE_FULL_DIR_INFORMATION FullDirBuffer;
|
||||
PFILE_BOTH_DIR_INFORMATION BothDirBuffer;
|
||||
|
||||
Stack = IoGetCurrentIrpStackLocation(Irp);
|
||||
|
||||
/* Obtain the callers parameters */
|
||||
BufferLength = Stack->Parameters.QueryDirectory.Length;
|
||||
SearchPattern = Stack->Parameters.QueryDirectory.FileName;
|
||||
FileInformationClass = Stack->Parameters.QueryDirectory.FileInformationClass;
|
||||
FileIndex = Stack->Parameters.QueryDirectory.FileIndex;
|
||||
|
||||
DPRINT("SearchPattern: %p '%wZ'\n", SearchPattern, SearchPattern);
|
||||
|
||||
/* Determine Buffer for result */
|
||||
if (Irp->MdlAddress)
|
||||
{
|
||||
Buffer = MmGetSystemAddressForMdl(Irp->MdlAddress);
|
||||
}
|
||||
else
|
||||
{
|
||||
Buffer = Irp->UserBuffer;
|
||||
}
|
||||
|
||||
/* Build the search pattern string */
|
||||
DPRINT("Ccb->u.Directory.SearchPattern.Buffer: %p\n", Ccb->u.Directory.SearchPattern.Buffer);
|
||||
if (Ccb->u.Directory.SearchPattern.Buffer == NULL)
|
||||
{
|
||||
First = TRUE;
|
||||
|
||||
if (SearchPattern != NULL)
|
||||
{
|
||||
Ccb->u.Directory.SearchPattern.Buffer =
|
||||
ExAllocatePool(NonPagedPool, SearchPattern->Length + sizeof(WCHAR));
|
||||
if (Ccb->u.Directory.SearchPattern.Buffer == NULL)
|
||||
{
|
||||
return STATUS_INSUFFICIENT_RESOURCES;
|
||||
}
|
||||
|
||||
Ccb->u.Directory.SearchPattern.Length = SearchPattern->Length;
|
||||
Ccb->u.Directory.SearchPattern.MaximumLength = SearchPattern->Length + sizeof(WCHAR);
|
||||
RtlCopyMemory(Ccb->u.Directory.SearchPattern.Buffer,
|
||||
SearchPattern->Buffer,
|
||||
SearchPattern->Length);
|
||||
Ccb->u.Directory.SearchPattern.Buffer[SearchPattern->Length / sizeof(WCHAR)] = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
Ccb->u.Directory.SearchPattern.Buffer =
|
||||
ExAllocatePool(NonPagedPool, 2 * sizeof(WCHAR));
|
||||
if (Ccb->u.Directory.SearchPattern.Buffer == NULL)
|
||||
{
|
||||
return STATUS_INSUFFICIENT_RESOURCES;
|
||||
}
|
||||
|
||||
Ccb->u.Directory.SearchPattern.Length = sizeof(WCHAR);
|
||||
Ccb->u.Directory.SearchPattern.MaximumLength = 2 * sizeof(WCHAR);
|
||||
Ccb->u.Directory.SearchPattern.Buffer[0] = L'*';
|
||||
Ccb->u.Directory.SearchPattern.Buffer[1] = 0;
|
||||
}
|
||||
}
|
||||
DPRINT("Search pattern: '%wZ'\n", &Ccb->u.Directory.SearchPattern);
|
||||
|
||||
/* Determine the file index */
|
||||
if (First || (Stack->Flags & SL_RESTART_SCAN))
|
||||
{
|
||||
FileIndex = 0;
|
||||
} else if ((Stack->Flags & SL_INDEX_SPECIFIED) == 0)
|
||||
{
|
||||
FileIndex = Ccb->u.Directory.FileIndex + 1;
|
||||
}
|
||||
DPRINT("FileIndex: %lu\n", FileIndex);
|
||||
|
||||
DPRINT("Buffer = %p tofind = %wZ\n", Buffer, &Ccb->u.Directory.SearchPattern);
|
||||
|
||||
PipeIndex = 0;
|
||||
|
||||
Vcb = Ccb->Fcb->Vcb;
|
||||
CurrentEntry = Vcb->PipeListHead.Flink;
|
||||
while (CurrentEntry != &Vcb->PipeListHead && Found == FALSE)
|
||||
{
|
||||
/* Get the FCB of the next pipe */
|
||||
PipeFcb = CONTAINING_RECORD(CurrentEntry,
|
||||
NPFS_FCB,
|
||||
PipeListEntry);
|
||||
|
||||
/* Make sure it is a pipe FCB */
|
||||
ASSERT(PipeFcb->Type == FCB_PIPE);
|
||||
|
||||
DPRINT("PipeName: %wZ\n", &PipeFcb->PipeName);
|
||||
|
||||
if (FsRtlIsNameInExpression(&Ccb->u.Directory.SearchPattern,
|
||||
&PipeFcb->PipeName,
|
||||
TRUE,
|
||||
NULL))
|
||||
{
|
||||
DPRINT("Found pipe: %wZ\n", &PipeFcb->PipeName);
|
||||
|
||||
if (PipeIndex >= FileIndex)
|
||||
{
|
||||
RtlZeroMemory(Buffer, BufferLength);
|
||||
|
||||
switch (FileInformationClass)
|
||||
{
|
||||
case FileDirectoryInformation:
|
||||
DirectoryBuffer = (PFILE_DIRECTORY_INFORMATION)Buffer;
|
||||
DirectoryBuffer->NextEntryOffset = 0;
|
||||
DirectoryBuffer->FileIndex = PipeIndex;
|
||||
DirectoryBuffer->FileAttributes = FILE_ATTRIBUTE_NORMAL;
|
||||
DirectoryBuffer->EndOfFile.QuadPart = PipeFcb->CurrentInstances;
|
||||
DirectoryBuffer->AllocationSize.LowPart = PipeFcb->MaximumInstances;
|
||||
DirectoryBuffer->FileNameLength = PipeFcb->PipeName.Length;
|
||||
RtlCopyMemory(DirectoryBuffer->FileName,
|
||||
PipeFcb->PipeName.Buffer,
|
||||
PipeFcb->PipeName.Length);
|
||||
*Size = sizeof(FILE_DIRECTORY_INFORMATION) + PipeFcb->PipeName.Length - sizeof(WCHAR);
|
||||
Status = STATUS_SUCCESS;
|
||||
break;
|
||||
|
||||
case FileFullDirectoryInformation:
|
||||
FullDirBuffer = (PFILE_FULL_DIR_INFORMATION)Buffer;
|
||||
FullDirBuffer->NextEntryOffset = 0;
|
||||
FullDirBuffer->FileIndex = PipeIndex;
|
||||
FullDirBuffer->FileAttributes = FILE_ATTRIBUTE_NORMAL;
|
||||
FullDirBuffer->EndOfFile.QuadPart = PipeFcb->CurrentInstances;
|
||||
FullDirBuffer->AllocationSize.LowPart = PipeFcb->MaximumInstances;
|
||||
FullDirBuffer->FileNameLength = PipeFcb->PipeName.Length;
|
||||
RtlCopyMemory(FullDirBuffer->FileName,
|
||||
PipeFcb->PipeName.Buffer,
|
||||
PipeFcb->PipeName.Length);
|
||||
*Size = sizeof(FILE_FULL_DIR_INFORMATION) + PipeFcb->PipeName.Length - sizeof(WCHAR);
|
||||
Status = STATUS_SUCCESS;
|
||||
break;
|
||||
|
||||
case FileBothDirectoryInformation:
|
||||
BothDirBuffer = (PFILE_BOTH_DIR_INFORMATION)Buffer;
|
||||
BothDirBuffer->NextEntryOffset = 0;
|
||||
BothDirBuffer->FileIndex = PipeIndex;
|
||||
BothDirBuffer->FileAttributes = FILE_ATTRIBUTE_NORMAL;
|
||||
BothDirBuffer->EndOfFile.QuadPart = PipeFcb->CurrentInstances;
|
||||
BothDirBuffer->AllocationSize.LowPart = PipeFcb->MaximumInstances;
|
||||
BothDirBuffer->FileNameLength = PipeFcb->PipeName.Length;
|
||||
RtlCopyMemory(BothDirBuffer->FileName,
|
||||
PipeFcb->PipeName.Buffer,
|
||||
PipeFcb->PipeName.Length);
|
||||
*Size = sizeof(FILE_BOTH_DIR_INFORMATION) + PipeFcb->PipeName.Length - sizeof(WCHAR);
|
||||
Status = STATUS_SUCCESS;
|
||||
break;
|
||||
|
||||
case FileNamesInformation:
|
||||
NamesBuffer = (PFILE_NAMES_INFORMATION)Buffer;
|
||||
NamesBuffer->NextEntryOffset = 0;
|
||||
NamesBuffer->FileIndex = PipeIndex;
|
||||
NamesBuffer->FileNameLength = PipeFcb->PipeName.Length;
|
||||
RtlCopyMemory(NamesBuffer->FileName,
|
||||
PipeFcb->PipeName.Buffer,
|
||||
PipeFcb->PipeName.Length);
|
||||
*Size = sizeof(FILE_NAMES_INFORMATION) + PipeFcb->PipeName.Length - sizeof(WCHAR);
|
||||
Status = STATUS_SUCCESS;
|
||||
break;
|
||||
|
||||
default:
|
||||
DPRINT1("Invalid information class: %lu\n", FileInformationClass);
|
||||
Status = STATUS_INVALID_INFO_CLASS;
|
||||
break;
|
||||
}
|
||||
|
||||
Ccb->u.Directory.FileIndex = PipeIndex;
|
||||
Found = TRUE;
|
||||
|
||||
// if (Stack->Flags & SL_RETURN_SINGLE_ENTRY)
|
||||
// return STATUS_SUCCESS;
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
PipeIndex++;
|
||||
}
|
||||
|
||||
CurrentEntry = CurrentEntry->Flink;
|
||||
}
|
||||
|
||||
if (Found == FALSE)
|
||||
Status = STATUS_NO_MORE_FILES;
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
||||
NTSTATUS NTAPI
|
||||
NpfsDirectoryControl(PDEVICE_OBJECT DeviceObject,
|
||||
PIRP Irp)
|
||||
{
|
||||
PIO_STACK_LOCATION IoStack;
|
||||
PFILE_OBJECT FileObject;
|
||||
PNPFS_CCB Ccb;
|
||||
PNPFS_FCB Fcb;
|
||||
NTSTATUS Status;
|
||||
ULONG Size = 0;
|
||||
|
||||
DPRINT("NpfsDirectoryControl() called\n");
|
||||
|
||||
IoStack = IoGetCurrentIrpStackLocation(Irp);
|
||||
|
||||
FileObject = IoStack->FileObject;
|
||||
|
||||
if (NpfsGetCcb(FileObject, &Ccb) != CCB_DIRECTORY)
|
||||
{
|
||||
Status = STATUS_INVALID_PARAMETER;
|
||||
|
||||
Irp->IoStatus.Status = Status;
|
||||
Irp->IoStatus.Information = 0;
|
||||
|
||||
IoCompleteRequest(Irp, IO_NO_INCREMENT);
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
Fcb = Ccb->Fcb;
|
||||
|
||||
switch (IoStack->MinorFunction)
|
||||
{
|
||||
case IRP_MN_QUERY_DIRECTORY:
|
||||
Status = NpfsQueryDirectory(Ccb,
|
||||
Irp,
|
||||
&Size);
|
||||
break;
|
||||
|
||||
case IRP_MN_NOTIFY_CHANGE_DIRECTORY:
|
||||
DPRINT1("IRP_MN_NOTIFY_CHANGE_DIRECTORY\n");
|
||||
Status = STATUS_NOT_IMPLEMENTED;
|
||||
break;
|
||||
|
||||
default:
|
||||
DPRINT1("NPFS: MinorFunction %d\n", IoStack->MinorFunction);
|
||||
Status = STATUS_INVALID_DEVICE_REQUEST;
|
||||
break;
|
||||
}
|
||||
|
||||
Irp->IoStatus.Status = Status;
|
||||
Irp->IoStatus.Information = Size;
|
||||
|
||||
IoCompleteRequest(Irp, IO_NO_INCREMENT);
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
/* EOF */
|
|
@ -95,6 +95,20 @@ NpfsConnectPipe(PIRP Irp,
|
|||
|
||||
DPRINT("NpfsConnectPipe()\n");
|
||||
|
||||
/* Fail, if the CCB is not a pipe CCB */
|
||||
if (Ccb->Type != CCB_PIPE)
|
||||
{
|
||||
DPRINT1("Not a pipe\n");
|
||||
return STATUS_ILLEGAL_FUNCTION;
|
||||
}
|
||||
|
||||
/* Fail, if the CCB is not a server end CCB */
|
||||
if (Ccb->PipeEnd != FILE_PIPE_SERVER_END)
|
||||
{
|
||||
DPRINT1("Not the server end\n");
|
||||
return STATUS_ILLEGAL_FUNCTION;
|
||||
}
|
||||
|
||||
if (Ccb->PipeState == FILE_PIPE_CONNECTED_STATE)
|
||||
{
|
||||
KeResetEvent(&Ccb->ConnectEvent);
|
||||
|
@ -192,6 +206,20 @@ NpfsDisconnectPipe(PNPFS_CCB Ccb)
|
|||
|
||||
DPRINT("NpfsDisconnectPipe()\n");
|
||||
|
||||
/* Fail, if the CCB is not a pipe CCB */
|
||||
if (Ccb->Type != CCB_PIPE)
|
||||
{
|
||||
DPRINT1("Not a pipe\n");
|
||||
return STATUS_ILLEGAL_FUNCTION;
|
||||
}
|
||||
|
||||
/* Fail, if the CCB is not a server end CCB */
|
||||
if (Ccb->PipeEnd != FILE_PIPE_SERVER_END)
|
||||
{
|
||||
DPRINT1("Not the server end\n");
|
||||
return STATUS_ILLEGAL_FUNCTION;
|
||||
}
|
||||
|
||||
Fcb = Ccb->Fcb;
|
||||
KeLockMutex(&Fcb->CcbListLock);
|
||||
|
||||
|
|
|
@ -44,8 +44,8 @@ DriverEntry(PDRIVER_OBJECT DriverObject,
|
|||
NpfsQueryVolumeInformation;
|
||||
DriverObject->MajorFunction[IRP_MJ_CLEANUP] = NpfsCleanup;
|
||||
DriverObject->MajorFunction[IRP_MJ_FLUSH_BUFFERS] = NpfsFlushBuffers;
|
||||
// DriverObject->MajorFunction[IRP_MJ_DIRECTORY_CONTROL] =
|
||||
// NpfsDirectoryControl;
|
||||
DriverObject->MajorFunction[IRP_MJ_DIRECTORY_CONTROL] =
|
||||
NpfsDirectoryControl;
|
||||
DriverObject->MajorFunction[IRP_MJ_FILE_SYSTEM_CONTROL] =
|
||||
NpfsFileSystemControl;
|
||||
// DriverObject->MajorFunction[IRP_MJ_QUERY_SECURITY] =
|
||||
|
@ -100,4 +100,54 @@ DriverEntry(PDRIVER_OBJECT DriverObject,
|
|||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
FCB_TYPE
|
||||
NpfsGetFcb(PFILE_OBJECT FileObject,
|
||||
PNPFS_FCB *Fcb)
|
||||
{
|
||||
PNPFS_FCB LocalFcb = NULL;
|
||||
FCB_TYPE FcbType = FCB_INVALID;
|
||||
|
||||
_SEH2_TRY
|
||||
{
|
||||
LocalFcb = (PNPFS_FCB)FileObject->FsContext;
|
||||
FcbType = LocalFcb->Type;
|
||||
}
|
||||
_SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER)
|
||||
{
|
||||
LocalFcb = NULL;
|
||||
FcbType = FCB_INVALID;
|
||||
}
|
||||
_SEH2_END;
|
||||
|
||||
*Fcb = LocalFcb;
|
||||
|
||||
return FcbType;
|
||||
}
|
||||
|
||||
|
||||
CCB_TYPE
|
||||
NpfsGetCcb(PFILE_OBJECT FileObject,
|
||||
PNPFS_CCB *Ccb)
|
||||
{
|
||||
PNPFS_CCB LocalCcb = NULL;
|
||||
CCB_TYPE CcbType = CCB_INVALID;
|
||||
|
||||
_SEH2_TRY
|
||||
{
|
||||
LocalCcb = (PNPFS_CCB)FileObject->FsContext2;
|
||||
CcbType = LocalCcb->Type;
|
||||
}
|
||||
_SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER)
|
||||
{
|
||||
LocalCcb = NULL;
|
||||
CcbType = CCB_INVALID;
|
||||
}
|
||||
_SEH2_END;
|
||||
|
||||
*Ccb = LocalCcb;
|
||||
|
||||
return CcbType;
|
||||
}
|
||||
|
||||
/* EOF */
|
||||
|
|
|
@ -3,9 +3,11 @@
|
|||
|
||||
#include <ntifs.h>
|
||||
#include <ndk/iotypes.h>
|
||||
#include <pseh/pseh2.h>
|
||||
|
||||
typedef enum _FCB_TYPE
|
||||
{
|
||||
FCB_INVALID,
|
||||
FCB_DEVICE,
|
||||
FCB_DIRECTORY,
|
||||
FCB_PIPE
|
||||
|
@ -13,6 +15,7 @@ typedef enum _FCB_TYPE
|
|||
|
||||
typedef enum _CCB_TYPE
|
||||
{
|
||||
CCB_INVALID,
|
||||
CCB_DEVICE,
|
||||
CCB_DIRECTORY,
|
||||
CCB_PIPE
|
||||
|
@ -55,6 +58,14 @@ typedef struct _NPFS_FCB
|
|||
LARGE_INTEGER TimeOut;
|
||||
} NPFS_FCB, *PNPFS_FCB;
|
||||
|
||||
|
||||
typedef struct _NPFS_CCB_DIRECTORY_DATA
|
||||
{
|
||||
UNICODE_STRING SearchPattern;
|
||||
ULONG FileIndex;
|
||||
} NPFS_CCB_DIRECTORY_DATA, *PNPFS_CCB_DIRECTORY_DATA;
|
||||
|
||||
|
||||
typedef struct _NPFS_CCB
|
||||
{
|
||||
LIST_ENTRY CcbListEntry;
|
||||
|
@ -79,6 +90,12 @@ typedef struct _NPFS_CCB
|
|||
ULONG MaxDataLength;
|
||||
|
||||
FAST_MUTEX DataListLock; /* Data queue lock */
|
||||
|
||||
union
|
||||
{
|
||||
NPFS_CCB_DIRECTORY_DATA Directory;
|
||||
} u;
|
||||
|
||||
} NPFS_CCB, *PNPFS_CCB;
|
||||
|
||||
typedef struct _NPFS_CONTEXT
|
||||
|
@ -130,6 +147,9 @@ NTSTATUS NTAPI NpfsCleanup(PDEVICE_OBJECT DeviceObject, PIRP Irp);
|
|||
DRIVER_DISPATCH NpfsClose;
|
||||
NTSTATUS NTAPI NpfsClose(PDEVICE_OBJECT DeviceObject, PIRP Irp);
|
||||
|
||||
DRIVER_DISPATCH NpfsDirectoryControl;
|
||||
NTSTATUS NTAPI NpfsDirectoryControl(PDEVICE_OBJECT DeviceObject, PIRP Irp);
|
||||
|
||||
DRIVER_DISPATCH NpfsRead;
|
||||
NTSTATUS NTAPI NpfsRead(PDEVICE_OBJECT DeviceObject, PIRP Irp);
|
||||
|
||||
|
@ -159,5 +179,12 @@ PNPFS_FCB
|
|||
NpfsFindPipe(PNPFS_VCB Vcb,
|
||||
PUNICODE_STRING PipeName);
|
||||
|
||||
FCB_TYPE
|
||||
NpfsGetFcb(PFILE_OBJECT FileObject,
|
||||
PNPFS_FCB *Fcb);
|
||||
|
||||
CCB_TYPE
|
||||
NpfsGetCcb(PFILE_OBJECT FileObject,
|
||||
PNPFS_CCB *Ccb);
|
||||
|
||||
#endif /* __DRIVERS_FS_NP_NPFS_H */
|
||||
|
|
|
@ -307,6 +307,20 @@ NpfsRead(IN PDEVICE_OBJECT DeviceObject,
|
|||
|
||||
DPRINT("NpfsRead(DeviceObject %p, Irp %p)\n", DeviceObject, Irp);
|
||||
|
||||
FileObject = IoGetCurrentIrpStackLocation(Irp)->FileObject;
|
||||
DPRINT("FileObject %p\n", FileObject);
|
||||
DPRINT("Pipe name %wZ\n", &FileObject->FileName);
|
||||
Ccb = FileObject->FsContext2;
|
||||
|
||||
/* Fail, if the CCB is not a pipe CCB */
|
||||
if (Ccb->Type != CCB_PIPE)
|
||||
{
|
||||
DPRINT("Not a pipe!\n");
|
||||
Status = STATUS_INVALID_PARAMETER;
|
||||
Irp->IoStatus.Information = 0;
|
||||
goto done;
|
||||
}
|
||||
|
||||
if (Irp->MdlAddress == NULL)
|
||||
{
|
||||
DPRINT("Irp->MdlAddress == NULL\n");
|
||||
|
@ -315,10 +329,6 @@ NpfsRead(IN PDEVICE_OBJECT DeviceObject,
|
|||
goto done;
|
||||
}
|
||||
|
||||
FileObject = IoGetCurrentIrpStackLocation(Irp)->FileObject;
|
||||
DPRINT("FileObject %p\n", FileObject);
|
||||
DPRINT("Pipe name %wZ\n", &FileObject->FileName);
|
||||
Ccb = FileObject->FsContext2;
|
||||
Context = (PNPFS_CONTEXT)&Irp->Tail.Overlay.DriverContext;
|
||||
|
||||
if ((Ccb->OtherSide) && (Ccb->OtherSide->PipeState == FILE_PIPE_DISCONNECTED_STATE) && (Ccb->PipeState == FILE_PIPE_DISCONNECTED_STATE))
|
||||
|
@ -736,7 +746,7 @@ NpfsWrite(PDEVICE_OBJECT DeviceObject,
|
|||
NTSTATUS Status = STATUS_SUCCESS;
|
||||
ULONG Length;
|
||||
ULONG Offset;
|
||||
ULONG Information;
|
||||
ULONG Information = 0;
|
||||
ULONG CopyLength;
|
||||
ULONG TempLength;
|
||||
|
||||
|
@ -748,12 +758,21 @@ NpfsWrite(PDEVICE_OBJECT DeviceObject,
|
|||
DPRINT("Pipe name %wZ\n", &FileObject->FileName);
|
||||
|
||||
Ccb = FileObject->FsContext2;
|
||||
|
||||
/* Fail, if the CCB is not a pipe CCB */
|
||||
if (Ccb->Type != CCB_PIPE)
|
||||
{
|
||||
DPRINT("Not a pipe!\n");
|
||||
Status = STATUS_INVALID_PARAMETER;
|
||||
Length = 0;
|
||||
goto done;
|
||||
}
|
||||
|
||||
ReaderCcb = Ccb->OtherSide;
|
||||
Fcb = Ccb->Fcb;
|
||||
|
||||
Length = IoStack->Parameters.Write.Length;
|
||||
Offset = IoStack->Parameters.Write.ByteOffset.u.LowPart;
|
||||
Information = 0;
|
||||
|
||||
if (Irp->MdlAddress == NULL)
|
||||
{
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue