mirror of
https://github.com/reactos/reactos.git
synced 2025-08-05 16:52:59 +00:00
- Zero out the OPEN_PACKET and only set non-zero members in functions that use it.
- NtCancelIoFile: - Don't use macro-based list looping. - Update operation counts. - Wait 10ms instead of 100ms. svn path=/trunk/; revision=22941
This commit is contained in:
parent
0535c5d920
commit
8395aae6a0
1 changed files with 62 additions and 93 deletions
|
@ -1099,33 +1099,19 @@ IopQueryAttributesFile(IN POBJECT_ATTRIBUTES ObjectAttributes,
|
||||||
IsBasic = (FileInformationSize == sizeof(FILE_BASIC_INFORMATION));
|
IsBasic = (FileInformationSize == sizeof(FILE_BASIC_INFORMATION));
|
||||||
|
|
||||||
/* Setup the Open Packet */
|
/* Setup the Open Packet */
|
||||||
|
RtlZeroMemory(&OpenPacket, sizeof(OPEN_PACKET));
|
||||||
OpenPacket.Type = IO_TYPE_OPEN_PACKET;
|
OpenPacket.Type = IO_TYPE_OPEN_PACKET;
|
||||||
OpenPacket.Size = sizeof(OPEN_PACKET);
|
OpenPacket.Size = sizeof(OPEN_PACKET);
|
||||||
OpenPacket.FileObject = NULL;
|
|
||||||
OpenPacket.FinalStatus = STATUS_SUCCESS;
|
|
||||||
OpenPacket.Information = 0;
|
|
||||||
OpenPacket.ParseCheck = 0;
|
|
||||||
OpenPacket.RelatedFileObject = NULL;
|
|
||||||
OpenPacket.AllocationSize.QuadPart = 0;
|
|
||||||
OpenPacket.CreateOptions = FILE_OPEN_REPARSE_POINT;
|
OpenPacket.CreateOptions = FILE_OPEN_REPARSE_POINT;
|
||||||
OpenPacket.FileAttributes = 0;
|
|
||||||
OpenPacket.ShareAccess = FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE;
|
OpenPacket.ShareAccess = FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE;
|
||||||
OpenPacket.EaBuffer = NULL;
|
|
||||||
OpenPacket.EaLength = 0;
|
|
||||||
OpenPacket.Options = 0;
|
|
||||||
OpenPacket.Disposition = FILE_OPEN;
|
OpenPacket.Disposition = FILE_OPEN;
|
||||||
OpenPacket.BasicInformation = IsBasic ? FileInformation : NULL;
|
OpenPacket.BasicInformation = IsBasic ? FileInformation : NULL;
|
||||||
OpenPacket.NetworkInformation = IsBasic ? &NetworkOpenInfo :
|
OpenPacket.NetworkInformation = IsBasic ? &NetworkOpenInfo :
|
||||||
(AccessMode != KernelMode) ?
|
(AccessMode != KernelMode) ?
|
||||||
&NetworkOpenInfo : FileInformation;
|
&NetworkOpenInfo : FileInformation;
|
||||||
OpenPacket.CreateFileType = 0;
|
|
||||||
OpenPacket.MailslotOrPipeParameters = NULL;
|
|
||||||
OpenPacket.Override = FALSE;
|
|
||||||
OpenPacket.QueryOnly = TRUE;
|
OpenPacket.QueryOnly = TRUE;
|
||||||
OpenPacket.DeleteOnly = FALSE;
|
|
||||||
OpenPacket.FullAttributes = IsBasic ? FALSE : TRUE;
|
OpenPacket.FullAttributes = IsBasic ? FALSE : TRUE;
|
||||||
OpenPacket.DummyFileObject = &DummyFileObject;
|
OpenPacket.DummyFileObject = &DummyFileObject;
|
||||||
OpenPacket.InternalFlags = 0;
|
|
||||||
|
|
||||||
/* Update the operation count */
|
/* Update the operation count */
|
||||||
IopUpdateOperationCount(IopOtherTransfer);
|
IopUpdateOperationCount(IopOtherTransfer);
|
||||||
|
@ -1314,13 +1300,9 @@ IoCreateFile(OUT PHANDLE FileHandle,
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Setup the Open Packet */
|
/* Setup the Open Packet */
|
||||||
|
RtlZeroMemory(&OpenPacket, sizeof(OPEN_PACKET));
|
||||||
OpenPacket.Type = IO_TYPE_OPEN_PACKET;
|
OpenPacket.Type = IO_TYPE_OPEN_PACKET;
|
||||||
OpenPacket.Size = sizeof(OPEN_PACKET);
|
OpenPacket.Size = sizeof(OPEN_PACKET);
|
||||||
OpenPacket.FileObject = NULL;
|
|
||||||
OpenPacket.FinalStatus = STATUS_SUCCESS;
|
|
||||||
OpenPacket.Information = 0;
|
|
||||||
OpenPacket.ParseCheck = 0;
|
|
||||||
OpenPacket.RelatedFileObject = NULL;
|
|
||||||
OpenPacket.OriginalAttributes = *ObjectAttributes;
|
OpenPacket.OriginalAttributes = *ObjectAttributes;
|
||||||
OpenPacket.AllocationSize = SafeAllocationSize;
|
OpenPacket.AllocationSize = SafeAllocationSize;
|
||||||
OpenPacket.CreateOptions = CreateOptions;
|
OpenPacket.CreateOptions = CreateOptions;
|
||||||
|
@ -1330,16 +1312,8 @@ IoCreateFile(OUT PHANDLE FileHandle,
|
||||||
OpenPacket.EaLength = EaLength;
|
OpenPacket.EaLength = EaLength;
|
||||||
OpenPacket.Options = Options;
|
OpenPacket.Options = Options;
|
||||||
OpenPacket.Disposition = CreateDisposition;
|
OpenPacket.Disposition = CreateDisposition;
|
||||||
OpenPacket.BasicInformation = NULL;
|
|
||||||
OpenPacket.NetworkInformation = NULL;
|
|
||||||
OpenPacket.CreateFileType = CreateFileType;
|
OpenPacket.CreateFileType = CreateFileType;
|
||||||
OpenPacket.MailslotOrPipeParameters = ExtraCreateParameters;
|
OpenPacket.MailslotOrPipeParameters = ExtraCreateParameters;
|
||||||
OpenPacket.Override = FALSE;
|
|
||||||
OpenPacket.QueryOnly = FALSE;
|
|
||||||
OpenPacket.DeleteOnly = FALSE;
|
|
||||||
OpenPacket.FullAttributes = FALSE;
|
|
||||||
OpenPacket.DummyFileObject = NULL;
|
|
||||||
OpenPacket.InternalFlags = 0;
|
|
||||||
|
|
||||||
/* Update the operation count */
|
/* Update the operation count */
|
||||||
IopUpdateOperationCount(IopOtherTransfer);
|
IopUpdateOperationCount(IopOtherTransfer);
|
||||||
|
@ -1596,31 +1570,17 @@ IoFastQueryNetworkAttributes(IN POBJECT_ATTRIBUTES ObjectAttributes,
|
||||||
PAGED_CODE();
|
PAGED_CODE();
|
||||||
|
|
||||||
/* Setup the Open Packet */
|
/* Setup the Open Packet */
|
||||||
|
RtlZeroMemory(&OpenPacket, sizeof(OPEN_PACKET));
|
||||||
OpenPacket.Type = IO_TYPE_OPEN_PACKET;
|
OpenPacket.Type = IO_TYPE_OPEN_PACKET;
|
||||||
OpenPacket.Size = sizeof(OPEN_PACKET);
|
OpenPacket.Size = sizeof(OPEN_PACKET);
|
||||||
OpenPacket.FileObject = NULL;
|
|
||||||
OpenPacket.FinalStatus = STATUS_SUCCESS;
|
|
||||||
OpenPacket.Information = 0;
|
|
||||||
OpenPacket.ParseCheck = 0;
|
|
||||||
OpenPacket.RelatedFileObject = NULL;
|
|
||||||
OpenPacket.AllocationSize.QuadPart = 0;
|
|
||||||
OpenPacket.CreateOptions = OpenOptions | FILE_OPEN_REPARSE_POINT;
|
OpenPacket.CreateOptions = OpenOptions | FILE_OPEN_REPARSE_POINT;
|
||||||
OpenPacket.FileAttributes = 0;
|
|
||||||
OpenPacket.ShareAccess = FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE;
|
OpenPacket.ShareAccess = FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE;
|
||||||
OpenPacket.EaBuffer = NULL;
|
|
||||||
OpenPacket.EaLength = 0;
|
|
||||||
OpenPacket.Options = IO_FORCE_ACCESS_CHECK;
|
OpenPacket.Options = IO_FORCE_ACCESS_CHECK;
|
||||||
OpenPacket.Disposition = FILE_OPEN;
|
OpenPacket.Disposition = FILE_OPEN;
|
||||||
OpenPacket.BasicInformation = NULL;
|
|
||||||
OpenPacket.NetworkInformation = Buffer;
|
OpenPacket.NetworkInformation = Buffer;
|
||||||
OpenPacket.CreateFileType = 0;
|
|
||||||
OpenPacket.MailslotOrPipeParameters = NULL;
|
|
||||||
OpenPacket.Override = FALSE;
|
|
||||||
OpenPacket.QueryOnly = TRUE;
|
OpenPacket.QueryOnly = TRUE;
|
||||||
OpenPacket.DeleteOnly = FALSE;
|
|
||||||
OpenPacket.FullAttributes = TRUE;
|
OpenPacket.FullAttributes = TRUE;
|
||||||
OpenPacket.DummyFileObject = &DummyFileObject;
|
OpenPacket.DummyFileObject = &DummyFileObject;
|
||||||
OpenPacket.InternalFlags = 0;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Attempt opening the file. This will call the I/O Parse Routine for
|
* Attempt opening the file. This will call the I/O Parse Routine for
|
||||||
|
@ -2146,25 +2106,32 @@ NtCancelIoFile(IN HANDLE FileHandle,
|
||||||
LARGE_INTEGER Interval;
|
LARGE_INTEGER Interval;
|
||||||
KPROCESSOR_MODE PreviousMode = KeGetPreviousMode();
|
KPROCESSOR_MODE PreviousMode = KeGetPreviousMode();
|
||||||
NTSTATUS Status = STATUS_SUCCESS;
|
NTSTATUS Status = STATUS_SUCCESS;
|
||||||
|
PLIST_ENTRY ListHead, NextEntry;
|
||||||
PAGED_CODE();
|
PAGED_CODE();
|
||||||
|
|
||||||
|
/* Check the previous mode */
|
||||||
if (PreviousMode != KernelMode)
|
if (PreviousMode != KernelMode)
|
||||||
{
|
{
|
||||||
|
/* Enter SEH for probing */
|
||||||
_SEH_TRY
|
_SEH_TRY
|
||||||
{
|
{
|
||||||
|
/* Probe the I/O Status Block */
|
||||||
ProbeForWrite(IoStatusBlock,
|
ProbeForWrite(IoStatusBlock,
|
||||||
sizeof(IO_STATUS_BLOCK),
|
sizeof(IO_STATUS_BLOCK),
|
||||||
sizeof(ULONG));
|
sizeof(ULONG));
|
||||||
}
|
}
|
||||||
_SEH_HANDLE
|
_SEH_HANDLE
|
||||||
{
|
{
|
||||||
|
/* Get the exception code */
|
||||||
Status = _SEH_GetExceptionCode();
|
Status = _SEH_GetExceptionCode();
|
||||||
}
|
}
|
||||||
_SEH_END;
|
_SEH_END;
|
||||||
|
|
||||||
|
/* Return exception code on failure */
|
||||||
if (!NT_SUCCESS(Status)) return Status;
|
if (!NT_SUCCESS(Status)) return Status;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Reference the file object */
|
||||||
Status = ObReferenceObjectByHandle(FileHandle,
|
Status = ObReferenceObjectByHandle(FileHandle,
|
||||||
0,
|
0,
|
||||||
IoFileObjectType,
|
IoFileObjectType,
|
||||||
|
@ -2176,59 +2143,77 @@ NtCancelIoFile(IN HANDLE FileHandle,
|
||||||
/* IRP cancellations are synchronized at APC_LEVEL. */
|
/* IRP cancellations are synchronized at APC_LEVEL. */
|
||||||
OldIrql = KfRaiseIrql(APC_LEVEL);
|
OldIrql = KfRaiseIrql(APC_LEVEL);
|
||||||
|
|
||||||
/*
|
/* Get the current thread */
|
||||||
* Walk the list of active IRPs and cancel the ones that belong to
|
|
||||||
* our file object.
|
|
||||||
*/
|
|
||||||
|
|
||||||
Thread = PsGetCurrentThread();
|
Thread = PsGetCurrentThread();
|
||||||
|
|
||||||
LIST_FOR_EACH(Irp, &Thread->IrpList, IRP, ThreadListEntry)
|
/* Update the operation counts */
|
||||||
|
IopUpdateOperationCount(IopOtherTransfer);
|
||||||
|
|
||||||
|
/* Loop the list */
|
||||||
|
ListHead = &Thread->IrpList;
|
||||||
|
NextEntry = ListHead->Flink;
|
||||||
|
while (ListHead != NextEntry)
|
||||||
{
|
{
|
||||||
|
/* Get the IRP and check if the File Object matches */
|
||||||
|
Irp = CONTAINING_RECORD(NextEntry, IRP, ThreadListEntry);
|
||||||
if (Irp->Tail.Overlay.OriginalFileObject == FileObject)
|
if (Irp->Tail.Overlay.OriginalFileObject == FileObject)
|
||||||
{
|
{
|
||||||
|
/* Cancel this IRP and keep looping */
|
||||||
IoCancelIrp(Irp);
|
IoCancelIrp(Irp);
|
||||||
/* Don't break here, we want to cancel all IRPs for the file object. */
|
|
||||||
OurIrpsInList = TRUE;
|
OurIrpsInList = TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Go to the next entry */
|
||||||
|
NextEntry = NextEntry->Flink;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Lower the IRQL */
|
||||||
KfLowerIrql(OldIrql);
|
KfLowerIrql(OldIrql);
|
||||||
|
|
||||||
while (OurIrpsInList)
|
/* Check if we had found an IRP */
|
||||||
|
if (OurIrpsInList)
|
||||||
{
|
{
|
||||||
OurIrpsInList = FALSE;
|
/* Setup a 10ms wait */
|
||||||
|
Interval.QuadPart = -100000;
|
||||||
|
|
||||||
/* Wait a short while and then look if all our IRPs were completed. */
|
/* Start looping */
|
||||||
Interval.QuadPart = -1000000; /* 100 milliseconds */
|
while (OurIrpsInList)
|
||||||
KeDelayExecutionThread(KernelMode, FALSE, &Interval);
|
|
||||||
|
|
||||||
OldIrql = KfRaiseIrql(APC_LEVEL);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Look in the list if all IRPs for the specified file object
|
|
||||||
* are completed (or cancelled). If someone sends a new IRP
|
|
||||||
* for our file object while we're here we can happily loop
|
|
||||||
* forever.
|
|
||||||
*/
|
|
||||||
|
|
||||||
LIST_FOR_EACH(Irp, &Thread->IrpList, IRP, ThreadListEntry)
|
|
||||||
{
|
{
|
||||||
if (Irp->Tail.Overlay.OriginalFileObject == FileObject)
|
/* Do the wait */
|
||||||
{
|
KeDelayExecutionThread(KernelMode, FALSE, &Interval);
|
||||||
OurIrpsInList = TRUE;
|
OurIrpsInList = FALSE;
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
KfLowerIrql(OldIrql);
|
/* Raise IRQL */
|
||||||
|
OldIrql = KfRaiseIrql(APC_LEVEL);
|
||||||
|
|
||||||
|
/* Now loop the list again */
|
||||||
|
NextEntry = ListHead->Flink;
|
||||||
|
while (NextEntry != ListHead)
|
||||||
|
{
|
||||||
|
/* Get the IRP and check if the File Object matches */
|
||||||
|
Irp = CONTAINING_RECORD(NextEntry, IRP, ThreadListEntry);
|
||||||
|
if (Irp->Tail.Overlay.OriginalFileObject == FileObject)
|
||||||
|
{
|
||||||
|
/* Keep looping */
|
||||||
|
OurIrpsInList = TRUE;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Go to the next entry */
|
||||||
|
NextEntry = NextEntry->Flink;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Lower the IRQL */
|
||||||
|
KeLowerIrql(OldIrql);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Enter SEH for writing back the I/O Status */
|
||||||
_SEH_TRY
|
_SEH_TRY
|
||||||
{
|
{
|
||||||
|
/* Write success */
|
||||||
IoStatusBlock->Status = STATUS_SUCCESS;
|
IoStatusBlock->Status = STATUS_SUCCESS;
|
||||||
IoStatusBlock->Information = 0;
|
IoStatusBlock->Information = 0;
|
||||||
Status = STATUS_SUCCESS;
|
|
||||||
}
|
}
|
||||||
_SEH_HANDLE
|
_SEH_HANDLE
|
||||||
{
|
{
|
||||||
|
@ -2236,8 +2221,9 @@ NtCancelIoFile(IN HANDLE FileHandle,
|
||||||
}
|
}
|
||||||
_SEH_END;
|
_SEH_END;
|
||||||
|
|
||||||
|
/* Dereference the file object and return success */
|
||||||
ObDereferenceObject(FileObject);
|
ObDereferenceObject(FileObject);
|
||||||
return Status;
|
return STATUS_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -2255,33 +2241,16 @@ NtDeleteFile(IN POBJECT_ATTRIBUTES ObjectAttributes)
|
||||||
PAGED_CODE();
|
PAGED_CODE();
|
||||||
|
|
||||||
/* Setup the Open Packet */
|
/* Setup the Open Packet */
|
||||||
|
RtlZeroMemory(&OpenPacket, sizeof(OPEN_PACKET));
|
||||||
OpenPacket.Type = IO_TYPE_OPEN_PACKET;
|
OpenPacket.Type = IO_TYPE_OPEN_PACKET;
|
||||||
OpenPacket.Size = sizeof(OPEN_PACKET);
|
OpenPacket.Size = sizeof(OPEN_PACKET);
|
||||||
OpenPacket.FileObject = NULL;
|
|
||||||
OpenPacket.FinalStatus = STATUS_SUCCESS;
|
|
||||||
OpenPacket.Information = 0;
|
|
||||||
OpenPacket.ParseCheck = 0;
|
|
||||||
OpenPacket.RelatedFileObject = NULL;
|
|
||||||
OpenPacket.AllocationSize.QuadPart = 0;
|
|
||||||
OpenPacket.CreateOptions = FILE_DELETE_ON_CLOSE;
|
OpenPacket.CreateOptions = FILE_DELETE_ON_CLOSE;
|
||||||
OpenPacket.FileAttributes = 0;
|
|
||||||
OpenPacket.ShareAccess = FILE_SHARE_READ |
|
OpenPacket.ShareAccess = FILE_SHARE_READ |
|
||||||
FILE_SHARE_WRITE |
|
FILE_SHARE_WRITE |
|
||||||
FILE_SHARE_DELETE;
|
FILE_SHARE_DELETE;
|
||||||
OpenPacket.EaBuffer = NULL;
|
|
||||||
OpenPacket.EaLength = 0;
|
|
||||||
OpenPacket.Options = 0;
|
|
||||||
OpenPacket.Disposition = FILE_OPEN;
|
OpenPacket.Disposition = FILE_OPEN;
|
||||||
OpenPacket.BasicInformation = NULL;
|
|
||||||
OpenPacket.NetworkInformation = NULL;
|
|
||||||
OpenPacket.CreateFileType = 0;
|
|
||||||
OpenPacket.MailslotOrPipeParameters = NULL;
|
|
||||||
OpenPacket.Override = FALSE;
|
|
||||||
OpenPacket.QueryOnly = FALSE;
|
|
||||||
OpenPacket.DeleteOnly = TRUE;
|
OpenPacket.DeleteOnly = TRUE;
|
||||||
OpenPacket.FullAttributes = FALSE;
|
|
||||||
OpenPacket.DummyFileObject = &DummyFileObject;
|
OpenPacket.DummyFileObject = &DummyFileObject;
|
||||||
OpenPacket.InternalFlags = 0;
|
|
||||||
|
|
||||||
/* Update the operation counts */
|
/* Update the operation counts */
|
||||||
IopUpdateOperationCount(IopOtherTransfer);
|
IopUpdateOperationCount(IopOtherTransfer);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue