[CLASSPNP]
[reactos.git] / reactos / drivers / storage / classpnp / classp.h
1 /*++
2
3 Copyright (C) Microsoft Corporation, 1991 - 1999
4
5 Module Name:
6
7 classp.h
8
9 Abstract:
10
11 Private header file for classpnp.sys modules. This contains private
12 structure and function declarations as well as constant values which do
13 not need to be exported.
14
15 Author:
16
17 Environment:
18
19 kernel mode only
20
21 Notes:
22
23
24 Revision History:
25
26 --*/
27
28 #include <ntddk.h>
29 #include <classpnp.h>
30 #include <ioevent.h>
31 #include <pseh/pseh2.h>
32
33 extern CLASSPNP_SCAN_FOR_SPECIAL_INFO ClassBadItems[];
34
35 extern GUID ClassGuidQueryRegInfoEx;
36
37
38 #define CLASSP_REG_SUBKEY_NAME (L"Classpnp")
39
40 #define CLASSP_REG_HACK_VALUE_NAME (L"HackMask")
41 #define CLASSP_REG_MMC_DETECTION_VALUE_NAME (L"MMCDetectionState")
42 #define CLASSP_REG_WRITE_CACHE_VALUE_NAME (L"WriteCacheEnableOverride")
43 #define CLASSP_REG_PERF_RESTORE_VALUE_NAME (L"RestorePerfAtCount")
44 #define CLASSP_REG_REMOVAL_POLICY_VALUE_NAME (L"UserRemovalPolicy")
45
46 #define CLASS_PERF_RESTORE_MINIMUM (0x10)
47 #define CLASS_ERROR_LEVEL_1 (0x4)
48 #define CLASS_ERROR_LEVEL_2 (0x8)
49
50 #define FDO_HACK_CANNOT_LOCK_MEDIA (0x00000001)
51 #define FDO_HACK_GESN_IS_BAD (0x00000002)
52 #define FDO_HACK_NO_SYNC_CACHE (0x00000004)
53
54 #define FDO_HACK_VALID_FLAGS (0x00000007)
55 #define FDO_HACK_INVALID_FLAGS (~FDO_HACK_VALID_FLAGS)
56
57 /*
58 * Lots of retries of synchronized SCSI commands that devices may not
59 * even support really slows down the system (especially while booting).
60 * (Even GetDriveCapacity may be failed on purpose if an external disk is powered off).
61 * If a disk cannot return a small initialization buffer at startup
62 * in two attempts (with delay interval) then we cannot expect it to return
63 * data consistently with four retries.
64 * So don't set the retry counts as high here as for data SRBs.
65 *
66 * If we find that these requests are failing consecutively,
67 * despite the retry interval, on otherwise reliable media,
68 * then we should either increase the retry interval for
69 * that failure or (by all means) increase these retry counts as appropriate.
70 */
71 #define NUM_LOCKMEDIAREMOVAL_RETRIES 1
72 #define NUM_MODESENSE_RETRIES 1
73 #define NUM_DRIVECAPACITY_RETRIES 1
74
75
76 #define CLASS_FILE_OBJECT_EXTENSION_KEY 'eteP'
77 #define CLASSP_VOLUME_VERIFY_CHECKED 0x34
78
79 #define CLASS_TAG_PRIVATE_DATA 'CPcS'
80 #define CLASS_TAG_PRIVATE_DATA_FDO 'FPcS'
81 #define CLASS_TAG_PRIVATE_DATA_PDO 'PPcS'
82
83 struct _MEDIA_CHANGE_DETECTION_INFO {
84
85 //
86 // Mutex to synchronize enable/disable requests and media state changes
87 //
88
89 KMUTEX MediaChangeMutex;
90
91 //
92 // The current state of the media (present, not present, unknown)
93 // protected by MediaChangeSynchronizationEvent
94 //
95
96 MEDIA_CHANGE_DETECTION_STATE MediaChangeDetectionState;
97
98 //
99 // This is a count of how many time MCD has been disabled. if it is
100 // set to zero, then we'll poll the device for MCN events with the
101 // then-current method (ie. TEST UNIT READY or GESN). this is
102 // protected by MediaChangeMutex
103 //
104
105 LONG MediaChangeDetectionDisableCount;
106
107
108 //
109 // The timer value to support media change events. This is a countdown
110 // value used to determine when to poll the device for a media change.
111 // The max value for the timer is 255 seconds. This is not protected
112 // by an event -- simply InterlockedExchanged() as needed.
113 //
114
115 LONG MediaChangeCountDown;
116
117 //
118 // recent changes allowed instant retries of the MCN irp. Since this
119 // could cause an infinite loop, keep a count of how many times we've
120 // retried immediately so that we can catch if the count exceeds an
121 // arbitrary limit.
122 //
123
124 LONG MediaChangeRetryCount;
125
126 //
127 // use GESN if it's available
128 //
129
130 struct {
131 BOOLEAN Supported;
132 BOOLEAN HackEventMask;
133 UCHAR EventMask;
134 UCHAR NoChangeEventMask;
135 PUCHAR Buffer;
136 PMDL Mdl;
137 ULONG BufferSize;
138 } Gesn;
139
140 //
141 // If this value is one, then the irp is currently in use.
142 // If this value is zero, then the irp is available.
143 // Use InterlockedCompareExchange() to set from "available" to "in use".
144 // ASSERT that InterlockedCompareExchange() showed previous value of
145 // "in use" when changing back to "available" state.
146 // This also implicitly protects the MediaChangeSrb and SenseBuffer
147 //
148
149 LONG MediaChangeIrpInUse;
150
151 //
152 // Pointer to the irp to be used for media change detection.
153 // protected by Interlocked MediaChangeIrpInUse
154 //
155
156 PIRP MediaChangeIrp;
157
158 //
159 // The srb for the media change detection.
160 // protected by Interlocked MediaChangeIrpInUse
161 //
162
163 SCSI_REQUEST_BLOCK MediaChangeSrb;
164 PUCHAR SenseBuffer;
165 ULONG SrbFlags;
166
167 //
168 // Second timer to keep track of how long the media change IRP has been
169 // in use. If this value exceeds the timeout (#defined) then we should
170 // print out a message to the user and set the MediaChangeIrpLost flag
171 // protected by using Interlocked() operations in ClasspSendMediaStateIrp,
172 // the only routine which should modify this value.
173 //
174
175 LONG MediaChangeIrpTimeInUse;
176
177 //
178 // Set by CdRomTickHandler when we determine that the media change irp has
179 // been lost
180 //
181
182 BOOLEAN MediaChangeIrpLost;
183
184 };
185
186 typedef enum {
187 SimpleMediaLock,
188 SecureMediaLock,
189 InternalMediaLock
190 } MEDIA_LOCK_TYPE, *PMEDIA_LOCK_TYPE;
191
192 typedef struct _FAILURE_PREDICTION_INFO {
193 FAILURE_PREDICTION_METHOD Method;
194 ULONG CountDown; // Countdown timer
195 ULONG Period; // Countdown period
196
197 PIO_WORKITEM WorkQueueItem;
198
199 KEVENT Event;
200 } FAILURE_PREDICTION_INFO, *PFAILURE_PREDICTION_INFO;
201
202
203
204 //
205 // This struct must always fit within four PVOIDs of info,
206 // as it uses the irp's "PVOID DriverContext[4]" to store
207 // this info
208 //
209 typedef struct _CLASS_RETRY_INFO {
210 struct _CLASS_RETRY_INFO *Next;
211 } CLASS_RETRY_INFO, *PCLASS_RETRY_INFO;
212
213
214
215 typedef struct _CSCAN_LIST {
216
217 //
218 // The current block which has an outstanding request.
219 //
220
221 ULONGLONG BlockNumber;
222
223 //
224 // The list of blocks past the CurrentBlock to which we're going to do
225 // i/o. This list is maintained in sorted order.
226 //
227
228 LIST_ENTRY CurrentSweep;
229
230 //
231 // The list of blocks behind the current block for which we'll have to
232 // wait until the next scan across the disk. This is kept as a stack,
233 // the cost of sorting it is taken when it's moved over to be the
234 // running list.
235 //
236
237 LIST_ENTRY NextSweep;
238
239 } CSCAN_LIST, *PCSCAN_LIST;
240
241 //
242 // add to the front of this structure to help prevent illegal
243 // snooping by other utilities.
244 //
245
246
247
248 typedef enum _CLASS_DETECTION_STATE {
249 ClassDetectionUnknown = 0,
250 ClassDetectionUnsupported = 1,
251 ClassDetectionSupported = 2
252 } CLASS_DETECTION_STATE, *PCLASS_DETECTION_STATE;
253
254
255 typedef struct _CLASS_ERROR_LOG_DATA {
256 LARGE_INTEGER TickCount; // Offset 0x00
257 ULONG PortNumber; // Offset 0x08
258
259 UCHAR ErrorPaging : 1; // Offset 0x0c
260 UCHAR ErrorRetried : 1;
261 UCHAR ErrorUnhandled : 1;
262 UCHAR ErrorReserved : 5;
263
264 UCHAR Reserved[3];
265
266 SCSI_REQUEST_BLOCK Srb; // Offset 0x10
267
268 /*
269 * We define the SenseData as the default length.
270 * Since the sense data returned by the port driver may be longer,
271 * SenseData must be at the end of this structure.
272 * For our internal error log, we only log the default length.
273 */
274 SENSE_DATA SenseData; // Offset 0x50 for x86 (or 0x68 for ia64) (ULONG32 Alignment required!)
275 } CLASS_ERROR_LOG_DATA, *PCLASS_ERROR_LOG_DATA;
276
277 #define NUM_ERROR_LOG_ENTRIES 16
278
279
280
281 typedef struct _TRANSFER_PACKET {
282
283 LIST_ENTRY AllPktsListEntry; // entry in fdoData's static AllTransferPacketsList
284 SINGLE_LIST_ENTRY SlistEntry; // for when in free list (use fast slist)
285
286 PIRP Irp;
287 PDEVICE_OBJECT Fdo;
288
289 /*
290 * This is the client IRP that this TRANSFER_PACKET is currently
291 * servicing.
292 */
293 PIRP OriginalIrp;
294 BOOLEAN CompleteOriginalIrpWhenLastPacketCompletes;
295
296 /*
297 * Stuff for retrying the transfer.
298 */
299 ULONG NumRetries;
300 KTIMER RetryTimer;
301 KDPC RetryTimerDPC;
302 ULONG RetryIntervalSec;
303
304 /*
305 * Event for synchronizing the transfer (optional).
306 * (Note that we can't have the event in the packet itself because
307 * by the time a thread waits on an event the packet may have
308 * been completed and re-issued.
309 */
310 PKEVENT SyncEventPtr;
311
312 /*
313 * Stuff for retrying during extreme low-memory stress
314 * (when we retry 1 page at a time).
315 */
316 BOOLEAN InLowMemRetry;
317 PUCHAR LowMemRetry_remainingBufPtr;
318 ULONG LowMemRetry_remainingBufLen;
319 LARGE_INTEGER LowMemRetry_nextChunkTargetLocation;
320
321 /*
322 * Fields used for cancelling the packet.
323 */
324 // BOOLEAN Cancelled;
325 // KEVENT CancelledEvent;
326
327 /*
328 * We keep the buffer and length values here as well
329 * as in the SRB because some miniports return
330 * the transferred length in SRB.DataTransferLength,
331 * and if the SRB failed we need that value again for the retry.
332 * We don't trust the lower stack to preserve any of these values in the SRB.
333 */
334 PUCHAR BufPtrCopy;
335 ULONG BufLenCopy;
336 LARGE_INTEGER TargetLocationCopy;
337
338 /*
339 * This is a standard SCSI structure that receives a detailed
340 * report about a SCSI error on the hardware.
341 */
342 SENSE_DATA SrbErrorSenseData;
343
344 /*
345 * This is the SRB block for this TRANSFER_PACKET.
346 * For IOCTLs, the SRB block includes two DWORDs for
347 * device object and ioctl code; so these must
348 * immediately follow the SRB block.
349 */
350 SCSI_REQUEST_BLOCK Srb;
351 // ULONG SrbIoctlDevObj; // not handling ioctls yet
352 // ULONG SrbIoctlCode;
353
354 } TRANSFER_PACKET, *PTRANSFER_PACKET;
355
356 /*
357 * MIN_INITIAL_TRANSFER_PACKETS is the minimum number of packets that
358 * we preallocate at startup for each device (we need at least one packet
359 * to guarantee forward progress during memory stress).
360 * MIN_WORKINGSET_TRANSFER_PACKETS is the number of TRANSFER_PACKETs
361 * we allow to build up and remain for each device;
362 * we _lazily_ work down to this number when they're not needed.
363 * MAX_WORKINGSET_TRANSFER_PACKETS is the number of TRANSFER_PACKETs
364 * that we _immediately_ reduce to when they are not needed.
365 *
366 * The absolute maximum number of packets that we will allocate is
367 * whatever is required by the current activity, up to the memory limit;
368 * as soon as stress ends, we snap down to MAX_WORKINGSET_TRANSFER_PACKETS;
369 * we then lazily work down to MIN_WORKINGSET_TRANSFER_PACKETS.
370 */
371 #define MIN_INITIAL_TRANSFER_PACKETS 1
372 #define MIN_WORKINGSET_TRANSFER_PACKETS_Consumer 4
373 #define MAX_WORKINGSET_TRANSFER_PACKETS_Consumer 64
374 #define MIN_WORKINGSET_TRANSFER_PACKETS_Server 64
375 #define MAX_WORKINGSET_TRANSFER_PACKETS_Server 1024
376 #define MIN_WORKINGSET_TRANSFER_PACKETS_Enterprise 256
377 #define MAX_WORKINGSET_TRANSFER_PACKETS_Enterprise 2048
378
379
380 //
381 // add to the front of this structure to help prevent illegal
382 // snooping by other utilities.
383 //
384 struct _CLASS_PRIVATE_FDO_DATA {
385
386 //
387 // this private structure allows us to
388 // dynamically re-enable the perf benefits
389 // lost due to transient error conditions.
390 // in w2k, a reboot was required. :(
391 //
392 struct {
393 ULONG OriginalSrbFlags;
394 ULONG SuccessfulIO;
395 ULONG ReEnableThreshhold; // 0 means never
396 } Perf;
397
398 ULONG_PTR HackFlags;
399
400 STORAGE_HOTPLUG_INFO HotplugInfo;
401
402 // Legacy. Still used by obsolete legacy code.
403 struct {
404 LARGE_INTEGER Delta; // in ticks
405 LARGE_INTEGER Tick; // when it should fire
406 PCLASS_RETRY_INFO ListHead; // singly-linked list
407 ULONG Granularity; // static
408 KSPIN_LOCK Lock; // protective spin lock
409 KDPC Dpc; // DPC routine object
410 KTIMER Timer; // timer to fire DPC
411 } Retry;
412
413 BOOLEAN TimerStarted;
414 BOOLEAN LoggedTURFailureSinceLastIO;
415
416 //
417 // privately allocated release queue irp
418 // protected by fdoExtension->ReleaseQueueSpinLock
419 //
420 BOOLEAN ReleaseQueueIrpAllocated;
421 PIRP ReleaseQueueIrp;
422
423 /*
424 * Queues for TRANSFER_PACKETs that contextualize the IRPs and SRBs
425 * that we send down to the port driver.
426 * (The free list is an slist so that we can use fast
427 * interlocked operations on it; but the relatively-static
428 * AllTransferPacketsList list has to be
429 * a doubly-linked list since we have to dequeue from the middle).
430 */
431 LIST_ENTRY AllTransferPacketsList;
432 SLIST_HEADER FreeTransferPacketsList;
433 ULONG NumFreeTransferPackets;
434 ULONG NumTotalTransferPackets;
435 ULONG DbgPeakNumTransferPackets;
436
437 /*
438 * Queue for deferred client irps
439 */
440 LIST_ENTRY DeferredClientIrpList;
441
442 /*
443 * Precomputed maximum transfer length for the hardware.
444 */
445 ULONG HwMaxXferLen;
446
447 /*
448 * SCSI_REQUEST_BLOCK template preconfigured with the constant values.
449 * This is slapped into the SRB in the TRANSFER_PACKET for each transfer.
450 */
451 SCSI_REQUEST_BLOCK SrbTemplate;
452
453 KSPIN_LOCK SpinLock;
454
455 /*
456 * Circular array of timestamped logs of errors that occurred on this device.
457 */
458 ULONG ErrorLogNextIndex;
459 CLASS_ERROR_LOG_DATA ErrorLogs[NUM_ERROR_LOG_ENTRIES];
460
461 };
462
463
464 #define MIN(a, b) ((a) < (b) ? (a) : (b))
465 #define MAX(a, b) ((a) > (b) ? (a) : (b))
466
467
468 #define NOT_READY_RETRY_INTERVAL 10
469 #define MINIMUM_RETRY_UNITS ((LONGLONG)32)
470
471
472 /*
473 * Simple singly-linked-list queuing macros, with no synchronization.
474 */
475 static inline VOID SimpleInitSlistHdr(SINGLE_LIST_ENTRY *SListHdr)
476 {
477 SListHdr->Next = NULL;
478 }
479 static inline VOID SimplePushSlist(SINGLE_LIST_ENTRY *SListHdr, SINGLE_LIST_ENTRY *SListEntry)
480 {
481 SListEntry->Next = SListHdr->Next;
482 SListHdr->Next = SListEntry;
483 }
484 static inline SINGLE_LIST_ENTRY *SimplePopSlist(SINGLE_LIST_ENTRY *SListHdr)
485 {
486 SINGLE_LIST_ENTRY *sListEntry = SListHdr->Next;
487 if (sListEntry){
488 SListHdr->Next = sListEntry->Next;
489 sListEntry->Next = NULL;
490 }
491 return sListEntry;
492 }
493 static inline BOOLEAN SimpleIsSlistEmpty(SINGLE_LIST_ENTRY *SListHdr)
494 {
495 return (SListHdr->Next == NULL);
496 }
497
498 DRIVER_INITIALIZE DriverEntry;
499
500 DRIVER_UNLOAD ClassUnload;
501
502 DRIVER_DISPATCH ClassCreateClose;
503
504 NTSTATUS
505 NTAPI
506 ClasspCreateClose(
507 IN PDEVICE_OBJECT DeviceObject,
508 IN PIRP Irp
509 );
510
511 VOID
512 NTAPI
513 ClasspCleanupProtectedLocks(
514 IN PFILE_OBJECT_EXTENSION FsContext
515 );
516
517 NTSTATUS
518 NTAPI
519 ClasspEjectionControl(
520 IN PDEVICE_OBJECT Fdo,
521 IN PIRP Irp,
522 IN MEDIA_LOCK_TYPE LockType,
523 IN BOOLEAN Lock
524 );
525
526 DRIVER_DISPATCH ClassReadWrite;
527
528 DRIVER_DISPATCH ClassDeviceControlDispatch;
529
530 DRIVER_DISPATCH ClassDispatchPnp;
531
532 NTSTATUS
533 NTAPI
534 ClassPnpStartDevice(
535 IN PDEVICE_OBJECT DeviceObject
536 );
537
538 NTSTATUS
539 NTAPI
540 ClassShutdownFlush(
541 IN PDEVICE_OBJECT DeviceObject,
542 IN PIRP Irp
543 );
544
545 DRIVER_DISPATCH ClassSystemControl;
546
547 //
548 // Class internal routines
549 //
550
551 DRIVER_ADD_DEVICE ClassAddDevice;
552
553 IO_COMPLETION_ROUTINE ClasspSendSynchronousCompletion;
554
555 VOID
556 NTAPI
557 RetryRequest(
558 PDEVICE_OBJECT DeviceObject,
559 PIRP Irp,
560 PSCSI_REQUEST_BLOCK Srb,
561 BOOLEAN Associated,
562 ULONG RetryInterval
563 );
564
565 NTSTATUS
566 NTAPI
567 ClassIoCompletion(
568 IN PDEVICE_OBJECT DeviceObject,
569 IN PIRP Irp,
570 IN PVOID Context
571 );
572
573 NTSTATUS
574 NTAPI
575 ClassPnpQueryFdoRelations(
576 IN PDEVICE_OBJECT Fdo,
577 IN PIRP Irp
578 );
579
580 NTSTATUS
581 NTAPI
582 ClassRetrieveDeviceRelations(
583 IN PDEVICE_OBJECT Fdo,
584 IN DEVICE_RELATION_TYPE RelationType,
585 OUT PDEVICE_RELATIONS *DeviceRelations
586 );
587
588 NTSTATUS
589 NTAPI
590 ClassGetPdoId(
591 IN PDEVICE_OBJECT Pdo,
592 IN BUS_QUERY_ID_TYPE IdType,
593 IN PUNICODE_STRING IdString
594 );
595
596 NTSTATUS
597 NTAPI
598 ClassQueryPnpCapabilities(
599 IN PDEVICE_OBJECT PhysicalDeviceObject,
600 IN PDEVICE_CAPABILITIES Capabilities
601 );
602
603 DRIVER_STARTIO ClasspStartIo;
604
605 NTSTATUS
606 NTAPI
607 ClasspPagingNotificationCompletion(
608 IN PDEVICE_OBJECT DeviceObject,
609 IN PIRP Irp,
610 IN PDEVICE_OBJECT RealDeviceObject
611 );
612
613 NTSTATUS
614 NTAPI
615 ClasspMediaChangeCompletion(
616 PDEVICE_OBJECT DeviceObject,
617 PIRP Irp,
618 PVOID Context
619 );
620
621 PFILE_OBJECT_EXTENSION
622 NTAPI
623 ClasspGetFsContext(
624 IN PCOMMON_DEVICE_EXTENSION CommonExtension,
625 IN PFILE_OBJECT FileObject
626 );
627
628 NTSTATUS
629 NTAPI
630 ClasspMcnControl(
631 IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension,
632 IN PIRP Irp,
633 IN PSCSI_REQUEST_BLOCK Srb
634 );
635
636 VOID
637 NTAPI
638 ClasspRegisterMountedDeviceInterface(
639 IN PDEVICE_OBJECT DeviceObject
640 );
641
642 NTSTATUS
643 NTAPI
644 ClasspDisableTimer(
645 PDEVICE_OBJECT DeviceObject
646 );
647
648 NTSTATUS
649 NTAPI
650 ClasspEnableTimer(
651 PDEVICE_OBJECT DeviceObject
652 );
653
654 //
655 // routines for dictionary list support
656 //
657
658 VOID
659 NTAPI
660 InitializeDictionary(
661 IN PDICTIONARY Dictionary
662 );
663
664 BOOLEAN
665 NTAPI
666 TestDictionarySignature(
667 IN PDICTIONARY Dictionary
668 );
669
670 NTSTATUS
671 NTAPI
672 AllocateDictionaryEntry(
673 IN PDICTIONARY Dictionary,
674 IN ULONGLONG Key,
675 IN ULONG Size,
676 IN ULONG Tag,
677 OUT PVOID *Entry
678 );
679
680 PVOID
681 NTAPI
682 GetDictionaryEntry(
683 IN PDICTIONARY Dictionary,
684 IN ULONGLONG Key
685 );
686
687 VOID
688 NTAPI
689 FreeDictionaryEntry(
690 IN PDICTIONARY Dictionary,
691 IN PVOID Entry
692 );
693
694
695 NTSTATUS
696 NTAPI
697 ClasspAllocateReleaseRequest(
698 IN PDEVICE_OBJECT Fdo
699 );
700
701 VOID
702 NTAPI
703 ClasspFreeReleaseRequest(
704 IN PDEVICE_OBJECT Fdo
705 );
706
707 IO_COMPLETION_ROUTINE ClassReleaseQueueCompletion;
708
709 VOID
710 NTAPI
711 ClasspReleaseQueue(
712 IN PDEVICE_OBJECT DeviceObject,
713 IN PIRP ReleaseQueueIrp
714 );
715
716 VOID
717 NTAPI
718 ClasspDisablePowerNotification(
719 PFUNCTIONAL_DEVICE_EXTENSION FdoExtension
720 );
721
722 //
723 // class power routines
724 //
725
726 DRIVER_DISPATCH ClassDispatchPower;
727
728 NTSTATUS
729 NTAPI
730 ClassMinimalPowerHandler(
731 IN PDEVICE_OBJECT DeviceObject,
732 IN PIRP Irp
733 );
734
735 //
736 // Child list routines
737 //
738
739 VOID
740 NTAPI
741 ClassAddChild(
742 IN PFUNCTIONAL_DEVICE_EXTENSION Parent,
743 IN PPHYSICAL_DEVICE_EXTENSION Child,
744 IN BOOLEAN AcquireLock
745 );
746
747 PPHYSICAL_DEVICE_EXTENSION
748 NTAPI
749 ClassRemoveChild(
750 IN PFUNCTIONAL_DEVICE_EXTENSION Parent,
751 IN PPHYSICAL_DEVICE_EXTENSION Child,
752 IN BOOLEAN AcquireLock
753 );
754
755 VOID
756 NTAPI
757 ClasspRetryDpcTimer(
758 IN PCLASS_PRIVATE_FDO_DATA FdoData
759 );
760
761 KDEFERRED_ROUTINE ClasspRetryRequestDpc;
762
763 VOID
764 NTAPI
765 ClassFreeOrReuseSrb(
766 IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension,
767 IN PSCSI_REQUEST_BLOCK Srb
768 );
769
770 VOID
771 NTAPI
772 ClassRetryRequest(
773 IN PDEVICE_OBJECT SelfDeviceObject,
774 IN PIRP Irp,
775 IN LARGE_INTEGER TimeDelta100ns // in 100ns units
776 );
777
778 VOID
779 NTAPI
780 ClasspBuildRequestEx(
781 IN PFUNCTIONAL_DEVICE_EXTENSION Fdo,
782 IN PIRP Irp,
783 IN PSCSI_REQUEST_BLOCK Srb
784 );
785
786 NTSTATUS
787 NTAPI
788 ClasspAllocateReleaseQueueIrp(
789 IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension
790 );
791
792 NTSTATUS
793 NTAPI
794 ClasspInitializeGesn(
795 IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension,
796 IN PMEDIA_CHANGE_DETECTION_INFO Info
797 );
798
799 VOID
800 NTAPI
801 ClasspSendNotification(
802 IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension,
803 IN const GUID * Guid,
804 IN ULONG ExtraDataSize,
805 IN PVOID ExtraData
806 );
807
808 VOID
809 NTAPI
810 ClassSendEjectionNotification(
811 IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension
812 );
813
814 VOID
815 NTAPI
816 ClasspScanForSpecialInRegistry(
817 IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension
818 );
819
820 VOID
821 NTAPI
822 ClasspScanForClassHacks(
823 IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension,
824 IN ULONG_PTR Data
825 );
826
827 NTSTATUS
828 NTAPI
829 ClasspInitializeHotplugInfo(
830 IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension
831 );
832
833 VOID
834 NTAPI
835 ClasspPerfIncrementErrorCount(
836 IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension
837 );
838 VOID
839 NTAPI
840 ClasspPerfIncrementSuccessfulIo(
841 IN PFUNCTIONAL_DEVICE_EXTENSION FdoExtension
842 );
843
844 PTRANSFER_PACKET NTAPI NewTransferPacket(PDEVICE_OBJECT Fdo);
845 VOID NTAPI DestroyTransferPacket(PTRANSFER_PACKET Pkt);
846 VOID NTAPI EnqueueFreeTransferPacket(PDEVICE_OBJECT Fdo, PTRANSFER_PACKET Pkt);
847 PTRANSFER_PACKET NTAPI DequeueFreeTransferPacket(PDEVICE_OBJECT Fdo, BOOLEAN AllocIfNeeded);
848 VOID NTAPI SetupReadWriteTransferPacket(PTRANSFER_PACKET pkt, PVOID Buf, ULONG Len, LARGE_INTEGER DiskLocation, PIRP OriginalIrp);
849 VOID NTAPI SubmitTransferPacket(PTRANSFER_PACKET Pkt);
850 NTSTATUS NTAPI TransferPktComplete(IN PDEVICE_OBJECT NullFdo, IN PIRP Irp, IN PVOID Context);
851 VOID NTAPI ServiceTransferRequest(PDEVICE_OBJECT Fdo, PIRP Irp);
852 VOID NTAPI TransferPacketRetryTimerDpc(IN PKDPC Dpc, IN PVOID DeferredContext, IN PVOID SystemArgument1, IN PVOID SystemArgument2);
853 BOOLEAN NTAPI InterpretTransferPacketError(PTRANSFER_PACKET Pkt);
854 BOOLEAN NTAPI RetryTransferPacket(PTRANSFER_PACKET Pkt);
855 VOID NTAPI EnqueueDeferredClientIrp(PCLASS_PRIVATE_FDO_DATA FdoData, PIRP Irp);
856 PIRP NTAPI DequeueDeferredClientIrp(PCLASS_PRIVATE_FDO_DATA FdoData);
857 VOID NTAPI InitLowMemRetry(PTRANSFER_PACKET Pkt, PVOID BufPtr, ULONG Len, LARGE_INTEGER TargetLocation);
858 BOOLEAN NTAPI StepLowMemRetry(PTRANSFER_PACKET Pkt);
859 VOID NTAPI SetupEjectionTransferPacket(TRANSFER_PACKET *Pkt, BOOLEAN PreventMediaRemoval, PKEVENT SyncEventPtr, PIRP OriginalIrp);
860 VOID NTAPI SetupModeSenseTransferPacket(TRANSFER_PACKET *Pkt, PKEVENT SyncEventPtr, PVOID ModeSenseBuffer, UCHAR ModeSenseBufferLen, UCHAR PageMode, PIRP OriginalIrp);
861 VOID NTAPI SetupDriveCapacityTransferPacket(TRANSFER_PACKET *Pkt, PVOID ReadCapacityBuffer, ULONG ReadCapacityBufferLen, PKEVENT SyncEventPtr, PIRP OriginalIrp);
862 PMDL NTAPI BuildDeviceInputMdl(PVOID Buffer, ULONG BufferLen);
863 VOID NTAPI FreeDeviceInputMdl(PMDL Mdl);
864 NTSTATUS NTAPI InitializeTransferPackets(PDEVICE_OBJECT Fdo);
865 VOID NTAPI DestroyAllTransferPackets(PDEVICE_OBJECT Fdo);
866
867 #include "debug.h"