sys: IRP_MJ_CREATE

This commit is contained in:
Bill Zissimopoulos 2015-12-07 15:04:35 -08:00
parent 253de21708
commit 264da71f7c

View File

@ -116,7 +116,7 @@ static NTSTATUS FspFsvolCreate(
goto exit; goto exit;
} }
/* impossible create options sent? */ /* check create options */
if (FlagOn(CreateOptions, FILE_NON_DIRECTORY_FILE) && if (FlagOn(CreateOptions, FILE_NON_DIRECTORY_FILE) &&
FlagOn(CreateOptions, FILE_DIRECTORY_FILE)) FlagOn(CreateOptions, FILE_DIRECTORY_FILE))
{ {
@ -454,50 +454,87 @@ VOID FspFsvolCreateComplete(
FSP_RETURN(); FSP_RETURN();
} }
SecurityDescriptor = /* check for trailing backslash */
(PVOID)(Response->Buffer + Response->Rsp.Create.Opened.SecurityDescriptor.Offset); if (HasTrailingBackslash &&
SecurityDescriptorSize = Response->Rsp.Create.Opened.SecurityDescriptor.Size; !FlagOn(ResponseFileAttributes, FILE_ATTRIBUTE_DIRECTORY))
{
FspFsvolCreateClose(Irp, Response);
FSP_RETURN(Result = STATUS_OBJECT_NAME_INVALID);
}
/* are we doing access checks? */ /* are we doing access checks? */
if (FsvrtDeviceExtension->VolumeParams.NoSystemAccessCheck && if (!FsvrtDeviceExtension->VolumeParams.NoSystemAccessCheck)
0 != SecurityDescriptorSize)
{ {
if ((PUINT8)SecurityDescriptor + SecurityDescriptorSize > /* read-only attribute check */
(PUINT8)Response + Response->Size || if (FILE_CREATED != Response->IoStatus.Information &&
!FspValidRelativeSecurityDescriptor(SecurityDescriptor, SecurityDescriptorSize, 0)) FlagOn(ResponseFileAttributes, FILE_ATTRIBUTE_READONLY))
{ {
FspFsvolCreateClose(Irp, Response); /* from fastfat: allowed accesses when read-only */
FSP_RETURN(Result = STATUS_ACCESS_DENIED); ACCESS_MASK Allowed =
DELETE | READ_CONTROL | WRITE_OWNER | WRITE_DAC |
SYNCHRONIZE | ACCESS_SYSTEM_SECURITY |
FILE_READ_DATA | FILE_READ_EA | FILE_WRITE_EA |
FILE_READ_ATTRIBUTES | FILE_WRITE_ATTRIBUTES |
FILE_EXECUTE | FILE_TRAVERSE | FILE_LIST_DIRECTORY |
FILE_ADD_SUBDIRECTORY | FILE_ADD_FILE | FILE_DELETE_CHILD;
if (FlagOn(DesiredAccess, ~Allowed))
{
FspFsvolCreateClose(Irp, Response);
FSP_RETURN(Result = STATUS_ACCESS_DENIED);
}
else
if (FlagOn(CreateOptions, FILE_DELETE_ON_CLOSE))
{
FspFsvolCreateClose(Irp, Response);
FSP_RETURN(Result = STATUS_CANNOT_DELETE);
}
} }
if (!SeAccessCheck(SecurityDescriptor, /* security descriptor check */
&AccessState->SubjectSecurityContext, SecurityDescriptor =
FALSE, (PVOID)(Response->Buffer + Response->Rsp.Create.Opened.SecurityDescriptor.Offset);
DesiredAccess, SecurityDescriptorSize = Response->Rsp.Create.Opened.SecurityDescriptor.Size;
AccessState->PreviouslyGrantedAccess, if (0 != SecurityDescriptorSize)
&Privileges,
IoGetFileObjectGenericMapping(),
RequestorMode,
&GrantedAccess,
&Result))
{ {
FspFsvolCreateClose(Irp, Response); if ((PUINT8)SecurityDescriptor + SecurityDescriptorSize >
FSP_RETURN(); (PUINT8)Response + Response->Size ||
} !FspValidRelativeSecurityDescriptor(SecurityDescriptor, SecurityDescriptorSize, 0))
{
FspFsvolCreateClose(Irp, Response);
FSP_RETURN(Result = STATUS_ACCESS_DENIED);
}
if (0 != Privileges) /* access check */
{ if (!SeAccessCheck(SecurityDescriptor,
Result = SeAppendPrivileges(AccessState, Privileges); &AccessState->SubjectSecurityContext,
SeFreePrivileges(Privileges); FALSE,
if (!NT_SUCCESS(Result)) DesiredAccess,
AccessState->PreviouslyGrantedAccess,
&Privileges,
IoGetFileObjectGenericMapping(),
RequestorMode,
&GrantedAccess,
&Result))
{ {
FspFsvolCreateClose(Irp, Response); FspFsvolCreateClose(Irp, Response);
FSP_RETURN(); FSP_RETURN();
} }
}
SetFlag(AccessState->PreviouslyGrantedAccess, GrantedAccess); if (0 != Privileges)
ClearFlag(AccessState->RemainingDesiredAccess, GrantedAccess); {
Result = SeAppendPrivileges(AccessState, Privileges);
SeFreePrivileges(Privileges);
if (!NT_SUCCESS(Result))
{
FspFsvolCreateClose(Irp, Response);
FSP_RETURN();
}
}
SetFlag(AccessState->PreviouslyGrantedAccess, GrantedAccess);
ClearFlag(AccessState->RemainingDesiredAccess, GrantedAccess);
}
} }
/* were we asked to open a directory or non-directory? */ /* were we asked to open a directory or non-directory? */
@ -513,12 +550,6 @@ VOID FspFsvolCreateComplete(
FspFsvolCreateClose(Irp, Response); FspFsvolCreateClose(Irp, Response);
FSP_RETURN(Result = STATUS_FILE_IS_A_DIRECTORY); FSP_RETURN(Result = STATUS_FILE_IS_A_DIRECTORY);
} }
if (HasTrailingBackslash &&
!FlagOn(ResponseFileAttributes, FILE_ATTRIBUTE_DIRECTORY))
{
FspFsvolCreateClose(Irp, Response);
FSP_RETURN(Result = STATUS_OBJECT_NAME_INVALID);
}
/* record the user-mode file system contexts */ /* record the user-mode file system contexts */
FsContext->UserContext = Response->Rsp.Create.Opened.UserContext; FsContext->UserContext = Response->Rsp.Create.Opened.UserContext;