ReactOS 0.4.16-dev-197-g92996da
irp.c
Go to the documentation of this file.
1/*
2 * PROJECT: ReactOS Kernel
3 * LICENSE: GPL - See COPYING in the top level directory
4 * FILE: ntoskrnl/io/iomgr/irp.c
5 * PURPOSE: IRP Handling Functions
6 * PROGRAMMERS: Alex Ionescu (alex.ionescu@reactos.org)
7 * Gunnar Dalsnes
8 * Filip Navara (navaraf@reactos.org)
9 * Pierre Schweitzer (pierre@reactos.org)
10 */
11
12/* INCLUDES ****************************************************************/
13
14#include <ntoskrnl.h>
15#define NDEBUG
16#include <debug.h>
17
20
21/* PRIVATE FUNCTIONS ********************************************************/
22
23VOID
26 IN PKNORMAL_ROUTINE *NormalRoutine,
27 IN PVOID *NormalContext,
30{
31 /* Free the IRP */
32 IoFreeIrp(CONTAINING_RECORD(Apc, IRP, Tail.Apc));
33}
34
35VOID
38{
39 /* Free the IRP */
40 IoFreeIrp(CONTAINING_RECORD(Apc, IRP, Tail.Apc));
41}
42
46 IN PKEVENT EventObject OPTIONAL,
48{
49 PAGED_CODE();
50
51 /* Dereference the event */
52 if (EventObject) ObDereferenceObject(EventObject);
53
54 /* Free a buffer, if any */
56
57 /* If this was a file opened for synch I/O, then unlock it */
59
60 /* Now dereference it and return */
63}
64
65VOID
68 IN PIRP Irp)
69{
71 BOOLEAN CancelResult;
73 PAGED_CODE();
74
75 /* Raise IRQL to APC */
77
78 /* Check if nobody completed it yet */
79 if (!KeReadStateEvent(EventObject))
80 {
81 /* First, cancel it */
82 CancelResult = IoCancelIrp(Irp);
84
85 /* Check if we cancelled it */
86 if (CancelResult)
87 {
88 /* Wait for the IRP to be cancelled */
89 Wait.QuadPart = -100000;
90 while (!KeReadStateEvent(EventObject))
91 {
92 /* Delay indefintely */
94 }
95 }
96 else
97 {
98 /* No cancellation done, so wait for the I/O system to kill it */
99 KeWaitForSingleObject(EventObject,
100 Executive,
102 FALSE,
103 NULL);
104 }
105 }
106 else
107 {
108 /* We got preempted, so give up */
110 }
111}
112
113VOID
114NTAPI
116{
117 KIRQL OldIrql, LockIrql;
118 PETHREAD IrpThread;
119 PLIST_ENTRY IrpEntry;
120 PIO_ERROR_LOG_PACKET ErrorLogEntry;
122 PIO_STACK_LOCATION IoStackLocation;
123
124 /* First, raise to APC to protect IrpList */
126
127 /* Get the Thread and check the list */
128 IrpThread = PsGetCurrentThread();
129 if (IsListEmpty(&IrpThread->IrpList))
130 {
131 /* It got completed now, so quit */
133 return;
134 }
135
136 /* Ensure no one will come disturb */
138
139 /* Get the misbehaving IRP */
140 IrpEntry = IrpThread->IrpList.Flink;
141 IopDeadIrp = CONTAINING_RECORD(IrpEntry, IRP, ThreadListEntry);
143 "%s - Deassociating IRP %p for %p\n",
146 IrpThread);
147
148 /* Don't cancel the IRP if it's already been completed far */
149 if (IopDeadIrp->CurrentLocation == (IopDeadIrp->StackCount + 2))
150 {
151 /* Return */
154 return;
155 }
156
157 /* Disown the IRP! */
158 IopDeadIrp->Tail.Overlay.Thread = NULL;
159 RemoveHeadList(&IrpThread->IrpList);
160 InitializeListHead(&IopDeadIrp->ThreadListEntry);
161
162 /* Get the stack location and check if it's valid */
163 IoStackLocation = IoGetCurrentIrpStackLocation(IopDeadIrp);
164 if (IopDeadIrp->CurrentLocation <= IopDeadIrp->StackCount)
165 {
166 /* Get the device object */
167 DeviceObject = IoStackLocation->DeviceObject;
168 }
169
171 /* Lower IRQL now, since we have the pointers we need */
173
174 /* Check if we can send an Error Log Entry*/
175 if (DeviceObject)
176 {
177 /* Allocate an entry */
179 sizeof(IO_ERROR_LOG_PACKET));
180 if (ErrorLogEntry)
181 {
182 /* Write the entry */
183 ErrorLogEntry->ErrorCode = IO_DRIVER_CANCEL_TIMEOUT;
184 IoWriteErrorLogEntry(ErrorLogEntry);
185 }
186 }
187}
188
189VOID
190NTAPI
193{
194 PMDL Mdl;
196 "%s - Cleaning IRP %p for %p\n",
198 Irp,
199 FileObject);
200
201 /* Check if there's an MDL */
202 while ((Mdl = Irp->MdlAddress))
203 {
204 /* Clear all of them */
205 Irp->MdlAddress = Mdl->Next;
206 IoFreeMdl(Mdl);
207 }
208
209 /* Check if the IRP has system buffer */
210 if (Irp->Flags & IRP_DEALLOCATE_BUFFER)
211 {
212 /* Free the buffer */
213 ExFreePoolWithTag(Irp->AssociatedIrp.SystemBuffer, TAG_SYS_BUF);
214 }
215
216 /* Check if this IRP has a user event, a file object, and is async */
217 if ((Irp->UserEvent) &&
218 !(Irp->Flags & IRP_SYNCHRONOUS_API) &&
219 (FileObject))
220 {
221 /* Dereference the User Event */
222 ObDereferenceObject(Irp->UserEvent);
223 }
224
225 /* Check if we have a file object and this isn't a create operation */
226 if ((FileObject) && !(Irp->Flags & IRP_CREATE_OPERATION))
227 {
228 /* Dereference the file object */
230 }
231
232 /* Free the IRP */
233 IoFreeIrp(Irp);
234}
235
236VOID
237NTAPI
239 IN PKNORMAL_ROUTINE* NormalRoutine,
240 IN PVOID* NormalContext,
243{
245 PIRP Irp;
246 PMDL Mdl, NextMdl;
247 PVOID Port = NULL, Key = NULL;
248 BOOLEAN SignaledCreateRequest = FALSE;
249
250 /* Get data from the APC */
252 Irp = CONTAINING_RECORD(Apc, IRP, Tail.Apc);
254 "%s - Completing IRP %p for %p\n",
256 Irp,
257 FileObject);
258
259 /* Sanity check */
260 ASSERT(Irp->IoStatus.Status != (NTSTATUS)0xFFFFFFFF);
261
262 /* Check if we have a file object */
263 if (*SystemArgument2)
264 {
265 /* Check if we're reparsing */
266 if ((Irp->IoStatus.Status == STATUS_REPARSE) &&
267 (Irp->IoStatus.Information == IO_REPARSE_TAG_MOUNT_POINT))
268 {
269 PREPARSE_DATA_BUFFER ReparseData;
270
272
276
277 IopDoNameTransmogrify(Irp, FileObject, ReparseData);
278 }
279 }
280
281 /* Handle Buffered case first */
282 if (Irp->Flags & IRP_BUFFERED_IO)
283 {
284 /* Check if we have an input buffer and if we succeeded */
285 if ((Irp->Flags & IRP_INPUT_OPERATION) &&
286 (Irp->IoStatus.Status != STATUS_VERIFY_REQUIRED) &&
287 !(NT_ERROR(Irp->IoStatus.Status)))
288 {
290 {
291 /* Copy the buffer back to the user */
292 RtlCopyMemory(Irp->UserBuffer,
293 Irp->AssociatedIrp.SystemBuffer,
294 Irp->IoStatus.Information);
295 }
297 {
298 /* Fail the IRP */
299 Irp->IoStatus.Status = _SEH2_GetExceptionCode();
300 }
301 _SEH2_END;
302 }
303
304 /* Also check if we should de-allocate it */
305 if (Irp->Flags & IRP_DEALLOCATE_BUFFER)
306 {
307 /* Deallocate it */
308 ExFreePool(Irp->AssociatedIrp.SystemBuffer);
309 }
310 }
311
312 /* Now we got rid of these two... */
314
315 /* Check if there's an MDL */
316 for (Mdl = Irp->MdlAddress; Mdl; Mdl = NextMdl)
317 {
318 /* Free it */
319 NextMdl = Mdl->Next;
320 IoFreeMdl(Mdl);
321 }
322
323 /* No MDLs left */
324 Irp->MdlAddress = NULL;
325
326 /*
327 * Check if either the request was completed without any errors
328 * (but warnings are OK!), or if it was completed with an error, but
329 * did return from a pending I/O Operation and is not synchronous.
330 */
331 if (!NT_ERROR(Irp->IoStatus.Status) ||
332 (Irp->PendingReturned &&
334 {
335 /* Get any information we need from the FO before we kill it */
336 if ((FileObject) && (FileObject->CompletionContext))
337 {
338 /* Save Completion Data */
339 Port = FileObject->CompletionContext->Port;
340 Key = FileObject->CompletionContext->Key;
341 }
342
343 /* Check for UserIos */
344 if (Irp->UserIosb != NULL)
345 {
346 /* Use SEH to make sure we don't write somewhere invalid */
348 {
349 /* Save the IOSB Information */
350 *Irp->UserIosb = Irp->IoStatus;
351 }
353 {
354 /* Ignore any error */
355 }
356 _SEH2_END;
357 }
358
359 /* Check if we have an event or a file object */
360 if (Irp->UserEvent)
361 {
362 /* At the very least, this is a PKEVENT, so signal it always */
363 KeSetEvent(Irp->UserEvent, 0, FALSE);
364
365 /* Check if we also have a File Object */
366 if (FileObject)
367 {
368 /* Check if this is an Asynch API */
369 if (!(Irp->Flags & IRP_SYNCHRONOUS_API))
370 {
371 /* Dereference the event */
372 ObDereferenceObject(Irp->UserEvent);
373 }
374
375 /*
376 * Now, if this is a Synch I/O File Object, then this event is
377 * NOT an actual Executive Event, so we won't dereference it,
378 * and instead, we will signal the File Object
379 */
380 if ((FileObject->Flags & FO_SYNCHRONOUS_IO) &&
381 !(Irp->Flags & IRP_OB_QUERY_NAME))
382 {
383 /* Signal the file object and set the status */
384 KeSetEvent(&FileObject->Event, 0, FALSE);
385 FileObject->FinalStatus = Irp->IoStatus.Status;
386 }
387
388 /*
389 * This could also be a create operation, in which case we want
390 * to make sure there's no APC fired.
391 */
392 if (Irp->Flags & IRP_CREATE_OPERATION)
393 {
394 /* Clear the APC Routine and remember this */
395 Irp->Overlay.AsynchronousParameters.UserApcRoutine = NULL;
396 SignaledCreateRequest = TRUE;
397 }
398 }
399 }
400 else if (FileObject)
401 {
402 /* Signal the file object and set the status */
403 KeSetEvent(&FileObject->Event, 0, FALSE);
404 FileObject->FinalStatus = Irp->IoStatus.Status;
405
406 /*
407 * This could also be a create operation, in which case we want
408 * to make sure there's no APC fired.
409 */
410 if (Irp->Flags & IRP_CREATE_OPERATION)
411 {
412 /* Clear the APC Routine and remember this */
413 Irp->Overlay.AsynchronousParameters.UserApcRoutine = NULL;
414 SignaledCreateRequest = TRUE;
415 }
416 }
417
418 /* Update transfer count for everything but create operation */
419 if (!(Irp->Flags & IRP_CREATE_OPERATION))
420 {
421 if (Irp->Flags & IRP_WRITE_OPERATION)
422 {
423 /* Update write transfer count */
425 (ULONG)Irp->IoStatus.Information);
426 }
427 else if (Irp->Flags & IRP_READ_OPERATION)
428 {
429 /* Update read transfer count */
431 (ULONG)Irp->IoStatus.Information);
432 }
433 else
434 {
435 /* Update other transfer count */
437 (ULONG)Irp->IoStatus.Information);
438 }
439 }
440
441 /* Now that we've signaled the events, de-associate the IRP */
443
444 /* Now check if a User APC Routine was requested */
445 if (Irp->Overlay.AsynchronousParameters.UserApcRoutine)
446 {
447 /* Initialize it */
448 KeInitializeApc(&Irp->Tail.Apc,
454 Overlay.AsynchronousParameters.UserApcRoutine,
455 Irp->RequestorMode,
456 Irp->
457 Overlay.AsynchronousParameters.UserApcContext);
458
459 /* Queue it */
460 KeInsertQueueApc(&Irp->Tail.Apc, Irp->UserIosb, NULL, 2);
461 }
462 else if ((Port) &&
463 (Irp->Overlay.AsynchronousParameters.UserApcContext))
464 {
465 /* We have an I/O Completion setup... create the special Overlay */
466 Irp->Tail.CompletionKey = Key;
467 Irp->Tail.Overlay.PacketType = IopCompletionPacketIrp;
468 KeInsertQueue(Port, &Irp->Tail.Overlay.ListEntry);
469 }
470 else
471 {
472 /* Free the IRP since we don't need it anymore */
473 IoFreeIrp(Irp);
474 }
475
476 /* Check if we have a file object that wasn't part of a create */
477 if ((FileObject) && !(SignaledCreateRequest))
478 {
479 /* Dereference it, since it's not needed anymore either */
481 }
482 }
483 else
484 {
485 /*
486 * Either we didn't return from the request, or we did return but this
487 * request was synchronous.
488 */
489 if ((Irp->PendingReturned) && (FileObject))
490 {
491 /* So we did return with a synch operation, was it the IRP? */
492 if (Irp->Flags & IRP_SYNCHRONOUS_API)
493 {
494 /* Yes, this IRP was synchronous, so return the I/O Status */
495 *Irp->UserIosb = Irp->IoStatus;
496
497 /* Now check if the user gave an event */
498 if (Irp->UserEvent)
499 {
500 /* Signal it */
501 KeSetEvent(Irp->UserEvent, 0, FALSE);
502 }
503 else
504 {
505 /* No event was given, so signal the FO instead */
506 KeSetEvent(&FileObject->Event, 0, FALSE);
507 }
508 }
509 else
510 {
511 /*
512 * It's not the IRP that was synchronous, it was the FO
513 * that was opened this way. Signal its event.
514 */
515 FileObject->FinalStatus = Irp->IoStatus.Status;
516 KeSetEvent(&FileObject->Event, 0, FALSE);
517 }
518 }
519
520 /* Now that we got here, we do this for incomplete I/Os as well */
521 if ((FileObject) && !(Irp->Flags & IRP_CREATE_OPERATION))
522 {
523 /* Dereference the File Object unless this was a create */
525 }
526
527 /*
528 * Check if this was an Executive Event (remember that we know this
529 * by checking if the IRP is synchronous)
530 */
531 if ((Irp->UserEvent) &&
532 (FileObject) &&
533 !(Irp->Flags & IRP_SYNCHRONOUS_API))
534 {
535 /* This isn't a PKEVENT, so dereference it */
536 ObDereferenceObject(Irp->UserEvent);
537 }
538
539 /* Now that we've signaled the events, de-associate the IRP */
541
542 /* Free the IRP as well */
543 IoFreeIrp(Irp);
544 }
545}
546
548NTAPI
550{
551 /* Our allocated stack size */
552 ReserveIrpAllocator->StackSize = 20;
553
554 /* Allocate the IRP now */
555 ReserveIrpAllocator->ReserveIrp = IoAllocateIrp(ReserveIrpAllocator->StackSize, FALSE);
556 /* If we cannot, abort system boot */
557 if (ReserveIrpAllocator->ReserveIrp == NULL)
558 {
559 return FALSE;
560 }
561
562 /* It's not in use */
563 ReserveIrpAllocator->ReserveIrpInUse = 0;
564 /* And init the event */
565 KeInitializeEvent(&ReserveIrpAllocator->WaitEvent, SynchronizationEvent, FALSE);
566
567 /* All good, keep booting */
568 return TRUE;
569}
570
571PIRP
572NTAPI
574{
575 /* If we need a stack size higher than what was allocated, then fail */
577 {
578 return NULL;
579 }
580
581 /* Now, wait until the IRP becomes available and reserve it immediately */
583 {
585 Executive,
587 FALSE,
588 NULL);
589 }
590
591 /* It's ours! Initialize it */
593
594 /* And return it to the caller */
596}
597
598VOID
600{
601 /* Mark we don't use the IRP anymore */
603
604 /* And set the event if someone is waiting on the IRP */
606}
607
608/* FUNCTIONS *****************************************************************/
609
610/*
611 * @implemented
612 */
613PIRP
614NTAPI
617{
618 PIRP Irp = NULL;
620 PKPRCB Prcb;
621 UCHAR Flags = 0;
624
625 /* Set Charge Quota Flag */
627
628 /* Get the PRCB */
629 Prcb = KeGetCurrentPrcb();
630
631 /* Figure out which Lookaside List to use */
632 if ((StackSize <= 8) && (ChargeQuota == FALSE || Prcb->LookasideIrpFloat > 0))
633 {
634 /* Set Fixed Size Flag */
636
637 /* See if we should use big list */
638 if (StackSize != 1)
639 {
640 Size = IoSizeOfIrp(8);
641 ListType = LookasideLargeIrpList;
642 }
643
644 /* Get the P List First */
645 List = (PNPAGED_LOOKASIDE_LIST)Prcb->PPLookasideList[ListType].P;
646
647 /* Attempt allocation */
648 List->L.TotalAllocates++;
649 Irp = (PIRP)InterlockedPopEntrySList(&List->L.ListHead);
650
651 /* Check if the P List failed */
652 if (!Irp)
653 {
654 /* Let the balancer know */
655 List->L.AllocateMisses++;
656
657 /* Try the L List */
658 List = (PNPAGED_LOOKASIDE_LIST)Prcb->PPLookasideList[ListType].L;
659 List->L.TotalAllocates++;
660 Irp = (PIRP)InterlockedPopEntrySList(&List->L.ListHead);
661 }
662 }
663
664 /* Check if we have to use the pool */
665 if (!Irp)
666 {
667 /* Did we try lookaside and fail? */
668 if (Flags & IRP_ALLOCATED_FIXED_SIZE) List->L.AllocateMisses++;
669
670 /* Check if we should charge quota */
671 if (ChargeQuota)
672 {
674 Size,
675 TAG_IRP);
676 }
677 else
678 {
679 /* Allocate the IRP with no quota charge */
681 }
682
683 /* Make sure it was sucessful */
684 if (!Irp) return NULL;
685 }
686 else if (Flags & IRP_QUOTA_CHARGED)
687 {
688 /* Decrement lookaside float */
691
692 /* In this case there is no charge quota */
693 Flags &= ~IRP_QUOTA_CHARGED;
694 }
695
696 /* Now Initialize it */
698
699 /* Set the Allocation Flags */
700 Irp->AllocationFlags = Flags;
701
702 /* Return it */
704 "%s - Allocated IRP %p with allocation flags %lx\n",
706 Irp,
707 Flags);
708 return Irp;
709}
710
711/*
712 * @implemented
713 */
714PIRP
715NTAPI
717{
718 LONG i;
719 PIRP Irp;
721
722 /* Try to get an IRP */
724 if (Irp)
725 return Irp;
726
727 /* If we fail, start looping till we may get one */
728 i = LONG_MAX;
729 do {
730 i--;
731
732 /* First, sleep for 10ms */
733 Sleep.QuadPart = -10 * 1000 * 10;
735
736 /* Then, retry allocation */
738 if (Irp)
739 return Irp;
740 } while (i > 0);
741
742 return Irp;
743}
744
745/*
746 * @implemented
747 */
748PIRP
749NTAPI
756{
757 PIRP Irp;
758 PIO_STACK_LOCATION StackPtr;
759
760 /* Allocate IRP */
761 Irp = IoAllocateIrp(DeviceObject->StackSize, FALSE);
762 if (!Irp) return NULL;
763
764 /* Get the Stack */
765 StackPtr = IoGetNextIrpStackLocation(Irp);
766
767 /* Write the Major function and then deal with it */
768 StackPtr->MajorFunction = (UCHAR)MajorFunction;
769
770 /* Do not handle the following here */
775 {
776 /* Check if this is Buffered IO */
777 if (DeviceObject->Flags & DO_BUFFERED_IO)
778 {
779 /* Allocate the System Buffer */
780 Irp->AssociatedIrp.SystemBuffer =
782 if (!Irp->AssociatedIrp.SystemBuffer)
783 {
784 /* Free the IRP and fail */
785 IoFreeIrp(Irp);
786 return NULL;
787 }
788
789 /* Set flags */
791
792 /* Handle special IRP_MJ_WRITE Case */
794 {
795 /* Copy the buffer data */
796 RtlCopyMemory(Irp->AssociatedIrp.SystemBuffer, Buffer, Length);
797 }
798 else
799 {
800 /* Set the Input Operation flag and set this as a User Buffer */
801 Irp->Flags |= IRP_INPUT_OPERATION;
802 Irp->UserBuffer = Buffer;
803 }
804 }
805 else if (DeviceObject->Flags & DO_DIRECT_IO)
806 {
807 /* Use an MDL for Direct I/O */
808 Irp->MdlAddress = IoAllocateMdl(Buffer,
809 Length,
810 FALSE,
811 FALSE,
812 NULL);
813 if (!Irp->MdlAddress)
814 {
815 /* Free the IRP and fail */
816 IoFreeIrp(Irp);
817 return NULL;
818 }
819
820 /* Probe and Lock */
822 {
823 /* Do the probe */
824 MmProbeAndLockPages(Irp->MdlAddress,
828 }
830 {
831 /* Free the IRP and its MDL */
832 IoFreeMdl(Irp->MdlAddress);
833 IoFreeIrp(Irp);
834
835 /* Fail */
836 _SEH2_YIELD(return NULL);
837 }
838 _SEH2_END;
839 }
840 else
841 {
842 /* Neither, use the buffer */
843 Irp->UserBuffer = Buffer;
844 }
845
846 /* Check if this is a read */
848 {
849 /* Set the parameters for a read */
850 StackPtr->Parameters.Read.Length = Length;
851 StackPtr->Parameters.Read.ByteOffset = *StartingOffset;
852 }
853 else if (MajorFunction == IRP_MJ_WRITE)
854 {
855 /* Otherwise, set write parameters */
856 StackPtr->Parameters.Write.Length = Length;
857 StackPtr->Parameters.Write.ByteOffset = *StartingOffset;
858 }
859 }
860
861 /* Set the Current Thread and IOSB */
862 Irp->UserIosb = IoStatusBlock;
863 Irp->Tail.Overlay.Thread = PsGetCurrentThread();
864
865 /* Return the IRP */
867 "%s - Built IRP %p with Major, Buffer, DO %lx %p %p\n",
869 Irp,
871 Buffer,
873 return Irp;
874}
875
876/*
877 * @implemented
878 */
879PIRP
880NTAPI
890{
891 PIRP Irp;
892 PIO_STACK_LOCATION StackPtr;
894
895 /* Allocate IRP */
896 Irp = IoAllocateIrp(DeviceObject->StackSize, FALSE);
897 if (!Irp) return NULL;
898
899 /* Get the Stack */
900 StackPtr = IoGetNextIrpStackLocation(Irp);
901
902 /* Set the DevCtl Type */
906
907 /* Set the IOCTL Data */
908 StackPtr->Parameters.DeviceIoControl.IoControlCode = IoControlCode;
909 StackPtr->Parameters.DeviceIoControl.InputBufferLength = InputBufferLength;
910 StackPtr->Parameters.DeviceIoControl.OutputBufferLength =
912
913 /* Handle the Methods */
915 {
916 /* Buffered I/O */
917 case METHOD_BUFFERED:
918
919 /* Select the right Buffer Length */
922
923 /* Make sure there is one */
924 if (BufferLength)
925 {
926 /* Allocate the System Buffer */
927 Irp->AssociatedIrp.SystemBuffer =
931 if (!Irp->AssociatedIrp.SystemBuffer)
932 {
933 /* Free the IRP and fail */
934 IoFreeIrp(Irp);
935 return NULL;
936 }
937
938 /* Check if we got a buffer */
939 if (InputBuffer)
940 {
941 /* Copy into the System Buffer */
942 RtlCopyMemory(Irp->AssociatedIrp.SystemBuffer,
945 }
946
947 /* Write the flags */
949 if (OutputBuffer) Irp->Flags |= IRP_INPUT_OPERATION;
950
951 /* Save the Buffer */
952 Irp->UserBuffer = OutputBuffer;
953 }
954 else
955 {
956 /* Clear the Flags and Buffer */
957 Irp->Flags = 0;
958 Irp->UserBuffer = NULL;
959 }
960 break;
961
962 /* Direct I/O */
963 case METHOD_IN_DIRECT:
965
966 /* Check if we got an input buffer */
967 if (InputBuffer)
968 {
969 /* Allocate the System Buffer */
970 Irp->AssociatedIrp.SystemBuffer =
974 if (!Irp->AssociatedIrp.SystemBuffer)
975 {
976 /* Free the IRP and fail */
977 IoFreeIrp(Irp);
978 return NULL;
979 }
980
981 /* Copy into the System Buffer */
982 RtlCopyMemory(Irp->AssociatedIrp.SystemBuffer,
985
986 /* Write the flags */
988 }
989 else
990 {
991 /* Clear the flags */
992 Irp->Flags = 0;
993 }
994
995 /* Check if we got an output buffer */
996 if (OutputBuffer)
997 {
998 /* Allocate the System Buffer */
999 Irp->MdlAddress = IoAllocateMdl(OutputBuffer,
1001 FALSE,
1002 FALSE,
1003 Irp);
1004 if (!Irp->MdlAddress)
1005 {
1006 /* Free the IRP and fail */
1007 IoFreeIrp(Irp);
1008 return NULL;
1009 }
1010
1011 /* Probe and Lock */
1012 _SEH2_TRY
1013 {
1014 /* Do the probe */
1015 MmProbeAndLockPages(Irp->MdlAddress,
1016 KernelMode,
1020 }
1022 {
1023 /* Free the MDL */
1024 IoFreeMdl(Irp->MdlAddress);
1025
1026 /* Free the input buffer and IRP */
1027 if (InputBuffer) ExFreePool(Irp->AssociatedIrp.SystemBuffer);
1028 IoFreeIrp(Irp);
1029
1030 /* Fail */
1031 _SEH2_YIELD(return NULL);
1032 }
1033 _SEH2_END;
1034 }
1035 break;
1036
1037 case METHOD_NEITHER:
1038
1039 /* Just save the Buffer */
1040 Irp->UserBuffer = OutputBuffer;
1041 StackPtr->Parameters.DeviceIoControl.Type3InputBuffer = InputBuffer;
1042 }
1043
1044 /* Now write the Event and IoSB */
1045 Irp->UserIosb = IoStatusBlock;
1046 Irp->UserEvent = Event;
1047
1048 /* Sync IRPs are queued to requestor thread's irp cancel/cleanup list */
1049 Irp->Tail.Overlay.Thread = PsGetCurrentThread();
1051
1052 /* Return the IRP */
1054 "%s - Built IRP %p with IOCTL, Buffers, DO %lx %p %p %p\n",
1056 Irp,
1060 DeviceObject);
1061 return Irp;
1062}
1063
1064/*
1065 * @implemented
1066 */
1067PIRP
1068NTAPI
1071 IN PVOID Buffer,
1072 IN ULONG Length,
1076{
1077 PIRP Irp;
1078
1079 /* Do the big work to set up the IRP */
1082 Buffer,
1083 Length,
1085 IoStatusBlock );
1086 if (!Irp) return NULL;
1087
1088 /* Set the Event which makes it Syncronous */
1089 Irp->UserEvent = Event;
1090
1091 /* Sync IRPs are queued to requestor thread's irp cancel/cleanup list */
1093 return Irp;
1094}
1095
1096/*
1097 * @implemented
1098 */
1099BOOLEAN
1100NTAPI
1102{
1103 KIRQL OldIrql;
1106 "%s - Canceling IRP %p\n",
1108 Irp);
1109 ASSERT(Irp->Type == IO_TYPE_IRP);
1110
1111 /* Acquire the cancel lock and cancel the IRP */
1113 Irp->Cancel = TRUE;
1114
1115 /* Clear the cancel routine and get the old one */
1117 if (CancelRoutine)
1118 {
1119 /* We had a routine, make sure the IRP isn't completed */
1120 if (Irp->CurrentLocation > (Irp->StackCount + 1))
1121 {
1122 /* It is, bugcheck */
1123 KeBugCheckEx(CANCEL_STATE_IN_COMPLETED_IRP,
1124 (ULONG_PTR)Irp,
1126 0,
1127 0);
1128 }
1129
1130 /* Set the cancel IRQL And call the routine */
1131 Irp->CancelIrql = OldIrql;
1133 return TRUE;
1134 }
1135
1136 /* Otherwise, release the cancel lock and fail */
1138 return FALSE;
1139}
1140
1141/*
1142 * @implemented
1143 */
1144VOID
1145NTAPI
1147{
1148 KIRQL OldIrql;
1149 ULONG Retries = 3000;
1151 PLIST_ENTRY ListHead, NextEntry;
1152 PIRP Irp;
1153 PAGED_CODE();
1154
1155 /* Windows isn't using given thread, but using current. */
1157
1159 "%s - Canceling IRPs for Thread %p\n",
1161 Thread);
1162
1163 /* Raise to APC to protect the IrpList */
1165
1166 /* Start by cancelling all the IRPs in the current thread queue. */
1167 ListHead = &Thread->IrpList;
1168 NextEntry = ListHead->Flink;
1169 while (ListHead != NextEntry)
1170 {
1171 /* Get the IRP */
1172 Irp = CONTAINING_RECORD(NextEntry, IRP, ThreadListEntry);
1173
1174 /* Cancel it */
1176
1177 /* Move to the next entry */
1178 NextEntry = NextEntry->Flink;
1179 }
1180
1181 /* Wait 100 milliseconds */
1182 Interval.QuadPart = -1000000;
1183
1184 /* Wait till all the IRPs are completed or cancelled. */
1185 while (!IsListEmpty(&Thread->IrpList))
1186 {
1187 /* Now we can lower */
1189
1190 /* Wait a short while and then look if all our IRPs were completed. */
1192
1193 /*
1194 * Don't stay here forever if some broken driver doesn't complete
1195 * the IRP.
1196 */
1197 if (!(Retries--))
1198 {
1199 /* Print out a message and remove the IRP */
1200 DPRINT1("Broken driver did not complete!\n");
1202 }
1203
1204 /* Raise the IRQL Again */
1206 }
1207
1208 /* We're done, lower the IRQL */
1210}
1211
1212/*
1213 * @implemented
1214 */
1215#undef IoCallDriver
1217NTAPI
1219 IN PIRP Irp)
1220{
1221 /* Call fastcall */
1223}
1224
1225#define IoCallDriver IofCallDriver
1226
1227/*
1228 * @implemented
1229 */
1230#undef IoCompleteRequest
1231VOID
1232NTAPI
1235{
1236 /* Call the fastcall */
1238}
1239
1240#define IoCompleteRequest IofCompleteRequest
1241
1242/*
1243 * @implemented
1244 */
1245VOID
1246NTAPI
1248{
1249 /* This is the same as calling IoQueueThreadIrp */
1251}
1252
1253/*
1254 * @implemented
1255 */
1259 IN PIRP Irp)
1260{
1262 PIO_STACK_LOCATION StackPtr;
1263
1264 /* Make sure this is a valid IRP */
1265 ASSERT(Irp->Type == IO_TYPE_IRP);
1266
1267 /* Get the Driver Object */
1268 DriverObject = DeviceObject->DriverObject;
1269
1270 /* Decrease the current location and check if */
1271 Irp->CurrentLocation--;
1272 if (Irp->CurrentLocation <= 0)
1273 {
1274 /* This IRP ran out of stack, bugcheck */
1275 KeBugCheckEx(NO_MORE_IRP_STACK_LOCATIONS, (ULONG_PTR)Irp, 0, 0, 0);
1276 }
1277
1278 /* Now update the stack location */
1279 StackPtr = IoGetNextIrpStackLocation(Irp);
1280 Irp->Tail.Overlay.CurrentStackLocation = StackPtr;
1281
1282 /* Get the Device Object */
1283 StackPtr->DeviceObject = DeviceObject;
1284
1285 /* Call it */
1286 return DriverObject->MajorFunction[StackPtr->MajorFunction](DeviceObject,
1287 Irp);
1288}
1289
1291VOID
1293{
1294 IoStackLocation->MinorFunction = 0;
1295 IoStackLocation->Flags = 0;
1296 IoStackLocation->Control &= SL_ERROR_RETURNED;
1297 IoStackLocation->Parameters.Others.Argument1 = 0;
1298 IoStackLocation->Parameters.Others.Argument2 = 0;
1299 IoStackLocation->Parameters.Others.Argument3 = 0;
1300 IoStackLocation->FileObject = NULL;
1301}
1302
1303/*
1304 * @implemented
1305 */
1306VOID
1310{
1311 PIO_STACK_LOCATION StackPtr, LastStackPtr;
1316 PMDL Mdl, NextMdl;
1317 ULONG MasterCount;
1318 PIRP MasterIrp;
1319 ULONG Flags;
1321 PREPARSE_DATA_BUFFER DataBuffer = NULL;
1323 "%s - Completing IRP %p\n",
1325 Irp);
1326
1327 /* Make sure this IRP isn't getting completed twice or is invalid */
1328 if ((Irp->CurrentLocation) > (Irp->StackCount + 1))
1329 {
1330 /* Bugcheck */
1331 KeBugCheckEx(MULTIPLE_IRP_COMPLETE_REQUESTS, (ULONG_PTR)Irp, 0, 0, 0);
1332 }
1333
1334 /* Some sanity checks */
1335 ASSERT(Irp->Type == IO_TYPE_IRP);
1336 ASSERT(!Irp->CancelRoutine);
1337 ASSERT(Irp->IoStatus.Status != STATUS_PENDING);
1338 ASSERT(Irp->IoStatus.Status != (NTSTATUS)0xFFFFFFFF);
1339
1340 /* Get the last stack */
1341 LastStackPtr = (PIO_STACK_LOCATION)(Irp + 1);
1342 if (LastStackPtr->Control & SL_ERROR_RETURNED)
1343 {
1344 /* Get the error code */
1345 ErrorCode = PtrToUlong(LastStackPtr->Parameters.Others.Argument4);
1346 }
1347
1348 /*
1349 * Start the loop with the current stack and point the IRP to the next stack
1350 * and then keep incrementing the stack as we loop through. The IRP should
1351 * always point to the next stack location w.r.t the one currently being
1352 * analyzed, so completion routine code will see the appropriate value.
1353 * Because of this, we must loop until the current stack location is +1 of
1354 * the stack count, because when StackPtr is at the end, CurrentLocation is +1.
1355 */
1356 for (StackPtr = IoGetCurrentIrpStackLocation(Irp),
1357 Irp->CurrentLocation++,
1358 Irp->Tail.Overlay.CurrentStackLocation++;
1359 Irp->CurrentLocation <= (Irp->StackCount + 1);
1360 StackPtr++,
1361 Irp->CurrentLocation++,
1362 Irp->Tail.Overlay.CurrentStackLocation++)
1363 {
1364 /* Set Pending Returned */
1365 Irp->PendingReturned = StackPtr->Control & SL_PENDING_RETURNED;
1366
1367 /* Check if we failed */
1368 if (!NT_SUCCESS(Irp->IoStatus.Status))
1369 {
1370 /* Check if it was changed by a completion routine */
1371 if (Irp->IoStatus.Status != ErrorCode)
1372 {
1373 /* Update the error for the current stack */
1374 ErrorCode = Irp->IoStatus.Status;
1375 StackPtr->Control |= SL_ERROR_RETURNED;
1376 LastStackPtr->Parameters.Others.Argument4 = UlongToPtr(ErrorCode);
1377 LastStackPtr->Control |= SL_ERROR_RETURNED;
1378 }
1379 }
1380
1381 /* Check if there is a Completion Routine to Call */
1382 if ((NT_SUCCESS(Irp->IoStatus.Status) &&
1383 (StackPtr->Control & SL_INVOKE_ON_SUCCESS)) ||
1384 (!NT_SUCCESS(Irp->IoStatus.Status) &&
1385 (StackPtr->Control & SL_INVOKE_ON_ERROR)) ||
1386 (Irp->Cancel &&
1387 (StackPtr->Control & SL_INVOKE_ON_CANCEL)))
1388 {
1389 /* Clear the stack location */
1390 IopClearStackLocation(StackPtr);
1391
1392 /* Check for highest-level device completion routines */
1393 if (Irp->CurrentLocation == (Irp->StackCount + 1))
1394 {
1395 /* Clear the DO, since the current stack location is invalid */
1397 }
1398 else
1399 {
1400 /* Otherwise, return the real one */
1402 }
1403
1404 /* Call the completion routine */
1406 Irp,
1407 StackPtr->Context);
1408
1409 /* Don't touch the Packet in this case, since it might be gone! */
1411 }
1412 else
1413 {
1414 /* Otherwise, check if this is a completed IRP */
1415 if ((Irp->CurrentLocation <= Irp->StackCount) &&
1416 (Irp->PendingReturned))
1417 {
1418 /* Mark it as pending */
1420 }
1421
1422 /* Clear the stack location */
1423 IopClearStackLocation(StackPtr);
1424 }
1425 }
1426
1427 /* Check if the IRP is an associated IRP */
1428 if (Irp->Flags & IRP_ASSOCIATED_IRP)
1429 {
1430 /* Get the master IRP and count */
1431 MasterIrp = Irp->AssociatedIrp.MasterIrp;
1432 MasterCount = InterlockedDecrement(&MasterIrp->AssociatedIrp.IrpCount);
1433
1434 /* Free the MDLs */
1435 for (Mdl = Irp->MdlAddress; Mdl; Mdl = NextMdl)
1436 {
1437 /* Go to the next one */
1438 NextMdl = Mdl->Next;
1439 IoFreeMdl(Mdl);
1440 }
1441
1442 /* Free the IRP itself */
1443 IoFreeIrp(Irp);
1444
1445 /* Complete the Master IRP */
1446 if (!MasterCount) IofCompleteRequest(MasterIrp, PriorityBoost);
1447 return;
1448 }
1449
1450 /* Check whether we have to reparse */
1451 if (Irp->IoStatus.Status == STATUS_REPARSE)
1452 {
1453 if (Irp->IoStatus.Information > IO_REMOUNT)
1454 {
1455 /* If that's a reparse tag we understand, save the buffer from deletion */
1456 if (Irp->IoStatus.Information == IO_REPARSE_TAG_MOUNT_POINT)
1457 {
1458 ASSERT(Irp->Tail.Overlay.AuxiliaryBuffer != NULL);
1459 DataBuffer = (PREPARSE_DATA_BUFFER)Irp->Tail.Overlay.AuxiliaryBuffer;
1460 Irp->Tail.Overlay.AuxiliaryBuffer = NULL;
1461 }
1462 else
1463 {
1464 Irp->IoStatus.Status = STATUS_IO_REPARSE_TAG_NOT_HANDLED;
1465 }
1466 }
1467 }
1468
1469 /* Check if we have an auxiliary buffer */
1470 if (Irp->Tail.Overlay.AuxiliaryBuffer)
1471 {
1472 /* Free it */
1473 ExFreePool(Irp->Tail.Overlay.AuxiliaryBuffer);
1474 Irp->Tail.Overlay.AuxiliaryBuffer = NULL;
1475 }
1476
1477 /* Check if this is a Paging I/O or Close Operation */
1478 if (Irp->Flags & (IRP_PAGING_IO | IRP_CLOSE_OPERATION))
1479 {
1480 /* Handle a Close Operation or Sync Paging I/O */
1482 {
1483 /* Set the I/O Status and Signal the Event */
1485 *Irp->UserIosb = Irp->IoStatus;
1486 KeSetEvent(Irp->UserEvent, PriorityBoost, FALSE);
1487
1488 /* Free the IRP for a Paging I/O Only, Close is handled by us */
1489 if (Flags)
1490 {
1491 /* If we were using the reserve IRP, then call the appropriate
1492 * free function (to make the IRP available again)
1493 */
1495 {
1497 }
1498 /* Otherwise, free for real! */
1499 else
1500 {
1501 IoFreeIrp(Irp);
1502 }
1503 }
1504 }
1505 else
1506 {
1507#if 0
1508 /* Page 166 */
1509 KeInitializeApc(&Irp->Tail.Apc
1510 &Irp->Tail.Overlay.Thread->Tcb,
1511 Irp->ApcEnvironment,
1512 IopCompletePageWrite,
1513 NULL,
1514 NULL,
1515 KernelMode,
1516 NULL);
1517 KeInsertQueueApc(&Irp->Tail.Apc,
1518 NULL,
1519 NULL,
1521#else
1522 /* Not implemented yet. */
1523 UNIMPLEMENTED_DBGBREAK("Not supported!\n");
1524#endif
1525 }
1526
1527 /* Get out of here */
1528 return;
1529 }
1530
1531 /* Unlock MDL Pages, page 167. */
1532 Mdl = Irp->MdlAddress;
1533 while (Mdl)
1534 {
1536 Mdl = Mdl->Next;
1537 }
1538
1539 /* Check if we should exit because of a Deferred I/O (page 168) */
1540 if ((Irp->Flags & IRP_DEFER_IO_COMPLETION) && !(Irp->PendingReturned))
1541 {
1542 /* Restore the saved reparse buffer for the caller */
1543 if (Irp->IoStatus.Status == STATUS_REPARSE &&
1544 Irp->IoStatus.Information == IO_REPARSE_TAG_MOUNT_POINT)
1545 {
1546 Irp->Tail.Overlay.AuxiliaryBuffer = (PCHAR)DataBuffer;
1547 }
1548
1549 /*
1550 * Return without queuing the completion APC, since the caller will
1551 * take care of doing its own optimized completion at PASSIVE_LEVEL.
1552 */
1553 return;
1554 }
1555
1556 /* Get the thread and file object */
1557 Thread = Irp->Tail.Overlay.Thread;
1558 FileObject = Irp->Tail.Overlay.OriginalFileObject;
1559
1560 /* Make sure the IRP isn't canceled */
1561 if (!Irp->Cancel)
1562 {
1563 /* Initialize the APC */
1564 KeInitializeApc(&Irp->Tail.Apc,
1565 &Thread->Tcb,
1566 Irp->ApcEnvironment,
1568 NULL,
1569 NULL,
1570 KernelMode,
1571 NULL);
1572
1573 /* Queue it */
1574 KeInsertQueueApc(&Irp->Tail.Apc,
1575 FileObject,
1576 DataBuffer,
1578 }
1579 else
1580 {
1581 /* The IRP just got canceled... does a thread still own it? */
1582 if (Thread)
1583 {
1584 /* Yes! There is still hope! Initialize the APC */
1585 KeInitializeApc(&Irp->Tail.Apc,
1586 &Thread->Tcb,
1587 Irp->ApcEnvironment,
1589 NULL,
1590 NULL,
1591 KernelMode,
1592 NULL);
1593
1594 /* Queue it */
1595 KeInsertQueueApc(&Irp->Tail.Apc,
1596 FileObject,
1597 DataBuffer,
1599 }
1600 else
1601 {
1602 /* Nothing left for us to do, kill it */
1603 ASSERT(Irp->Cancel);
1605 }
1606 }
1607}
1608
1610NTAPI
1612 IN PIRP Irp,
1614{
1615 if (Irp->PendingReturned)
1618}
1619
1620/*
1621 * @implemented
1622 */
1623BOOLEAN
1624NTAPI
1626 IN PIRP Irp)
1627{
1628 KEVENT Event;
1630
1631 /* Check if next stack location is available */
1632 if (Irp->CurrentLocation > Irp->StackCount || Irp->CurrentLocation <= 1)
1633 {
1634 /* No more stack location */
1635 return FALSE;
1636 }
1637
1638 /* Initialize event */
1640
1641 /* Copy stack location for next driver */
1643
1644 /* Set a completion routine, which will signal the event */
1646
1647 /* Call next driver */
1649
1650 /* Check if irp is pending */
1651 if (Status == STATUS_PENDING)
1652 {
1653 /* Yes, wait for its completion */
1655 }
1656
1657 /* Return success */
1658 return TRUE;
1659}
1660
1661/*
1662 * @implemented
1663 */
1664VOID
1665NTAPI
1667{
1670 PKPRCB Prcb;
1672 "%s - Freeing IRPs %p\n",
1674 Irp);
1675
1676 /* Make sure the Thread IRP list is empty and that it OK to free it */
1677 ASSERT(Irp->Type == IO_TYPE_IRP);
1678 ASSERT(IsListEmpty(&Irp->ThreadListEntry));
1679 ASSERT(Irp->CurrentLocation >= Irp->StackCount);
1680
1681 /* Get the PRCB */
1682 Prcb = KeGetCurrentPrcb();
1683
1684 /* If this was a lookaside alloc, increment lookaside float */
1685 if (Irp->AllocationFlags & IRP_LOOKASIDE_ALLOCATION)
1686 {
1687 Irp->AllocationFlags &= ~IRP_LOOKASIDE_ALLOCATION;
1689 }
1690
1691 /* If this was a pool alloc, free it with the pool */
1692 if (!(Irp->AllocationFlags & IRP_ALLOCATED_FIXED_SIZE))
1693 {
1694 /* Free it */
1696 }
1697 else
1698 {
1699 /* Check if this was a Big IRP */
1700 if (Irp->StackCount != 1) ListType = LookasideLargeIrpList;
1701
1702 /* Use the P List */
1703 List = (PNPAGED_LOOKASIDE_LIST)Prcb->PPLookasideList[ListType].P;
1704 List->L.TotalFrees++;
1705
1706 /* Check if the Free was within the Depth or not */
1707 if (ExQueryDepthSList(&List->L.ListHead) >= List->L.Depth)
1708 {
1709 /* Let the balancer know */
1710 List->L.FreeMisses++;
1711
1712 /* Use the L List */
1713 List = (PNPAGED_LOOKASIDE_LIST)Prcb->PPLookasideList[ListType].L;
1714 List->L.TotalFrees++;
1715
1716 /* Check if the Free was within the Depth or not */
1717 if (ExQueryDepthSList(&List->L.ListHead) >= List->L.Depth)
1718 {
1719 /* All lists failed, use the pool */
1720 List->L.FreeMisses++;
1722 Irp = NULL;
1723 }
1724 }
1725
1726 /* The free was within the Depth */
1727 if (Irp)
1728 {
1729 /* Remove the association with the process */
1730 if (Irp->AllocationFlags & IRP_QUOTA_CHARGED)
1731 {
1733 Irp->AllocationFlags &= ~IRP_QUOTA_CHARGED;
1734 }
1735
1736 /* Add it to the lookaside list */
1737 InterlockedPushEntrySList(&List->L.ListHead,
1738 (PSLIST_ENTRY)Irp);
1739 }
1740 }
1741}
1742
1743/*
1744 * @implemented
1745 */
1749{
1751 ULONG Flags;
1752
1753 /* Get the flags */
1754 Flags = Irp->Flags;
1755
1756 /* Check what priority it has */
1758 {
1759 /* High priority */
1761 }
1762 else if (Flags & IRP_PAGING_IO)
1763 {
1764 /* Normal priority */
1766 }
1767 else
1768 {
1769 /* Invalid -- not a paging IRP */
1771 }
1772
1773 /* Return the priority */
1774 return Priority;
1775}
1776
1777/*
1778 * @implemented
1779 */
1781NTAPI
1783{
1784 /* Return the requestor process */
1785 if (Irp->Tail.Overlay.Thread)
1786 {
1787 if (Irp->ApcEnvironment == OriginalApcEnvironment)
1788 {
1789 return Irp->Tail.Overlay.Thread->ThreadsProcess;
1790 }
1791 else if (Irp->ApcEnvironment == AttachedApcEnvironment)
1792 {
1793 return (PEPROCESS)Irp->Tail.Overlay.Thread->Tcb.ApcState.Process;
1794 }
1795 }
1796
1797 return NULL;
1798}
1799
1800/*
1801 * @implemented
1802 */
1803ULONG
1804NTAPI
1806{
1808
1809 /* Return the requestor process' id */
1811 if (Process) return PtrToUlong(Process->UniqueProcessId);
1812
1813 return 0;
1814}
1815
1816/*
1817 * @implemented
1818 */
1820NTAPI
1822 OUT PULONG pSessionId)
1823{
1825
1826 /* Return the session */
1827 if (Irp->Tail.Overlay.Thread)
1828 {
1829 Process = Irp->Tail.Overlay.Thread->ThreadsProcess;
1830 *pSessionId = MmGetSessionId(Process);
1831 return STATUS_SUCCESS;
1832 }
1833
1834 *pSessionId = (ULONG)-1;
1835 return STATUS_UNSUCCESSFUL;
1836}
1837
1838/*
1839 * @implemented
1840 */
1841PIRP
1842NTAPI
1844{
1845 /* Return the IRP */
1846 return (PIRP)PsGetCurrentThread()->TopLevelIrp;
1847}
1848
1849/*
1850 * @implemented
1851 */
1852VOID
1853NTAPI
1857{
1858 /* Clear it */
1860 "%s - Initializing IRP %p\n",
1862 Irp);
1864
1865 /* Set the Header and other data */
1866 Irp->Type = IO_TYPE_IRP;
1867 Irp->Size = PacketSize;
1868 Irp->StackCount = StackSize;
1869 Irp->CurrentLocation = StackSize + 1;
1870 Irp->ApcEnvironment = KeGetCurrentThread()->ApcStateIndex;
1871 Irp->Tail.Overlay.CurrentStackLocation = (PIO_STACK_LOCATION)(Irp + 1) + StackSize;
1872
1873 /* Initialize the Thread List */
1874 InitializeListHead(&Irp->ThreadListEntry);
1875}
1876
1877/*
1878 * @implemented
1879 */
1880BOOLEAN
1881NTAPI
1883{
1884 BOOLEAN SynchIO;
1885 BOOLEAN ForceAsync;
1886
1887 /* If the IRP requests synchronous paging I/O, if the file object was opened
1888 for synchronous I/O, if the IRP_SYNCHRONOUS_API flag is set in the IRP
1889 the operation is synchronous */
1891 (Irp->Flags & IRP_SYNCHRONOUS_API) || (Irp->Flags & IRP_SYNCHRONOUS_PAGING_IO);
1892
1893 /* If the IRP requests asynchronous paging I/O, the operation is asynchronous,
1894 even if one of the above conditions is true */
1895 ForceAsync = (Irp->Flags & IRP_PAGING_IO) && !(Irp->Flags & IRP_SYNCHRONOUS_PAGING_IO);
1896
1897 /* Check the flags */
1898 if (SynchIO && !ForceAsync)
1899 {
1900 /* Synch API or Paging I/O is OK, as is Sync File I/O */
1901 return TRUE;
1902 }
1903
1904 /* Otherwise, it is an asynchronous operation. */
1905 return FALSE;
1906}
1907
1908/*
1909 * @unimplemented
1910 */
1911BOOLEAN
1912NTAPI
1914 IN PREPARSE_DATA_BUFFER ReparseBuffer)
1915{
1917 return FALSE;
1918}
1919
1920/*
1921 * @implemented
1922 */
1923PIRP
1924NTAPI
1927{
1928 PIRP AssocIrp;
1930 "%s - Associating IRP %p\n",
1932 Irp);
1933
1934 /* Allocate the IRP */
1935 AssocIrp = IoAllocateIrp(StackSize, FALSE);
1936 if (!AssocIrp) return NULL;
1937
1938 /* Set the Flags */
1939 AssocIrp->Flags |= IRP_ASSOCIATED_IRP;
1940
1941 /* Set the Thread */
1942 AssocIrp->Tail.Overlay.Thread = Irp->Tail.Overlay.Thread;
1943
1944 /* Associate them */
1945 AssocIrp->AssociatedIrp.MasterIrp = Irp;
1946 return AssocIrp;
1947}
1948
1949/*
1950 * @implemented
1951 */
1952VOID
1953NTAPI
1955{
1957 "%s - Queueing IRP %p\n",
1959 Irp);
1960
1961 /* Use our inlined routine */
1963}
1964
1965/*
1966 * @implemented
1967 * Reference: Chris Cant's "Writing WDM Device Drivers"
1968 */
1969VOID
1970NTAPI
1973{
1974 UCHAR AllocationFlags;
1976 "%s - Reusing IRP %p\n",
1978 Irp);
1979
1980 /* Make sure it's OK to reuse it */
1981 ASSERT(!Irp->CancelRoutine);
1982 ASSERT(IsListEmpty(&Irp->ThreadListEntry));
1983
1984 /* Get the old flags */
1985 AllocationFlags = Irp->AllocationFlags;
1986
1987 /* Reinitialize the IRP */
1988 IoInitializeIrp(Irp, Irp->Size, Irp->StackCount);
1989
1990 /* Duplicate the data */
1991 Irp->IoStatus.Status = Status;
1992 Irp->AllocationFlags = AllocationFlags;
1993}
1994
1995/*
1996 * @implemented
1997 */
1998VOID
1999NTAPI
2001{
2002 /* Set the IRP */
2003 PsGetCurrentThread()->TopLevelIrp = (ULONG_PTR)Irp;
2004}
2005
2006#if defined (_WIN64)
2007BOOLEAN
2008NTAPI
2009IoIs32bitProcess(
2011{
2013 return FALSE;
2014}
2015#endif
struct _IO_STACK_LOCATION * PIO_STACK_LOCATION
static PIO_STACK_LOCATION IoGetCurrentIrpStackLocation(PIRP Irp)
#define PAGED_CODE()
unsigned char BOOLEAN
static ULONG StackSize
Definition: StackOverflow.c:19
#define InterlockedIncrement
Definition: armddk.h:53
#define InterlockedExchange
Definition: armddk.h:54
#define InterlockedDecrement
Definition: armddk.h:52
LONG NTSTATUS
Definition: precomp.h:26
#define DPRINT1
Definition: precomp.h:8
#define UNIMPLEMENTED
Definition: debug.h:118
_In_ PFCB _In_ LONGLONG StartingOffset
Definition: cdprocs.h:291
#define IRP_MJ_PNP
Definition: cdrw_usr.h:52
Definition: bufpool.h:45
_In_ PIRP Irp
Definition: csq.h:116
#define STATUS_PENDING
Definition: d3dkmdt.h:43
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:33
#define __FUNCTION__
Definition: types.h:116
#define UNIMPLEMENTED_DBGBREAK(...)
Definition: debug.h:57
#define UlongToPtr(u)
Definition: config.h:106
#define ULONG_PTR
Definition: config.h:101
#define PtrToUlong(u)
Definition: config.h:107
#define ExAllocatePoolWithTag(hernya, size, tag)
Definition: env_spec_w32.h:350
#define IsListEmpty(ListHead)
Definition: env_spec_w32.h:954
UCHAR KIRQL
Definition: env_spec_w32.h:591
#define DO_BUFFERED_IO
Definition: env_spec_w32.h:394
#define PsGetCurrentThread()
Definition: env_spec_w32.h:81
#define KeRaiseIrql(irql, oldIrql)
Definition: env_spec_w32.h:597
#define KeWaitForSingleObject(pEvt, foo, a, b, c)
Definition: env_spec_w32.h:478
#define KeInitializeEvent(pEvt, foo, foo2)
Definition: env_spec_w32.h:477
#define APC_LEVEL
Definition: env_spec_w32.h:695
#define KeLowerIrql(oldIrql)
Definition: env_spec_w32.h:602
#define KeSetEvent(pEvt, foo, foo2)
Definition: env_spec_w32.h:476
#define DO_DIRECT_IO
Definition: env_spec_w32.h:396
#define ExFreePool(addr)
Definition: env_spec_w32.h:352
#define RemoveHeadList(ListHead)
Definition: env_spec_w32.h:964
#define NonPagedPool
Definition: env_spec_w32.h:307
#define InitializeListHead(ListHead)
Definition: env_spec_w32.h:944
#define KeDelayExecutionThread(mode, foo, t)
Definition: env_spec_w32.h:484
LONG NTAPI KeReadStateEvent(IN PKEVENT Event)
Definition: eventobj.c:120
#define _SEH2_END
Definition: filesup.c:22
#define _SEH2_TRY
Definition: filesup.c:19
_In_opt_ PFILE_OBJECT _In_opt_ PETHREAD Thread
Definition: fltkernel.h:2653
_Must_inspect_result_ _In_ PLARGE_INTEGER _In_ PLARGE_INTEGER _In_ ULONG _In_ PFILE_OBJECT _In_ PVOID Process
Definition: fsrtlfuncs.h:223
#define IoFreeMdl
Definition: fxmdl.h:89
#define IoAllocateMdl
Definition: fxmdl.h:88
Status
Definition: gdiplustypes.h:25
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
VOID FASTCALL KeReleaseQueuedSpinLock(IN KSPIN_LOCK_QUEUE_NUMBER LockNumber, IN KIRQL OldIrql)
Definition: spinlock.c:154
KIRQL FASTCALL KeAcquireQueuedSpinLock(IN KSPIN_LOCK_QUEUE_NUMBER LockNumber)
Definition: spinlock.c:108
#define KeGetCurrentThread
Definition: hal.h:55
CPPORT Port[4]
Definition: headless.c:35
#define EXCEPTION_EXECUTE_HANDLER
Definition: excpt.h:85
#define LONG_MAX
Definition: limits.h:43
FORCEINLINE VOID IopQueueIrpToThread(IN PIRP Irp)
Definition: io_x.h:49
static __inline VOID IopUpdateTransferCount(IN IOP_TRANSFER_TYPE Type, IN ULONG TransferCount)
Definition: io_x.h:116
static __inline VOID IopUnlockFileObject(IN PFILE_OBJECT FileObject)
Definition: io_x.h:36
FORCEINLINE VOID IopUnQueueIrpFromThread(IN PIRP Irp)
Definition: io_x.h:66
IoMarkIrpPending(Irp)
IoSetCancelRoutine(Irp, CancelRoutine)
#define IoSetCompletionRoutine(_Irp, _CompletionRoutine, _Context, _InvokeOnSuccess, _InvokeOnError, _InvokeOnCancel)
Definition: irp.cpp:490
if(dx< 0)
Definition: linetemp.h:194
#define PCHAR
Definition: match.c:90
VOID NTAPI MmProbeAndLockPages(IN PMDL Mdl, IN KPROCESSOR_MODE AccessMode, IN LOCK_OPERATION Operation)
Definition: mdlsup.c:931
VOID NTAPI MmUnlockPages(IN PMDL Mdl)
Definition: mdlsup.c:1435
#define ASSERT(a)
Definition: mode.c:44
#define ExFreePoolWithTag(_P, _T)
Definition: module.h:1109
static OUT PIO_STATUS_BLOCK IoStatusBlock
Definition: pipe.c:75
#define IO_METHOD_FROM_CTL_CODE(C)
Definition: mup.h:11
_In_ NDIS_ERROR_CODE ErrorCode
Definition: ndis.h:4436
#define KernelMode
Definition: asm.h:34
FORCEINLINE struct _KPRCB * KeGetCurrentPrcb(VOID)
Definition: ketypes.h:1150
@ AttachedApcEnvironment
Definition: ketypes.h:768
@ OriginalApcEnvironment
Definition: ketypes.h:767
@ CurrentApcEnvironment
Definition: ketypes.h:769
VOID(NTAPI * PKNORMAL_ROUTINE)(IN PVOID NormalContext OPTIONAL, IN PVOID SystemArgument1 OPTIONAL, IN PVOID SystemArgument2 OPTIONAL)
Definition: ketypes.h:744
enum _PP_NPAGED_LOOKASIDE_NUMBER PP_NPAGED_LOOKASIDE_NUMBER
@ LookasideLargeIrpList
Definition: mmtypes.h:169
@ LookasideSmallIrpList
Definition: mmtypes.h:168
DWORD Interval
Definition: netstat.c:30
#define METHOD_NEITHER
Definition: nt_native.h:597
#define FASTCALL
Definition: nt_native.h:50
#define METHOD_OUT_DIRECT
Definition: nt_native.h:596
#define METHOD_BUFFERED
Definition: nt_native.h:594
#define METHOD_IN_DIRECT
Definition: nt_native.h:595
_In_ ULONG _In_ ULONG _In_ ULONG Length
Definition: ntddpcm.h:102
@ NotificationEvent
@ SynchronizationEvent
#define IoCopyCurrentIrpStackLocationToNext(Irp)
Definition: ntifs_ex.h:413
#define IO_DRIVER_CANCEL_TIMEOUT
Definition: ntiologc.h:80
VOID NTAPI IopDoNameTransmogrify(IN PIRP Irp, IN PFILE_OBJECT FileObject, IN PREPARSE_DATA_BUFFER DataBuffer)
Definition: file.c:170
@ IopWriteTransfer
Definition: io.h:262
@ IopReadTransfer
Definition: io.h:261
@ IopOtherTransfer
Definition: io.h:263
#define IO_IRP_DEBUG
Definition: io.h:19
@ IopCompletionPacketIrp
Definition: io.h:271
#define IOTRACE(x, fmt,...)
Definition: io.h:47
#define IsIrpSynchronous(Irp, FileObject)
Definition: io.h:120
VOID NTAPI ExReturnPoolQuota(IN PVOID P)
Definition: expool.c:1852
ULONG NTAPI MmGetSessionId(IN PEPROCESS Process)
Definition: session.c:179
VOID NTAPI IoWriteErrorLogEntry(IN PVOID ElEntry)
Definition: error.c:628
PVOID NTAPI IoAllocateErrorLogEntry(IN PVOID IoObject, IN UCHAR EntrySize)
Definition: error.c:528
NTSTATUS FASTCALL IofCallDriver(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
Definition: irp.c:1258
VOID NTAPI IoCancelThreadIo(IN PETHREAD Thread)
Definition: irp.c:1146
VOID NTAPI IoInitializeIrp(IN PIRP Irp, IN USHORT PacketSize, IN CCHAR StackSize)
Definition: irp.c:1854
VOID NTAPI IoQueueThreadIrp(IN PIRP Irp)
Definition: irp.c:1954
VOID FASTCALL IofCompleteRequest(IN PIRP Irp, IN CCHAR PriorityBoost)
Definition: irp.c:1308
ULONG NTAPI IoGetRequestorProcessId(IN PIRP Irp)
Definition: irp.c:1805
PIRP NTAPI IoBuildSynchronousFsdRequest(IN ULONG MajorFunction, IN PDEVICE_OBJECT DeviceObject, IN PVOID Buffer, IN ULONG Length, IN PLARGE_INTEGER StartingOffset, IN PKEVENT Event, IN PIO_STATUS_BLOCK IoStatusBlock)
Definition: irp.c:1069
VOID NTAPI IopAbortIrpKernelApc(IN PKAPC Apc)
Definition: irp.c:37
VOID NTAPI IoEnqueueIrp(IN PIRP Irp)
Definition: irp.c:1247
#define IoCompleteRequest
Definition: irp.c:1240
VOID NTAPI IopCompleteRequest(IN PKAPC Apc, IN PKNORMAL_ROUTINE *NormalRoutine, IN PVOID *NormalContext, IN PVOID *SystemArgument1, IN PVOID *SystemArgument2)
Definition: irp.c:238
BOOLEAN NTAPI IopInitializeReserveIrp(IN PRESERVE_IRP_ALLOCATOR ReserveIrpAllocator)
Definition: irp.c:549
FORCEINLINE VOID IopClearStackLocation(IN PIO_STACK_LOCATION IoStackLocation)
Definition: irp.c:1292
VOID NTAPI IopFreeIrpKernelApc(IN PKAPC Apc, IN PKNORMAL_ROUTINE *NormalRoutine, IN PVOID *NormalContext, IN PVOID *SystemArgument1, IN PVOID *SystemArgument2)
Definition: irp.c:25
NTSTATUS NTAPI IopCleanupFailedIrp(IN PFILE_OBJECT FileObject, IN PKEVENT EventObject OPTIONAL, IN PVOID Buffer OPTIONAL)
Definition: irp.c:45
BOOLEAN NTAPI IoIsOperationSynchronous(IN PIRP Irp)
Definition: irp.c:1882
BOOLEAN NTAPI IoIsValidNameGraftingBuffer(IN PIRP Irp, IN PREPARSE_DATA_BUFFER ReparseBuffer)
Definition: irp.c:1913
PIRP IopDeadIrp
Definition: irp.c:18
PIRP NTAPI IopAllocateReserveIrp(IN CCHAR StackSize)
Definition: irp.c:573
PIRP NTAPI IoAllocateIrp(IN CCHAR StackSize, IN BOOLEAN ChargeQuota)
Definition: irp.c:615
VOID NTAPI IopDisassociateThreadIrp(VOID)
Definition: irp.c:115
PIRP NTAPI IoBuildAsynchronousFsdRequest(IN ULONG MajorFunction, IN PDEVICE_OBJECT DeviceObject, IN PVOID Buffer, IN ULONG Length, IN PLARGE_INTEGER StartingOffset, IN PIO_STATUS_BLOCK IoStatusBlock)
Definition: irp.c:750
PEPROCESS NTAPI IoGetRequestorProcess(IN PIRP Irp)
Definition: irp.c:1782
VOID NTAPI IopAbortInterruptedIrp(IN PKEVENT EventObject, IN PIRP Irp)
Definition: irp.c:67
PIRP NTAPI IopAllocateIrpMustSucceed(IN CCHAR StackSize)
Definition: irp.c:716
VOID NTAPI IoReuseIrp(IN OUT PIRP Irp, IN NTSTATUS Status)
Definition: irp.c:1971
NTSTATUS NTAPI IopSynchronousCompletion(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN PVOID Context)
Definition: irp.c:1611
BOOLEAN NTAPI IoCancelIrp(IN PIRP Irp)
Definition: irp.c:1101
PIRP NTAPI IoBuildDeviceIoControlRequest(IN ULONG IoControlCode, IN PDEVICE_OBJECT DeviceObject, IN PVOID InputBuffer, IN ULONG InputBufferLength, IN PVOID OutputBuffer, IN ULONG OutputBufferLength, IN BOOLEAN InternalDeviceIoControl, IN PKEVENT Event, IN PIO_STATUS_BLOCK IoStatusBlock)
Definition: irp.c:881
PIRP NTAPI IoGetTopLevelIrp(VOID)
Definition: irp.c:1843
VOID IopFreeReserveIrp(IN CCHAR PriorityBoost)
Definition: irp.c:599
IO_PAGING_PRIORITY FASTCALL IoGetPagingIoPriority(IN PIRP Irp)
Definition: irp.c:1748
BOOLEAN NTAPI IoForwardIrpSynchronously(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
Definition: irp.c:1625
#define IoCallDriver
Definition: irp.c:1225
VOID NTAPI IoSetTopLevelIrp(IN PIRP Irp)
Definition: irp.c:2000
VOID NTAPI IoFreeIrp(IN PIRP Irp)
Definition: irp.c:1666
VOID NTAPI IopCleanupIrp(IN PIRP Irp, IN PFILE_OBJECT FileObject)
Definition: irp.c:191
PIRP NTAPI IoMakeAssociatedIrp(IN PIRP Irp, IN CCHAR StackSize)
Definition: irp.c:1925
NTSTATUS NTAPI IoGetRequestorSessionId(IN PIRP Irp, OUT PULONG pSessionId)
Definition: irp.c:1821
RESERVE_IRP_ALLOCATOR IopReserveIrpAllocator
Definition: irp.c:19
VOID NTAPI IoReleaseCancelSpinLock(IN KIRQL Irql)
Definition: util.c:150
VOID NTAPI IoAcquireCancelSpinLock(OUT PKIRQL Irql)
Definition: util.c:56
BOOLEAN NTAPI KeInsertQueueApc(IN PKAPC Apc, IN PVOID SystemArgument1, IN PVOID SystemArgument2, IN KPRIORITY PriorityBoost)
Definition: apc.c:735
VOID NTAPI KeInitializeApc(IN PKAPC Apc, IN PKTHREAD Thread, IN KAPC_ENVIRONMENT TargetEnvironment, IN PKKERNEL_ROUTINE KernelRoutine, IN PKRUNDOWN_ROUTINE RundownRoutine OPTIONAL, IN PKNORMAL_ROUTINE NormalRoutine, IN KPROCESSOR_MODE Mode, IN PVOID Context)
Definition: apc.c:651
LONG NTAPI KeInsertQueue(IN PKQUEUE Queue, IN PLIST_ENTRY Entry)
Definition: queue.c:198
#define STATUS_REPARSE
Definition: ntstatus.h:83
#define STATUS_IO_REPARSE_TAG_NOT_HANDLED
Definition: ntstatus.h:757
VOID NTAPI ObDereferenceObjectDeferDelete(IN PVOID Object)
Definition: obref.c:358
long LONG
Definition: pedump.c:60
unsigned short USHORT
Definition: pedump.c:61
#define _SEH2_GetExceptionCode()
Definition: pseh2_64.h:165
#define _SEH2_EXCEPT(...)
Definition: pseh2_64.h:66
#define _SEH2_YIELD(__stmt)
Definition: pseh2_64.h:168
#define IRP_MJ_READ
Definition: rdpdr.c:46
#define IRP_MJ_DEVICE_CONTROL
Definition: rdpdr.c:52
#define IRP_MJ_WRITE
Definition: rdpdr.c:47
VOID NTAPI KeBugCheckEx(_In_ ULONG BugCheckCode, _In_ ULONG_PTR BugCheckParameter1, _In_ ULONG_PTR BugCheckParameter2, _In_ ULONG_PTR BugCheckParameter3, _In_ ULONG_PTR BugCheckParameter4)
Definition: rtlcompat.c:108
#define STATUS_MORE_PROCESSING_REQUIRED
Definition: shellext.h:68
#define STATUS_SUCCESS
Definition: shellext.h:65
struct _REPARSE_DATA_BUFFER * PREPARSE_DATA_BUFFER
PULONG MinorVersion OPTIONAL
Definition: CrossNt.h:68
Key()
Definition: map_test.cpp:305
KTHREAD Tcb
Definition: pstypes.h:1104
LIST_ENTRY IrpList
Definition: pstypes.h:1145
NTSTATUS ErrorCode
Definition: iotypes.h:2007
struct _IO_STACK_LOCATION::@3974::@3979 Write
PFILE_OBJECT FileObject
Definition: iotypes.h:3169
PDEVICE_OBJECT DeviceObject
Definition: iotypes.h:3223
struct _IO_STACK_LOCATION::@3974::@3978 Read
PIO_COMPLETION_ROUTINE CompletionRoutine
Definition: iotypes.h:3314
struct _IO_STACK_LOCATION::@1575::@1576 DeviceIoControl
union _IO_STACK_LOCATION::@1575 Parameters
struct _IO_STACK_LOCATION::@3974::@4013 Others
union _IRP::@1577 AssociatedIrp
Definition: ketypes.h:547
PP_LOOKASIDE_LIST PPLookasideList[16]
Definition: ketypes.h:697
LONG LookasideIrpFloat
Definition: ketypes.h:728
Definition: typedefs.h:120
struct _LIST_ENTRY * Flink
Definition: typedefs.h:121
struct _GENERAL_LOOKASIDE * P
Definition: ketypes.h:871
struct _GENERAL_LOOKASIDE * L
Definition: ketypes.h:872
USHORT ReparseDataLength
Definition: shellext.h:166
volatile LONG ReserveIrpInUse
Definition: io.h:504
KEVENT WaitEvent
Definition: io.h:505
VOID WINAPI DECLSPEC_HOTPATCH Sleep(IN DWORD dwMilliseconds)
Definition: synch.c:790
#define TAG_SYS_BUF
Definition: tag.h:87
uint32_t * PULONG
Definition: typedefs.h:59
#define NTAPI
Definition: typedefs.h:36
#define RtlCopyMemory(Destination, Source, Length)
Definition: typedefs.h:263
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:262
uint32_t ULONG_PTR
Definition: typedefs.h:65
#define IN
Definition: typedefs.h:39
#define CONTAINING_RECORD(address, type, field)
Definition: typedefs.h:260
uint32_t ULONG
Definition: typedefs.h:59
#define OUT
Definition: typedefs.h:40
char CCHAR
Definition: typedefs.h:51
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
#define STATUS_VERIFY_REQUIRED
Definition: udferr_usr.h:130
#define STATUS_INSUFFICIENT_RESOURCES
Definition: udferr_usr.h:158
#define NT_ERROR(Status)
Definition: umtypes.h:106
#define TAG_IRP
Definition: vfat.h:548
_In_ PDEVICE_OBJECT DeviceObject
Definition: wdfdevice.h:2055
_In_ WDFREQUEST _In_ WDFFILEOBJECT FileObject
Definition: wdfdevice.h:550
_Must_inspect_result_ _In_ WDFDEVICE _In_ PWDF_DEVICE_PROPERTY_DATA _In_ DEVPROPTYPE _In_ ULONG Size
Definition: wdfdevice.h:4533
_In_ UCHAR MajorFunction
Definition: wdfdevice.h:1697
_Must_inspect_result_ _In_ WDFDEVICE _In_ DEVICE_REGISTRY_PROPERTY _In_ ULONG BufferLength
Definition: wdfdevice.h:3771
_In_ WDFDEVICE _In_ PVOID _In_opt_ PMDL Mdl
_In_ WDFDPC _In_ BOOLEAN Wait
Definition: wdfdpc.h:170
_Must_inspect_result_ _In_ PDRIVER_OBJECT DriverObject
Definition: wdfdriver.h:213
_In_ WDFINTERRUPT _In_ WDF_INTERRUPT_POLICY _In_ WDF_INTERRUPT_PRIORITY Priority
Definition: wdfinterrupt.h:655
_In_ WDFREQUEST _In_ size_t _In_ size_t _In_ ULONG IoControlCode
Definition: wdfio.h:325
_In_ WDFREQUEST _In_ size_t OutputBufferLength
Definition: wdfio.h:320
_In_ WDFREQUEST _In_ size_t _In_ size_t InputBufferLength
Definition: wdfio.h:322
_Must_inspect_result_ _In_ WDFIOTARGET _In_opt_ WDFREQUEST _In_opt_ PWDF_MEMORY_DESCRIPTOR OutputBuffer
Definition: wdfiotarget.h:863
_Must_inspect_result_ _In_ WDFIOTARGET _In_opt_ WDFREQUEST _In_opt_ PWDF_MEMORY_DESCRIPTOR InputBuffer
Definition: wdfiotarget.h:953
_In_ WDFREQUEST _In_ NTSTATUS _In_ CCHAR PriorityBoost
Definition: wdfrequest.h:1016
_Must_inspect_result_ _In_ WDFCMRESLIST List
Definition: wdfresource.h:550
#define FORCEINLINE
Definition: wdftypes.h:67
_Must_inspect_result_ _In_ ULONG Flags
Definition: wsk.h:170
FORCEINLINE USHORT ExQueryDepthSList(_In_ PSLIST_HEADER SListHead)
Definition: exfuncs.h:153
#define ExAllocatePoolWithQuotaTag(a, b, c)
Definition: exfuncs.h:530
struct LOOKASIDE_ALIGN _NPAGED_LOOKASIDE_LIST * PNPAGED_LOOKASIDE_LIST
__drv_aliasesMem FORCEINLINE PIO_STACK_LOCATION IoGetNextIrpStackLocation(_In_ PIRP Irp)
Definition: iofuncs.h:2695
_In_opt_ PDRIVER_CANCEL CancelRoutine
Definition: iofuncs.h:2744
#define IoSizeOfIrp(_StackSize)
_In_ USHORT PacketSize
Definition: iofuncs.h:1058
_Must_inspect_result_ __drv_aliasesMem _In_ PDEVICE_OBJECT _In_opt_ PVOID _In_ ULONG _Out_opt_ PVOID _In_ ULONG _In_ BOOLEAN InternalDeviceIoControl
Definition: iofuncs.h:720
_Must_inspect_result_ _In_ BOOLEAN ChargeQuota
Definition: iofuncs.h:651
#define SL_PENDING_RETURNED
Definition: iotypes.h:3325
#define IRP_CLASS_CACHE_OPERATION
enum _IO_PAGING_PRIORITY IO_PAGING_PRIORITY
#define IRP_DEALLOCATE_BUFFER
#define IRP_CLOSE_OPERATION
#define IO_TYPE_IRP
#define IRP_SYNCHRONOUS_API
#define IRP_QUOTA_CHARGED
#define SL_ERROR_RETURNED
Definition: iotypes.h:3326
#define IRP_INPUT_OPERATION
#define IO_NO_INCREMENT
Definition: iotypes.h:598
#define IRP_PAGING_IO
#define IRP_OB_QUERY_NAME
@ IoPagingPriorityNormal
Definition: iotypes.h:2821
@ IoPagingPriorityHigh
Definition: iotypes.h:2822
@ IoPagingPriorityInvalid
Definition: iotypes.h:2820
#define IRP_WRITE_OPERATION
#define POOL_QUOTA_FAIL_INSTEAD_OF_RAISE
DRIVER_CANCEL * PDRIVER_CANCEL
Definition: iotypes.h:2759
#define SL_INVOKE_ON_ERROR
Definition: iotypes.h:3329
#define IRP_CREATE_OPERATION
#define IRP_DEFER_IO_COMPLETION
#define IRP_ASSOCIATED_IRP
* PFILE_OBJECT
Definition: iotypes.h:1998
#define MAXIMUM_REPARSE_DATA_BUFFER_SIZE
Definition: iotypes.h:7213
#define SL_INVOKE_ON_CANCEL
Definition: iotypes.h:3327
#define IRP_MJ_FLUSH_BUFFERS
#define IRP_READ_OPERATION
#define IRP_LOOKASIDE_ALLOCATION
#define IRP_MJ_INTERNAL_DEVICE_CONTROL
#define IRP_ALLOCATED_FIXED_SIZE
#define IO_REPARSE_TAG_MOUNT_POINT
Definition: iotypes.h:7231
#define FO_SYNCHRONOUS_IO
Definition: iotypes.h:1776
#define IRP_MJ_SHUTDOWN
#define IO_REMOUNT
Definition: iotypes.h:544
#define IRP_MJ_POWER
#define IRP_BUFFERED_IO
#define IRP_SYNCHRONOUS_PAGING_IO
#define SL_INVOKE_ON_SUCCESS
Definition: iotypes.h:3328
_Requires_lock_held_ Interrupt _Releases_lock_ Interrupt _In_ _IRQL_restores_ KIRQL OldIrql
Definition: kefuncs.h:778
@ Suspended
Definition: ketypes.h:420
@ Executive
Definition: ketypes.h:415
@ IoReadAccess
Definition: ketypes.h:863
@ IoWriteAccess
Definition: ketypes.h:864
_In_opt_ PVOID _In_opt_ PVOID SystemArgument1
Definition: ketypes.h:688
@ LockQueueIoCompletionLock
Definition: ketypes.h:669
_In_opt_ PVOID _In_opt_ PVOID _In_opt_ PVOID SystemArgument2
Definition: ketypes.h:689
#define ObDereferenceObject
Definition: obfuncs.h:203
#define InterlockedPushEntrySList(SListHead, SListEntry)
Definition: rtlfuncs.h:3403
#define InterlockedPopEntrySList(SListHead)
Definition: rtlfuncs.h:3406
#define PSLIST_ENTRY
Definition: rtltypes.h:134
unsigned char UCHAR
Definition: xmlstorage.h:181