mirror of
https://github.com/reactos/reactos.git
synced 2024-08-26 05:08:39 +00:00
[fastfat_new]
- Fix wrong comment in FatiCreate, spotted by Ged Murphy. - Add some parameters validation to FatiCreate, and a check for volume open request. - Add node types and a decoding routine. - Implement VCB locking/unlocking. svn path=/trunk/; revision=43202
This commit is contained in:
parent
eaf6203af2
commit
dfe3bd48b3
|
@ -33,7 +33,9 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
||||||
ULONG CreateDisposition;
|
ULONG CreateDisposition;
|
||||||
|
|
||||||
/* Control blocks */
|
/* Control blocks */
|
||||||
PVCB Vcb;
|
PVCB Vcb, DecodedVcb;
|
||||||
|
PFCB Fcb;
|
||||||
|
PCCB Ccb;
|
||||||
|
|
||||||
/* IRP data */
|
/* IRP data */
|
||||||
PFILE_OBJECT FileObject;
|
PFILE_OBJECT FileObject;
|
||||||
|
@ -48,8 +50,8 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
||||||
ULONG EaLength;
|
ULONG EaLength;
|
||||||
|
|
||||||
/* Misc */
|
/* Misc */
|
||||||
//NTSTATUS Status;
|
NTSTATUS Status;
|
||||||
IO_STATUS_BLOCK Iosb;
|
//IO_STATUS_BLOCK Iosb;
|
||||||
PIO_STACK_LOCATION IrpSp;
|
PIO_STACK_LOCATION IrpSp;
|
||||||
|
|
||||||
/* Get current IRP stack location */
|
/* Get current IRP stack location */
|
||||||
|
@ -75,14 +77,14 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
||||||
(IrpSp->FileObject->FileName.Buffer[1] == L'\\') &&
|
(IrpSp->FileObject->FileName.Buffer[1] == L'\\') &&
|
||||||
(IrpSp->FileObject->FileName.Buffer[0] == L'\\'))
|
(IrpSp->FileObject->FileName.Buffer[0] == L'\\'))
|
||||||
{
|
{
|
||||||
/* Remove two leading slashes */
|
/* Remove a leading slash */
|
||||||
IrpSp->FileObject->FileName.Length -= sizeof(WCHAR);
|
IrpSp->FileObject->FileName.Length -= sizeof(WCHAR);
|
||||||
|
|
||||||
RtlMoveMemory(&IrpSp->FileObject->FileName.Buffer[0],
|
RtlMoveMemory(&IrpSp->FileObject->FileName.Buffer[0],
|
||||||
&IrpSp->FileObject->FileName.Buffer[1],
|
&IrpSp->FileObject->FileName.Buffer[1],
|
||||||
IrpSp->FileObject->FileName.Length );
|
IrpSp->FileObject->FileName.Length );
|
||||||
|
|
||||||
/* If there are two leading slashes again, exit */
|
/* Check again: if there are still two leading slashes,
|
||||||
|
exit with an error */
|
||||||
if ((IrpSp->FileObject->FileName.Length > sizeof(WCHAR)) &&
|
if ((IrpSp->FileObject->FileName.Length > sizeof(WCHAR)) &&
|
||||||
(IrpSp->FileObject->FileName.Buffer[1] == L'\\') &&
|
(IrpSp->FileObject->FileName.Buffer[1] == L'\\') &&
|
||||||
(IrpSp->FileObject->FileName.Buffer[0] == L'\\'))
|
(IrpSp->FileObject->FileName.Buffer[0] == L'\\'))
|
||||||
|
@ -146,6 +148,55 @@ FatiCreate(IN PFAT_IRP_CONTEXT IrpContext,
|
||||||
((CreateDisposition == FILE_OPEN) ||
|
((CreateDisposition == FILE_OPEN) ||
|
||||||
(CreateDisposition == FILE_OPEN_IF)));
|
(CreateDisposition == FILE_OPEN_IF)));
|
||||||
|
|
||||||
|
/* Validate parameters: directory/nondirectory mismatch and
|
||||||
|
AllocationSize being more than 4GB */
|
||||||
|
if ((DirectoryFile && NonDirectoryFile) ||
|
||||||
|
Irp->Overlay.AllocationSize.HighPart != 0)
|
||||||
|
{
|
||||||
|
FatCompleteRequest(IrpContext, Irp, STATUS_INVALID_PARAMETER);
|
||||||
|
|
||||||
|
DPRINT1("FatiCreate: STATUS_INVALID_PARAMETER\n", 0);
|
||||||
|
return STATUS_INVALID_PARAMETER;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Acquire the VCB lock exclusively */
|
||||||
|
if (!FatAcquireExclusiveVcb(IrpContext, Vcb))
|
||||||
|
{
|
||||||
|
// TODO: Postpone the IRP for later processing
|
||||||
|
ASSERT(FALSE);
|
||||||
|
return STATUS_NOT_IMPLEMENTED;
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: Verify the VCB
|
||||||
|
|
||||||
|
/* If VCB is locked, then no file openings are possible */
|
||||||
|
if (Vcb->State & VCB_STATE_FLAG_LOCKED)
|
||||||
|
{
|
||||||
|
DPRINT1("This volume is locked\n");
|
||||||
|
Status = STATUS_ACCESS_DENIED;
|
||||||
|
|
||||||
|
/* Cleanup and return */
|
||||||
|
FatReleaseVcb(IrpContext, Vcb);
|
||||||
|
return Status;
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: Check if the volume is write protected and disallow DELETE_ON_CLOSE
|
||||||
|
|
||||||
|
// TODO: Make sure EAs aren't supported on FAT32
|
||||||
|
|
||||||
|
if (FileName.Length == 0)
|
||||||
|
{
|
||||||
|
/* It is a volume open request, check related FO to be sure */
|
||||||
|
|
||||||
|
if (!RelatedFO ||
|
||||||
|
FatDecodeFileObject(RelatedFO, &DecodedVcb, &Fcb, &Ccb) == UserVolumeOpen)
|
||||||
|
{
|
||||||
|
/* It is indeed a volume open request */
|
||||||
|
DPRINT1("Volume open request, not implemented now!\n");
|
||||||
|
UNIMPLEMENTED;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
//return Iosb.Status;
|
//return Iosb.Status;
|
||||||
return STATUS_SUCCESS;
|
return STATUS_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
|
@ -271,4 +271,99 @@ FatQueueRequest(IN PFAT_IRP_CONTEXT IrpContext,
|
||||||
ExQueueWorkItem(&IrpContext->WorkQueueItem,
|
ExQueueWorkItem(&IrpContext->WorkQueueItem,
|
||||||
DelayedWorkQueue);
|
DelayedWorkQueue);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TYPE_OF_OPEN
|
||||||
|
NTAPI
|
||||||
|
FatDecodeFileObject(IN PFILE_OBJECT FileObject,
|
||||||
|
OUT PVCB *Vcb,
|
||||||
|
OUT PFCB *FcbOrDcb,
|
||||||
|
OUT PCCB *Ccb)
|
||||||
|
{
|
||||||
|
TYPE_OF_OPEN TypeOfOpen = UnopenedFileObject;
|
||||||
|
PVOID FsContext = FileObject->FsContext;
|
||||||
|
PVOID FsContext2 = FileObject->FsContext2;
|
||||||
|
|
||||||
|
/* If FsContext is NULL, then everything is NULL */
|
||||||
|
if (!FsContext)
|
||||||
|
{
|
||||||
|
*Ccb = NULL;
|
||||||
|
*FcbOrDcb = NULL;
|
||||||
|
*Vcb = NULL;
|
||||||
|
|
||||||
|
return TypeOfOpen;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* CCB is always stored in FsContext2 */
|
||||||
|
*Ccb = FsContext2;
|
||||||
|
|
||||||
|
/* Switch according to the NodeType */
|
||||||
|
switch (FatNodeType(FsContext))
|
||||||
|
{
|
||||||
|
/* Volume */
|
||||||
|
case FAT_NTC_VCB:
|
||||||
|
*FcbOrDcb = NULL;
|
||||||
|
*Vcb = FsContext;
|
||||||
|
|
||||||
|
TypeOfOpen = ( *Ccb == NULL ? VirtualVolumeFile : UserVolumeOpen );
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
/* Root or normal directory*/
|
||||||
|
case FAT_NTC_ROOT_DCB:
|
||||||
|
case FAT_NTC_DCB:
|
||||||
|
*FcbOrDcb = FsContext;
|
||||||
|
*Vcb = (*FcbOrDcb)->Vcb;
|
||||||
|
|
||||||
|
TypeOfOpen = (*Ccb == NULL ? DirectoryFile : UserDirectoryOpen);
|
||||||
|
|
||||||
|
DPRINT1("Referencing a directory: %Z\n", &(*FcbOrDcb)->FullFileName);
|
||||||
|
break;
|
||||||
|
|
||||||
|
/* File */
|
||||||
|
case FAT_NTC_FCB:
|
||||||
|
*FcbOrDcb = FsContext;
|
||||||
|
*Vcb = (*FcbOrDcb)->Vcb;
|
||||||
|
|
||||||
|
TypeOfOpen = (*Ccb == NULL ? EaFile : UserFileOpen);
|
||||||
|
|
||||||
|
DPRINT1("Referencing a file: %Z\n", &(*FcbOrDcb)->FullFileName);
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
DPRINT1("Unknown node type %x\n", FatNodeType(FsContext));
|
||||||
|
ASSERT(FALSE);
|
||||||
|
}
|
||||||
|
|
||||||
|
return TypeOfOpen;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BOOLEAN
|
||||||
|
NTAPI
|
||||||
|
FatAcquireExclusiveVcb(IN PFAT_IRP_CONTEXT IrpContext,
|
||||||
|
IN PVCB Vcb)
|
||||||
|
{
|
||||||
|
/* Acquire VCB's resource if possible */
|
||||||
|
if (ExAcquireResourceExclusiveLite(&Vcb->Resource,
|
||||||
|
BooleanFlagOn(IrpContext->Flags, IRPCONTEXT_CANWAIT)))
|
||||||
|
{
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
VOID
|
||||||
|
NTAPI
|
||||||
|
FatReleaseVcb(IN PFAT_IRP_CONTEXT IrpContext,
|
||||||
|
IN PVCB Vcb)
|
||||||
|
{
|
||||||
|
/* Release VCB's resource */
|
||||||
|
ExReleaseResourceLite(&Vcb->Resource);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/* EOF */
|
/* EOF */
|
||||||
|
|
|
@ -132,6 +132,20 @@ FatCompleteRequest(PFAT_IRP_CONTEXT IrpContext OPTIONAL,
|
||||||
PIRP Irp OPTIONAL,
|
PIRP Irp OPTIONAL,
|
||||||
NTSTATUS Status);
|
NTSTATUS Status);
|
||||||
|
|
||||||
|
BOOLEAN NTAPI
|
||||||
|
FatAcquireExclusiveVcb(IN PFAT_IRP_CONTEXT IrpContext,
|
||||||
|
IN PVCB Vcb);
|
||||||
|
|
||||||
|
VOID NTAPI
|
||||||
|
FatReleaseVcb(IN PFAT_IRP_CONTEXT IrpContext,
|
||||||
|
IN PVCB Vcb);
|
||||||
|
|
||||||
|
TYPE_OF_OPEN
|
||||||
|
NTAPI
|
||||||
|
FatDecodeFileObject(IN PFILE_OBJECT FileObject,
|
||||||
|
OUT PVCB *Vcb,
|
||||||
|
OUT PFCB *FcbOrDcb,
|
||||||
|
OUT PCCB *Ccb);
|
||||||
|
|
||||||
/* --------------------------------------------------------- lock.c */
|
/* --------------------------------------------------------- lock.c */
|
||||||
|
|
||||||
|
|
|
@ -489,6 +489,12 @@ FatInitializeVcb(IN PFAT_IRP_CONTEXT IrpContext,
|
||||||
Vcb->Header.ValidDataLength.HighPart = MAXLONG;
|
Vcb->Header.ValidDataLength.HighPart = MAXLONG;
|
||||||
Vcb->Header.ValidDataLength.LowPart = MAXULONG;
|
Vcb->Header.ValidDataLength.LowPart = MAXULONG;
|
||||||
|
|
||||||
|
/* Set VCB to a good condition */
|
||||||
|
Vcb->Condition = VcbGood;
|
||||||
|
|
||||||
|
/* Initialize VCB's resource */
|
||||||
|
ExInitializeResourceLite(&Vcb->Resource);
|
||||||
|
|
||||||
/* Initialize CC */
|
/* Initialize CC */
|
||||||
CcInitializeCacheMap(Vcb->StreamFileObject,
|
CcInitializeCacheMap(Vcb->StreamFileObject,
|
||||||
(PCC_FILE_SIZES)&Vcb->Header.AllocationSize,
|
(PCC_FILE_SIZES)&Vcb->Header.AllocationSize,
|
||||||
|
|
|
@ -8,6 +8,18 @@ typedef PVOID PBCB;
|
||||||
|
|
||||||
typedef NTSTATUS (*PFAT_OPERATION_HANDLER) (PFAT_IRP_CONTEXT);
|
typedef NTSTATUS (*PFAT_OPERATION_HANDLER) (PFAT_IRP_CONTEXT);
|
||||||
|
|
||||||
|
/* Node type stuff */
|
||||||
|
typedef CSHORT FAT_NODE_TYPE;
|
||||||
|
typedef FAT_NODE_TYPE *PFAT_NODE_TYPE;
|
||||||
|
|
||||||
|
#define FatNodeType(Ptr) (*((PFAT_NODE_TYPE)(Ptr)))
|
||||||
|
|
||||||
|
/* Node type codes */
|
||||||
|
#define FAT_NTC_VCB (CSHORT) '00VF'
|
||||||
|
#define FAT_NTC_FCB (CSHORT) 'CF'
|
||||||
|
#define FAT_NTC_DCB (CSHORT) 'DF'
|
||||||
|
#define FAT_NTC_ROOT_DCB (CSHORT) 'RFD'
|
||||||
|
|
||||||
typedef struct _FAT_GLOBAL_DATA
|
typedef struct _FAT_GLOBAL_DATA
|
||||||
{
|
{
|
||||||
ERESOURCE Resource;
|
ERESOURCE Resource;
|
||||||
|
@ -116,7 +128,14 @@ typedef struct _FAT_METHODS {
|
||||||
PFAT_SETFAT_VALUE_RUN_ROUTINE SetValueRun;
|
PFAT_SETFAT_VALUE_RUN_ROUTINE SetValueRun;
|
||||||
} FAT_METHODS, *PFAT_METHODS;
|
} FAT_METHODS, *PFAT_METHODS;
|
||||||
|
|
||||||
#define FAT_NTC_VCB (USHORT) '00VF'
|
#define VCB_STATE_FLAG_LOCKED 0x01
|
||||||
|
|
||||||
|
typedef enum _VCB_CONDITION
|
||||||
|
{
|
||||||
|
VcbGood,
|
||||||
|
VcbNotMounted,
|
||||||
|
VcbBad
|
||||||
|
} VCB_CONDITION;
|
||||||
|
|
||||||
/* Volume Control Block */
|
/* Volume Control Block */
|
||||||
typedef struct _VCB
|
typedef struct _VCB
|
||||||
|
@ -129,6 +148,9 @@ typedef struct _VCB
|
||||||
PDEVICE_OBJECT TargetDeviceObject;
|
PDEVICE_OBJECT TargetDeviceObject;
|
||||||
LIST_ENTRY VcbLinks;
|
LIST_ENTRY VcbLinks;
|
||||||
PVPB Vpb;
|
PVPB Vpb;
|
||||||
|
ULONG State;
|
||||||
|
VCB_CONDITION Condition;
|
||||||
|
ERESOURCE Resource;
|
||||||
|
|
||||||
/* Notifications support */
|
/* Notifications support */
|
||||||
PNOTIFY_SYNC NotifySync;
|
PNOTIFY_SYNC NotifySync;
|
||||||
|
@ -196,9 +218,6 @@ typedef struct _FCB_NAME_LINK {
|
||||||
UCHAR Type;
|
UCHAR Type;
|
||||||
} FCB_NAME_LINK, *PFCB_NAME_LINK;
|
} FCB_NAME_LINK, *PFCB_NAME_LINK;
|
||||||
|
|
||||||
#define FAT_NTC_FCB (USHORT) 'CF'
|
|
||||||
#define FAT_NTC_DCB (USHORT) 'DF'
|
|
||||||
|
|
||||||
typedef struct _FCB
|
typedef struct _FCB
|
||||||
{
|
{
|
||||||
FSRTL_ADVANCED_FCB_HEADER Header;
|
FSRTL_ADVANCED_FCB_HEADER Header;
|
||||||
|
@ -225,6 +244,8 @@ typedef struct _FCB
|
||||||
FCB_NAME_LINK FileName[0x2];
|
FCB_NAME_LINK FileName[0x2];
|
||||||
/* Buffer for the short name */
|
/* Buffer for the short name */
|
||||||
WCHAR ShortNameBuffer[0xc];
|
WCHAR ShortNameBuffer[0xc];
|
||||||
|
/* Full file name */
|
||||||
|
UNICODE_STRING FullFileName;
|
||||||
/* File basic info */
|
/* File basic info */
|
||||||
FILE_BASIC_INFORMATION BasicInfo;
|
FILE_BASIC_INFORMATION BasicInfo;
|
||||||
union
|
union
|
||||||
|
@ -285,6 +306,16 @@ typedef struct _CCB
|
||||||
UCHAR Flags;
|
UCHAR Flags;
|
||||||
} CCB, *PCCB;
|
} CCB, *PCCB;
|
||||||
|
|
||||||
|
typedef enum _TYPE_OF_OPEN
|
||||||
|
{
|
||||||
|
UnopenedFileObject,
|
||||||
|
UserFileOpen,
|
||||||
|
UserDirectoryOpen,
|
||||||
|
UserVolumeOpen,
|
||||||
|
VirtualVolumeFile,
|
||||||
|
DirectoryFile,
|
||||||
|
EaFile
|
||||||
|
} TYPE_OF_OPEN;
|
||||||
|
|
||||||
#define CCB_SEARCH_RETURN_SINGLE_ENTRY 0x01
|
#define CCB_SEARCH_RETURN_SINGLE_ENTRY 0x01
|
||||||
#define CCB_SEARCH_PATTERN_LEGAL_8DOT3 0x02
|
#define CCB_SEARCH_PATTERN_LEGAL_8DOT3 0x02
|
||||||
|
|
Loading…
Reference in a new issue