ReactOS 0.4.15-dev-7907-g95bf896
partmgr.c
Go to the documentation of this file.
1/*
2 * PROJECT: Partition manager driver
3 * LICENSE: GPL-2.0-or-later (https://spdx.org/licenses/GPL-2.0-or-later)
4 * PURPOSE: Main file
5 * COPYRIGHT: 2020 Victor Perevertkin (victor.perevertkin@reactos.org)
6 */
7
8/* The Partition Manager Driver in ReactOS complements disk.sys/classpnp.sys drivers
9 * (which are derived from Windows 10 drivers) so does not do exactly what Windows 2003 partmgr.sys
10 * does. Here is acts like both partition and volume manager, because volmgr.sys does not (yet)
11 * exist in ReactOS. Thus handles some IOCTL_VOLUME_*, and IOCTL_MOUNTMGR_* IOCTLs.
12 */
13
14#include "partmgr.h"
15
16
17static
18CODE_SEG("PAGE")
21 _In_ CONST PDRIVE_LAYOUT_INFORMATION_EX LayoutEx)
22{
24 PPARTITION_INFORMATION Partition;
25 PPARTITION_INFORMATION_EX PartitionEx;
26
27 PAGED_CODE();
28
29 ASSERT(LayoutEx);
30
31 if (LayoutEx->PartitionStyle != PARTITION_STYLE_MBR)
32 {
34 return NULL;
35 }
36
37 size_t layoutSize = FIELD_OFFSET(DRIVE_LAYOUT_INFORMATION, PartitionEntry[0]) +
38 LayoutEx->PartitionCount * sizeof (PARTITION_INFORMATION);
39
40 Layout = ExAllocatePoolWithTag(PagedPool, layoutSize, TAG_PARTMGR);
41
42 if (Layout == NULL)
43 {
44 return NULL;
45 }
46
47 Layout->Signature = LayoutEx->Mbr.Signature;
48 Layout->PartitionCount = LayoutEx->PartitionCount;
49
50 for (UINT32 i = 0; i < LayoutEx->PartitionCount; i++)
51 {
52 Partition = &Layout->PartitionEntry[i];
53 PartitionEx = &LayoutEx->PartitionEntry[i];
54
55 Partition->StartingOffset = PartitionEx->StartingOffset;
56 Partition->PartitionLength = PartitionEx->PartitionLength;
57 Partition->RewritePartition = PartitionEx->RewritePartition;
58 Partition->PartitionNumber = PartitionEx->PartitionNumber;
59
60 Partition->PartitionType = PartitionEx->Mbr.PartitionType;
61 Partition->BootIndicator = PartitionEx->Mbr.BootIndicator;
62 Partition->RecognizedPartition = PartitionEx->Mbr.RecognizedPartition;
63 Partition->HiddenSectors = PartitionEx->Mbr.HiddenSectors;
64 }
65
66 return Layout;
67}
68
69static
70CODE_SEG("PAGE")
71PDRIVE_LAYOUT_INFORMATION_EX
74{
75 PDRIVE_LAYOUT_INFORMATION_EX layoutEx;
76
77 PAGED_CODE();
78
79 ASSERT(Layout != NULL);
80
81 size_t layoutSize = FIELD_OFFSET(DRIVE_LAYOUT_INFORMATION_EX, PartitionEntry[0]) +
82 Layout->PartitionCount * sizeof (PARTITION_INFORMATION_EX);
83
84 layoutEx = ExAllocatePoolUninitialized(PagedPool, layoutSize, TAG_PARTMGR);
85
86 if (layoutEx == NULL)
87 {
88 return NULL;
89 }
90
91 layoutEx->PartitionStyle = PARTITION_STYLE_MBR;
92 layoutEx->PartitionCount = Layout->PartitionCount;
93 layoutEx->Mbr.Signature = Layout->Signature;
94
95 for (UINT32 i = 0; i < Layout->PartitionCount; i++)
96 {
97 PPARTITION_INFORMATION part = &Layout->PartitionEntry[i];
98
99 layoutEx->PartitionEntry[i] = (PARTITION_INFORMATION_EX) {
100 .PartitionStyle = PARTITION_STYLE_MBR,
101 .StartingOffset = part->StartingOffset,
102 .PartitionLength = part->PartitionLength,
103 .RewritePartition = part->RewritePartition,
104 .PartitionNumber = part->PartitionNumber,
105 .Mbr = {
106 .PartitionType = part->PartitionType,
107 .BootIndicator = part->BootIndicator,
108 .RecognizedPartition = part->RecognizedPartition,
109 .HiddenSectors = part->HiddenSectors,
110 }
111 };
112 }
113
114 return layoutEx;
115}
116
117static
118CODE_SEG("PAGE")
119VOID
122 _Inout_ PDRIVE_LAYOUT_INFORMATION_EX NewLayout)
123{
125 PSINGLE_LIST_ENTRY curEntry, prevEntry;
126 UINT32 totalPartitions = 0;
127
128 // Clear the partition numbers from the list entries
129 for (UINT32 i = 0; i < NewLayout->PartitionCount; i++)
130 {
131 NewLayout->PartitionEntry[i].PartitionNumber = 0;
132 }
133
134 // iterate over old partition list
135 prevEntry = &FdoExtension->PartitionList;
136 curEntry = FdoExtension->PartitionList.Next;
137 while (curEntry != NULL)
138 {
139 PPARTITION_EXTENSION partExt = CONTAINING_RECORD(curEntry, PARTITION_EXTENSION, ListEntry);
140 UINT32 partNumber = 0; // count detected partitions for device symlinks
141 BOOLEAN found = FALSE;
143
144 // trying to find this partition in returned layout
145 for (UINT32 i = 0; i < NewLayout->PartitionCount; i++)
146 {
147 partEntry = &NewLayout->PartitionEntry[i];
148
149 // skip unused and container partitions
150 if (NewLayout->PartitionStyle == PARTITION_STYLE_MBR &&
153 {
154 continue;
155 }
156
157 partNumber++;
158
159 // skip already found partitions
160 if (partEntry->PartitionNumber)
161 {
162 continue;
163 }
164
165 // skip if partitions are not equal
166 if (partEntry->StartingOffset.QuadPart != partExt->StartingOffset ||
167 partEntry->PartitionLength.QuadPart != partExt->PartitionLength)
168 {
169 continue;
170 }
171
172 // found matching partition - processing it
173 found = TRUE;
174 break;
175 }
176
177 if (found)
178 {
179 // update (possibly changed) partition metadata
180 if (NewLayout->PartitionStyle == PARTITION_STYLE_MBR)
181 {
182 partExt->Mbr.PartitionType = partEntry->Mbr.PartitionType;
183 partExt->Mbr.BootIndicator = partEntry->Mbr.BootIndicator;
184 }
185 else
186 {
187 partExt->Gpt.PartitionType = partEntry->Gpt.PartitionType;
188 partExt->Gpt.PartitionId = partEntry->Gpt.PartitionId;
189 partExt->Gpt.Attributes = partEntry->Gpt.Attributes;
190
191 RtlCopyMemory(partExt->Gpt.Name, partEntry->Gpt.Name, sizeof(partExt->Gpt.Name));
192 }
193
194 partExt->OnDiskNumber = partNumber;
195 partEntry->PartitionNumber = partNumber; // mark it as a found one
196 totalPartitions++;
197 }
198 else
199 {
200 // detach the device from the list
201 prevEntry->Next = curEntry->Next;
202 curEntry = prevEntry;
203 partExt->Attached = FALSE;
204
205 // enumerated PDOs will receive IRP_MN_REMOVE_DEVICE
206 if (!partExt->IsEnumerated)
207 {
208 PartitionHandleRemove(partExt, TRUE);
209 }
210 }
211
212 prevEntry = curEntry;
213 curEntry = curEntry->Next;
214 }
215
216 UINT32 partNumber = 0;
217 UINT32 pdoNumber = 1;
218
219 // now looking through remaining "new" partitions
220 for (UINT32 i = 0; i < NewLayout->PartitionCount; i++)
221 {
222 PPARTITION_INFORMATION_EX partEntry = &NewLayout->PartitionEntry[i];
223
224 // again, skip unused and container partitions
225 if (NewLayout->PartitionStyle == PARTITION_STYLE_MBR &&
228 {
229 continue;
230 }
231
232 partNumber++;
233
234 // and skip processed partitions
235 if (partEntry->PartitionNumber != 0)
236 {
237 continue;
238 }
239
240 // find the first free PDO index
241 for (PSINGLE_LIST_ENTRY curEntry = FdoExtension->PartitionList.Next;
242 curEntry != NULL;
243 curEntry = curEntry->Next)
244 {
245 PPARTITION_EXTENSION partExt = CONTAINING_RECORD(curEntry,
247 ListEntry);
248
249 if (partExt->DetectedNumber == pdoNumber)
250 {
251 // found a matching pdo number - restart the search
252 curEntry = FdoExtension->PartitionList.Next;
253 pdoNumber++;
254 }
255 }
256
257 partEntry->PartitionNumber = partNumber;
258
259 PDEVICE_OBJECT partitionDevice;
261 partEntry,
262 pdoNumber,
263 NewLayout->PartitionStyle,
264 &partitionDevice);
265
266 if (!NT_SUCCESS(status))
267 {
268 partEntry->PartitionNumber = 0;
269 continue;
270 }
271
272 // mark partition as removable if parent device is removable
273 if (FdoExtension->LowerDevice->Characteristics & FILE_REMOVABLE_MEDIA)
274 partitionDevice->Characteristics |= FILE_REMOVABLE_MEDIA;
275
276 totalPartitions++;
277
278 // insert the structure to the partition list
279 curEntry = FdoExtension->PartitionList.Next;
280 prevEntry = NULL;
281 while (curEntry != NULL)
282 {
283 PPARTITION_EXTENSION curPart = CONTAINING_RECORD(curEntry,
285 ListEntry);
286 if (curPart->OnDiskNumber < partNumber)
287 {
288 prevEntry = curEntry;
289 curEntry = curPart->ListEntry.Next;
290 }
291 else
292 { // we found where to put the partition
293 break;
294 }
295 }
296
297 PPARTITION_EXTENSION partExt = partitionDevice->DeviceExtension;
298
299 if (prevEntry)
300 {
301 // insert after prevEntry
302 partExt->ListEntry.Next = prevEntry->Next;
303 prevEntry->Next = &partExt->ListEntry;
304 }
305 else
306 {
307 // insert in the beginning
308 partExt->ListEntry.Next = FdoExtension->PartitionList.Next;
309 FdoExtension->PartitionList.Next = &partExt->ListEntry;
310 }
311
312 partExt->Attached = TRUE;
313 }
314
315 FdoExtension->EnumeratedPartitionsTotal = totalPartitions;
316}
317
318// requires partitioning lock held
319static
320CODE_SEG("PAGE")
324 _Out_ PDRIVE_LAYOUT_INFORMATION_EX *DriveLayout)
325{
326 PAGED_CODE();
327
328 if (FdoExtension->LayoutValid)
329 {
330 *DriveLayout = FdoExtension->LayoutCache;
331 return STATUS_SUCCESS;
332 }
333
334 PDRIVE_LAYOUT_INFORMATION_EX layoutEx = NULL;
335 NTSTATUS status = IoReadPartitionTableEx(FdoExtension->LowerDevice, &layoutEx);
336
337 if (!NT_SUCCESS(status))
338 {
339 return status;
340 }
341
342 if (FdoExtension->LayoutCache)
343 {
344 ExFreePool(FdoExtension->LayoutCache);
345 }
346
347 FdoExtension->LayoutCache = layoutEx;
348 FdoExtension->LayoutValid = TRUE;
349
350 *DriveLayout = layoutEx;
351
352 return status;
353}
354
355static
356CODE_SEG("PAGE")
360 _In_ PIRP Irp)
361{
363
364 PAGED_CODE();
365
366 // We're patching the DISK_PARTITION_INFO part of the returned structure
367 // as disk.sys doesn't really know about the partition table on a disk
368
369 PDISK_GEOMETRY_EX_INTERNAL geometryEx = Irp->AssociatedIrp.SystemBuffer;
370 size_t outBufferLength = ioStack->Parameters.DeviceIoControl.OutputBufferLength;
372
374 FdoExtension->LowerDevice,
375 NULL,
376 0,
377 geometryEx,
378 outBufferLength,
379 FALSE);
380
381 if (!NT_SUCCESS(status))
382 {
383 return status;
384 }
385
386 // if DISK_PARTITION_INFO fits the output size
387 if (outBufferLength >= FIELD_OFFSET(DISK_GEOMETRY_EX_INTERNAL, Detection))
388 {
390
391 geometryEx->Partition.SizeOfPartitionInfo = sizeof(geometryEx->Partition);
392 geometryEx->Partition.PartitionStyle = FdoExtension->DiskData.PartitionStyle;
393
394 switch (geometryEx->Partition.PartitionStyle)
395 {
397 geometryEx->Partition.Mbr.Signature = FdoExtension->DiskData.Mbr.Signature;
398 // checksum?
399 break;
400
402 geometryEx->Partition.Gpt.DiskId = FdoExtension->DiskData.Gpt.DiskId;
403 break;
404
405 default:
406 RtlZeroMemory(&geometryEx->Partition, sizeof(geometryEx->Partition));
407 }
408
410 }
411
412 // the logic is copied from disk.sys
413 Irp->IoStatus.Information = min(outBufferLength, sizeof(DISK_GEOMETRY_EX_INTERNAL));
414
415 return status;
416}
417
418static
419CODE_SEG("PAGE")
423 _In_ PIRP Irp)
424{
425 PPARTITION_INFORMATION partInfo = Irp->AssociatedIrp.SystemBuffer;
426
427 PAGED_CODE();
428
429 if (!VerifyIrpOutBufferSize(Irp, sizeof(*partInfo)))
430 {
432 }
433
435
436 *partInfo = (PARTITION_INFORMATION){
438 .StartingOffset.QuadPart = 0,
439 .PartitionLength.QuadPart = FdoExtension->DiskData.DiskSize,
440 .HiddenSectors = 0,
441 .PartitionNumber = 0,
442 .BootIndicator = FALSE,
443 .RewritePartition = FALSE,
444 .RecognizedPartition = FALSE,
445 };
446
448
449 Irp->IoStatus.Information = sizeof(*partInfo);
450 return STATUS_SUCCESS;
451}
452
453static
454CODE_SEG("PAGE")
458 _In_ PIRP Irp)
459{
460 PPARTITION_INFORMATION_EX partInfoEx = Irp->AssociatedIrp.SystemBuffer;
461
462 PAGED_CODE();
463
464 if (!VerifyIrpOutBufferSize(Irp, sizeof(*partInfoEx)))
465 {
467 }
468
470
471 // most of the fields a zeroed for Partition0
472 *partInfoEx = (PARTITION_INFORMATION_EX){
473 .PartitionLength.QuadPart = FdoExtension->DiskData.DiskSize,
474 .PartitionStyle = FdoExtension->DiskData.PartitionStyle,
475 };
476
478
479 Irp->IoStatus.Information = sizeof(*partInfoEx);
480 return STATUS_SUCCESS;
481}
482
483static
484CODE_SEG("PAGE")
488 _In_ PIRP Irp)
489{
490 PAGED_CODE();
491
493
494 PDRIVE_LAYOUT_INFORMATION_EX layoutEx;
496
497 if (!NT_SUCCESS(status))
498 {
500 return status;
501 }
502
503 // checking this value from layoutEx in case it has been changed
504 if (layoutEx->PartitionStyle != PARTITION_STYLE_MBR)
505 {
508 }
509
510 size_t size = FIELD_OFFSET(DRIVE_LAYOUT_INFORMATION, PartitionEntry[0]);
511 size += layoutEx->PartitionCount * sizeof(PARTITION_INFORMATION);
512
514 {
517 }
518
520
522
523 if (partitionList == NULL)
524 {
525 Irp->IoStatus.Information = 0;
527 }
528
529 RtlMoveMemory(Irp->AssociatedIrp.SystemBuffer, partitionList, size);
530 ExFreePoolWithTag(partitionList, TAG_PARTMGR);
531
532 Irp->IoStatus.Information = size;
533 return STATUS_SUCCESS;
534}
535
536static
537CODE_SEG("PAGE")
541 _In_ PIRP Irp)
542{
543 PAGED_CODE();
544
546
547 PDRIVE_LAYOUT_INFORMATION_EX layoutEx;
549 if (!NT_SUCCESS(status))
550 {
552 return status;
553 }
554
555 size_t size = FIELD_OFFSET(DRIVE_LAYOUT_INFORMATION_EX, PartitionEntry[0]);
556 size += layoutEx->PartitionCount * sizeof(PARTITION_INFORMATION_EX);
557
559 {
562 }
563
564 RtlCopyMemory(Irp->AssociatedIrp.SystemBuffer, layoutEx, size);
565
567
568 Irp->IoStatus.Information = size;
569 return STATUS_SUCCESS;
570}
571
572static
573CODE_SEG("PAGE")
577 _In_ PIRP Irp)
578{
579 PDRIVE_LAYOUT_INFORMATION layoutInfo = Irp->AssociatedIrp.SystemBuffer;
580
581 PAGED_CODE();
582
583 if (!VerifyIrpInBufferSize(Irp, sizeof(*layoutInfo)))
584 {
586 }
587
588 size_t layoutSize = FIELD_OFFSET(DRIVE_LAYOUT_INFORMATION, PartitionEntry[0]);
589 layoutSize += layoutInfo->PartitionCount * sizeof(PARTITION_INFORMATION);
590
591 if (!VerifyIrpInBufferSize(Irp, layoutSize))
592 {
594 }
595
596 PDRIVE_LAYOUT_INFORMATION_EX layoutEx = PartMgrConvertLayoutToExtended(layoutInfo);
597
598 if (layoutEx == NULL)
599 {
600 Irp->IoStatus.Information = 0;
602 }
603
605
606 // this in fact updates the bus relations
608
609 // write the partition table to the disk
610 NTSTATUS status = IoWritePartitionTableEx(FdoExtension->LowerDevice, layoutEx);
611 if (NT_SUCCESS(status))
612 {
613 // save the layout cache
614 if (FdoExtension->LayoutCache)
615 {
616 ExFreePool(FdoExtension->LayoutCache);
617 }
618 FdoExtension->LayoutCache = layoutEx;
619 FdoExtension->LayoutValid = TRUE;
620
621 // set updated partition numbers
622 for (UINT32 i = 0; i < layoutInfo->PartitionCount; i++)
623 {
624 PPARTITION_INFORMATION part = &layoutInfo->PartitionEntry[i];
625
626 part->PartitionNumber = layoutEx->PartitionEntry[i].PartitionNumber;
627 }
628 }
629 else
630 {
631 FdoExtension->LayoutValid = FALSE;
632 }
633
635
637
638 // notify everyone that the disk layout has changed
640
641 notification.Event = GUID_IO_DISK_LAYOUT_CHANGE;
642 notification.Version = 1;
644 notification.FileObject = NULL;
645 notification.NameBufferOffset = -1;
646
649 NULL,
650 NULL);
651
652 Irp->IoStatus.Information = layoutSize;
653 return STATUS_SUCCESS;
654}
655
656static
657CODE_SEG("PAGE")
661 _In_ PIRP Irp)
662{
663 PDRIVE_LAYOUT_INFORMATION_EX layoutEx, layoutUser = Irp->AssociatedIrp.SystemBuffer;
665
666 PAGED_CODE();
667
668 if (!VerifyIrpInBufferSize(Irp, sizeof(*layoutUser)))
669 {
671 }
672
673 size_t layoutSize = FIELD_OFFSET(DRIVE_LAYOUT_INFORMATION_EX, PartitionEntry[0]);
674 layoutSize += layoutUser->PartitionCount * sizeof(PARTITION_INFORMATION_EX);
675
676 if (!VerifyIrpInBufferSize(Irp, layoutSize))
677 {
679 }
680
681 // we need to copy the structure from the IRP input buffer
682 layoutEx = ExAllocatePoolWithTag(PagedPool, layoutSize, TAG_PARTMGR);
683 if (!layoutEx)
684 {
685 Irp->IoStatus.Information = 0;
687 }
688
689 RtlCopyMemory(layoutEx, layoutUser, layoutSize);
690
692
693 // if partition count is 0, it's the same as IOCTL_DISK_CREATE_DISK
694 if (layoutEx->PartitionCount == 0)
695 {
696 CREATE_DISK createDisk = {0};
697 createDisk.PartitionStyle = layoutEx->PartitionStyle;
698 if (createDisk.PartitionStyle == PARTITION_STYLE_MBR)
699 {
700 createDisk.Mbr.Signature = layoutEx->Mbr.Signature;
701 }
702 else if (createDisk.PartitionStyle == PARTITION_STYLE_GPT)
703 {
704 createDisk.Gpt.DiskId = layoutEx->Gpt.DiskId;
705 }
706
707 status = IoCreateDisk(FdoExtension->LowerDevice, &createDisk);
708 }
709 else
710 {
711 // this in fact updates the bus relations
713
714 // write the partition table to the disk
715 status = IoWritePartitionTableEx(FdoExtension->LowerDevice, layoutEx);
716 if (NT_SUCCESS(status))
717 {
718 // set updated partition numbers
719 for (UINT32 i = 0; i < layoutEx->PartitionCount; i++)
720 {
721 PPARTITION_INFORMATION_EX part = &layoutEx->PartitionEntry[i];
722
723 part->PartitionNumber = layoutEx->PartitionEntry[i].PartitionNumber;
724 }
725 }
726 }
727
728 // update the layout cache
729 if (NT_SUCCESS(status))
730 {
731 if (FdoExtension->LayoutCache)
732 {
733 ExFreePool(FdoExtension->LayoutCache);
734 }
735 FdoExtension->LayoutCache = layoutEx;
736 FdoExtension->LayoutValid = TRUE;
737 }
738 else
739 {
740 FdoExtension->LayoutValid = FALSE;
741 }
742
744
746
747 // notify everyone that the disk layout has changed
749
750 notification.Event = GUID_IO_DISK_LAYOUT_CHANGE;
751 notification.Version = 1;
753 notification.FileObject = NULL;
754 notification.NameBufferOffset = -1;
755
758 NULL,
759 NULL);
760
761 Irp->IoStatus.Information = layoutSize;
762 return STATUS_SUCCESS;
763}
764
765static
766CODE_SEG("PAGE")
770 _In_ PIRP Irp)
771{
772 PAGED_CODE();
773
775 FdoExtension->LayoutValid = FALSE;
777
779 return STATUS_SUCCESS;
780}
781
782static
783CODE_SEG("PAGE")
787 _In_ PIRP Irp)
788{
789 PAGED_CODE();
790
791 PCREATE_DISK createDisk = Irp->AssociatedIrp.SystemBuffer;
792 if (!VerifyIrpInBufferSize(Irp, sizeof(*createDisk)))
793 {
795 }
796
798
799 NTSTATUS status = IoCreateDisk(FdoExtension->LowerDevice, createDisk);
800
801 FdoExtension->LayoutValid = FALSE;
803
805 return status;
806}
807
808static
809CODE_SEG("PAGE")
813 _In_ PIRP Irp)
814{
815 CREATE_DISK createDisk = { .PartitionStyle = PARTITION_STYLE_RAW };
816
817 PAGED_CODE();
818
820
821 NTSTATUS status = IoCreateDisk(FdoExtension->LowerDevice, &createDisk);
822
823 FdoExtension->LayoutValid = FALSE;
825
827 return status;
828}
829
830static
831CODE_SEG("PAGE")
835 _In_ PIRP Irp)
836{
837 // obtain the disk device number
838 // this is not expected to change thus not in PartMgrRefreshDiskData
839 STORAGE_DEVICE_NUMBER deviceNumber;
841 FdoExtension->LowerDevice,
842 NULL,
843 0,
844 &deviceNumber,
845 sizeof(deviceNumber),
846 FALSE);
847 if (!NT_SUCCESS(status))
848 {
849 return status;
850 }
851
852 FdoExtension->DiskData.DeviceNumber = deviceNumber.DeviceNumber;
853
854 // register the disk interface
855 // partmgr.sys from Windows 8.1 also registers a mysterious GUID_DEVINTERFACE_HIDDEN_DISK here
856 UNICODE_STRING interfaceName;
858 &GUID_DEVINTERFACE_DISK,
859 NULL,
860 &interfaceName);
861
862 if(!NT_SUCCESS(status))
863 {
864 ERR("Failed to register GUID_DEVINTERFACE_DISK, status %x\n", status);
865 return status;
866 }
867
868 FdoExtension->DiskInterfaceName = interfaceName;
869 status = IoSetDeviceInterfaceState(&interfaceName, TRUE);
870
871 INFO("Disk interface %wZ\n", &interfaceName);
872
873 if (!NT_SUCCESS(status))
874 {
875 RtlFreeUnicodeString(&interfaceName);
876 RtlInitUnicodeString(&FdoExtension->DiskInterfaceName, NULL);
877 }
878
879 return status;
880}
881
882// requires partitioning lock held
883static
884CODE_SEG("PAGE")
888{
890
891 PAGED_CODE();
892
893 // get the DiskSize and BytesPerSector
894 DISK_GEOMETRY_EX geometryEx;
896 FdoExtension->LowerDevice,
897 NULL,
898 0,
899 &geometryEx,
900 sizeof(geometryEx),
901 FALSE);
902 if (!NT_SUCCESS(status))
903 {
904 return status;
905 }
906
907 FdoExtension->DiskData.DiskSize = geometryEx.DiskSize.QuadPart;
908 FdoExtension->DiskData.BytesPerSector = geometryEx.Geometry.BytesPerSector;
909
910 // get the partition style-related info
911 PDRIVE_LAYOUT_INFORMATION_EX layoutEx = NULL;
913 if (!NT_SUCCESS(status))
914 {
915 return status;
916 }
917
918 FdoExtension->DiskData.PartitionStyle = layoutEx->PartitionStyle;
919 if (FdoExtension->DiskData.PartitionStyle == PARTITION_STYLE_MBR)
920 {
921 FdoExtension->DiskData.Mbr.Signature = layoutEx->Mbr.Signature;
922 // FdoExtension->DiskData.Mbr.Checksum = geometryEx.Partition.Mbr.CheckSum;
923 }
924 else
925 {
926 FdoExtension->DiskData.Gpt.DiskId = layoutEx->Gpt.DiskId;
927 }
928
929 return STATUS_SUCCESS;
930}
931
932static
933CODE_SEG("PAGE")
937 _In_ PIRP Irp)
938{
941
942 PAGED_CODE();
943
944 if (type == BusRelations)
945 {
947
949 if (!NT_SUCCESS(status))
950 {
952 Irp->IoStatus.Status = STATUS_INSUFFICIENT_RESOURCES;
953 Irp->IoStatus.Information = 0;
955 return Irp->IoStatus.Status;
956 }
957
958 INFO("Partition style %u\n", FdoExtension->DiskData.PartitionStyle);
959
960 // PartMgrAcquireLayoutLock calls PartMgrGetDriveLayout inside
961 // so we're sure here that it returns only cached layout
962 PDRIVE_LAYOUT_INFORMATION_EX layoutEx;
964
966
967 // now fill the DeviceRelations structure
968 TRACE("Reporting %u partitions\n", FdoExtension->EnumeratedPartitionsTotal);
969
970 PDEVICE_RELATIONS deviceRelations =
972 sizeof(DEVICE_RELATIONS)
973 + sizeof(PDEVICE_OBJECT)
974 * (FdoExtension->EnumeratedPartitionsTotal - 1),
976
977 if (!deviceRelations)
978 {
980 Irp->IoStatus.Status = STATUS_INSUFFICIENT_RESOURCES;
981 Irp->IoStatus.Information = 0;
983 return Irp->IoStatus.Status;
984 }
985
986 deviceRelations->Count = 0;
987
988 PSINGLE_LIST_ENTRY curEntry = FdoExtension->PartitionList.Next;
989 while (curEntry != NULL)
990 {
991 PPARTITION_EXTENSION partExt = CONTAINING_RECORD(curEntry,
993 ListEntry);
994
995 // mark the PDO to know that we don't need to manually delete it
996 partExt->IsEnumerated = TRUE;
997 deviceRelations->Objects[deviceRelations->Count++] = partExt->DeviceObject;
999
1000 curEntry = partExt->ListEntry.Next;
1001 }
1002
1003 ASSERT(deviceRelations->Count == FdoExtension->EnumeratedPartitionsTotal);
1004
1006
1007 Irp->IoStatus.Information = (ULONG_PTR)deviceRelations;
1008 Irp->IoStatus.Status = STATUS_SUCCESS;
1009 }
1010
1012 return IoCallDriver(FdoExtension->LowerDevice, Irp);
1013}
1014
1015static
1016CODE_SEG("PAGE")
1020 _In_ PIRP Irp)
1021{
1022 PAGED_CODE();
1023
1024 if (FdoExtension->DiskInterfaceName.Buffer)
1025 {
1026 IoSetDeviceInterfaceState(&FdoExtension->DiskInterfaceName, FALSE);
1027 RtlFreeUnicodeString(&FdoExtension->DiskInterfaceName);
1028 RtlInitUnicodeString(&FdoExtension->DiskInterfaceName, NULL);
1029 }
1030
1031 // Send the IRP down the stack
1033 Irp->IoStatus.Status = STATUS_SUCCESS;
1034 NTSTATUS status = IoCallDriver(FdoExtension->LowerDevice, Irp);
1035
1036 IoDetachDevice(FdoExtension->LowerDevice);
1037 IoDeleteDevice(FdoExtension->DeviceObject);
1038 return status;
1039}
1040
1041static
1042CODE_SEG("PAGE")
1046 _In_ PIRP Irp)
1047{
1048 PAGED_CODE();
1049
1050 // all enumerated child devices should receive IRP_MN_REMOVE_DEVICE
1051 // removing only non-enumerated ones here
1052 for (PSINGLE_LIST_ENTRY curEntry = FdoExtension->PartitionList.Next;
1053 curEntry != NULL;
1054 curEntry = curEntry->Next)
1055 {
1056 PPARTITION_EXTENSION partExt = CONTAINING_RECORD(curEntry,
1058 ListEntry);
1059
1060 if (partExt->IsEnumerated)
1061 {
1062 PartitionHandleRemove(partExt, TRUE);
1063 }
1064 }
1065
1066 // Send the IRP down the stack
1068 Irp->IoStatus.Status = STATUS_SUCCESS;
1069 return IoCallDriver(FdoExtension->LowerDevice, Irp);
1070}
1071
1072static
1073CODE_SEG("PAGE")
1075NTAPI
1079{
1081
1082 PAGED_CODE();
1083
1085 sizeof(FDO_EXTENSION),
1086 0,
1089 FALSE,
1090 &deviceObject);
1091
1092 if (!NT_SUCCESS(status))
1093 {
1094 ERR("Failed to create FDO 0x%x\n", status);
1095 return status;
1096 }
1097
1098 PFDO_EXTENSION deviceExtension = deviceObject->DeviceExtension;
1099 RtlZeroMemory(deviceExtension, sizeof(*deviceExtension));
1100
1101 deviceExtension->IsFDO = TRUE;
1102 deviceExtension->DeviceObject = deviceObject;
1104 deviceExtension->PhysicalDiskDO = PhysicalDeviceObject;
1106
1107 // the the attaching failed
1108 if (!deviceExtension->LowerDevice)
1109 {
1111
1112 return STATUS_DEVICE_REMOVED;
1113 }
1115
1116 // device is initialized
1117 deviceObject->Flags &= ~DO_DEVICE_INITIALIZING;
1118
1119 return STATUS_SUCCESS;
1120}
1121
1122static
1124NTAPI
1127 _In_ PIRP Irp)
1128{
1130 PFDO_EXTENSION fdoExtension = DeviceObject->DeviceExtension;
1132
1133 // Note: IRP_MJ_DEVICE_CONTROL handler in the storage stack must be able to pass IOCTLs
1134 // at an IRQL higher than PASSIVE_LEVEL
1135
1136 INFO("IRP_MJ_DEVICE_CONTROL %p Irp %p IOCTL %x isFdo: %u\n",
1137 DeviceObject, Irp, ioStack->Parameters.DeviceIoControl.IoControlCode, fdoExtension->IsFDO);
1138
1139 if (!fdoExtension->IsFDO)
1140 {
1142 }
1143
1144 switch (ioStack->Parameters.DeviceIoControl.IoControlCode)
1145 {
1147 status = FdoIoctlDiskGetDriveGeometryEx(fdoExtension, Irp);
1148 break;
1149
1151 status = FdoIoctlDiskGetPartitionInfo(fdoExtension, Irp);
1152 break;
1153
1155 status = FdoIoctlDiskGetPartitionInfoEx(fdoExtension, Irp);
1156 break;
1157
1159 status = FdoIoctlDiskGetDriveLayout(fdoExtension, Irp);
1160 break;
1161
1163 status = FdoIoctlDiskGetDriveLayoutEx(fdoExtension, Irp);
1164 break;
1165
1167 status = FdoIoctlDiskSetDriveLayout(fdoExtension, Irp);
1168 break;
1169
1171 status = FdoIoctlDiskSetDriveLayoutEx(fdoExtension, Irp);
1172 break;
1173
1175 status = FdoIoctlDiskUpdateProperties(fdoExtension, Irp);
1176 break;
1177
1179 status = FdoIoctlDiskCreateDisk(fdoExtension, Irp);
1180 break;
1181
1183 status = FdoIoctlDiskDeleteDriveLayout(fdoExtension, Irp);
1184 break;
1185 // case IOCTL_DISK_GROW_PARTITION: // todo
1186 default:
1188 }
1189
1190 Irp->IoStatus.Status = status;
1192 return status;
1193}
1194
1195static
1196CODE_SEG("PAGE")
1198NTAPI
1201 _In_ PIRP Irp)
1202{
1203 PAGED_CODE();
1204
1205 PFDO_EXTENSION fdoExtension = DeviceObject->DeviceExtension;
1207
1208 INFO("IRP_MJ_PNP %p Irp %p %s isFDO: %u\n",
1209 DeviceObject, Irp, GetIRPMinorFunctionString(ioStack->MinorFunction), fdoExtension->IsFDO);
1210
1211 if (!fdoExtension->IsFDO)
1212 {
1214 }
1215
1216 switch (ioStack->MinorFunction) {
1217
1219 {
1221
1222 // if this is sent to the FDO so we should forward it down the
1223 // attachment chain before we can start the FDO
1224
1225 if (!IoForwardIrpSynchronously(fdoExtension->LowerDevice, Irp))
1226 {
1228 }
1229 else
1230 {
1231 status = FdoHandleStartDevice(fdoExtension, Irp);
1232 }
1233
1234 Irp->IoStatus.Status = status;
1236 return status;
1237 }
1239 {
1240 return FdoHandleDeviceRelations(fdoExtension, Irp);
1241 }
1243 {
1244 return FdoHandleSurpriseRemoval(fdoExtension, Irp);
1245 }
1247 {
1248 return FdoHandleRemoveDevice(fdoExtension, Irp);
1249 }
1254 case IRP_MN_STOP_DEVICE:
1255 {
1256 Irp->IoStatus.Status = STATUS_SUCCESS;
1257 // fallthrough
1258 }
1259 default:
1260 {
1262 return IoCallDriver(fdoExtension->LowerDevice, Irp);
1263 }
1264 }
1265}
1266
1267static
1269NTAPI
1272 _In_ PIRP Irp)
1273{
1274 PPARTITION_EXTENSION partExt = DeviceObject->DeviceExtension;
1276
1277 if (!partExt->IsFDO)
1278 {
1279 if (!partExt->IsEnumerated)
1280 {
1281 Irp->IoStatus.Status = STATUS_DEVICE_DOES_NOT_EXIST;
1284 }
1285 else
1286 {
1287 ioStack->Parameters.Read.ByteOffset.QuadPart += partExt->StartingOffset;
1288 }
1289 }
1290
1292 return IoCallDriver(partExt->LowerDevice, Irp);
1293}
1294
1297NTAPI
1300 _In_ PIRP Irp)
1301{
1302 PPARTITION_EXTENSION partExt = DeviceObject->DeviceExtension;
1304
1306
1307 if (!partExt->IsFDO)
1308 {
1310
1311 if (!partExt->IsEnumerated)
1312 {
1314 }
1315 else if (ioStack->MinorFunction == IRP_MN_SET_POWER ||
1317 {
1319 }
1320 else
1321 {
1322 status = Irp->IoStatus.Status;
1323 }
1324
1325 Irp->IoStatus.Status = status;
1327 return status;
1328 }
1329 else
1330 {
1332 return PoCallDriver(partExt->LowerDevice, Irp);
1333 }
1334}
1335
1338NTAPI
1341 _In_ PIRP Irp)
1342{
1343 PPARTITION_EXTENSION partExt = DeviceObject->DeviceExtension;
1344 PDEVICE_OBJECT lowerDevice;
1345
1346 // forward to the partition0 device in both cases
1347 if (!partExt->IsFDO)
1348 {
1349 if (!partExt->IsEnumerated)
1350 {
1351 Irp->IoStatus.Status = STATUS_DEVICE_DOES_NOT_EXIST;
1354 }
1355 else
1356 {
1357 PFDO_EXTENSION fdoExtension = partExt->LowerDevice->DeviceExtension;
1358 lowerDevice = fdoExtension->LowerDevice;
1359 }
1360 }
1361 else
1362 {
1363 lowerDevice = partExt->LowerDevice;
1364 }
1365
1367 return IoCallDriver(lowerDevice, Irp);
1368}
1369
1370CODE_SEG("PAGE")
1371VOID
1372NTAPI
1375{
1376
1377}
1378
1379CODE_SEG("INIT")
1381NTAPI
1385{
1386 DriverObject->DriverUnload = PartMgrUnload;
1387 DriverObject->DriverExtension->AddDevice = PartMgrAddDevice;
1390 DriverObject->MajorFunction[IRP_MJ_READ] = PartMgrReadWrite;
1391 DriverObject->MajorFunction[IRP_MJ_WRITE] = PartMgrReadWrite;
1393 DriverObject->MajorFunction[IRP_MJ_PNP] = PartMgrPnp;
1396 DriverObject->MajorFunction[IRP_MJ_POWER] = PartMgrPower;
1397
1398 return STATUS_SUCCESS;
1399}
#define ExAllocatePoolUninitialized
static PIO_STACK_LOCATION IoGetCurrentIrpStackLocation(PIRP Irp)
#define PAGED_CODE()
#define CODE_SEG(...)
unsigned char BOOLEAN
unsigned int UINT32
LONG NTSTATUS
Definition: precomp.h:26
#define ERR(fmt,...)
Definition: debug.h:110
#define PARTITION_ENTRY_UNUSED
Definition: disk.h:86
PDEVICE_OBJECT PhysicalDeviceObject
Definition: btrfs_drv.h:1157
#define FILE_DEVICE_SECURE_OPEN
Definition: cdrw_usr.h:46
#define IRP_MJ_PNP
Definition: cdrw_usr.h:52
_In_ PIRP Irp
Definition: csq.h:116
#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:32
FORCEINLINE PCHAR GetIRPMinorFunctionString(UCHAR MinorFunction)
Definition: driverdbg.h:13
DRIVER_INITIALIZE DriverEntry
Definition: condrv.c:21
#define INFO
Definition: debug.h:89
#define ULONG_PTR
Definition: config.h:101
NTSTATUS PartitionHandleRemove(_In_ PPARTITION_EXTENSION PartExt, _In_ BOOLEAN FinalRemove)
Definition: partition.c:175
NTSTATUS PartitionHandleDeviceControl(_In_ PDEVICE_OBJECT DeviceObject, _In_ PIRP Irp)
Definition: partition.c:449
NTSTATUS PartitionHandlePnp(_In_ PDEVICE_OBJECT DeviceObject, _In_ PIRP Irp)
Definition: partition.c:385
NTSTATUS PartitionCreateDevice(_In_ PDEVICE_OBJECT FDObject, _In_ PPARTITION_INFORMATION_EX PartitionEntry, _In_ UINT32 PdoNumber, _In_ PARTITION_STYLE PartitionStyle, _Out_ PDEVICE_OBJECT *PDO)
Definition: partition.c:15
@ FdoExtension
Definition: precomp.h:48
#define ExAllocatePoolWithTag(hernya, size, tag)
Definition: env_spec_w32.h:350
#define KeInitializeEvent(pEvt, foo, foo2)
Definition: env_spec_w32.h:477
#define DO_DIRECT_IO
Definition: env_spec_w32.h:396
#define ExFreePool(addr)
Definition: env_spec_w32.h:352
#define PagedPool
Definition: env_spec_w32.h:308
#define IOCTL_DISK_GET_DRIVE_GEOMETRY_EX
Definition: ntddk_ex.h:208
#define IOCTL_DISK_GET_PARTITION_INFO_EX
Definition: ntddk_ex.h:206
#define IOCTL_DISK_GET_DRIVE_LAYOUT_EX
Definition: ntddk_ex.h:207
NTSTATUS NTAPI IoCreateDisk(IN PDEVICE_OBJECT DeviceObject, IN PCREATE_DISK Disk)
Definition: fstubex.c:1807
NTSTATUS NTAPI IoWritePartitionTableEx(IN PDEVICE_OBJECT DeviceObject, IN PDRIVE_LAYOUT_INFORMATION_EX DriveLayout)
Definition: fstubex.c:2466
NTSTATUS NTAPI IoReadPartitionTableEx(IN PDEVICE_OBJECT DeviceObject, IN PDRIVE_LAYOUT_INFORMATION_EX *DriveLayout)
Definition: fstubex.c:2279
MxDeviceObject deviceObject
GLuint GLuint GLsizei GLenum type
Definition: gl.h:1545
GLsizeiptr size
Definition: glext.h:5919
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
DRIVER_DISPATCH ForwardIrpAndForget
Definition: i8042prt.h:341
#define ASSERT(a)
Definition: mode.c:44
#define ExFreePoolWithTag(_P, _T)
Definition: module.h:1109
struct _PARTITION_INFORMATION_EX PARTITION_INFORMATION_EX
@ PARTITION_STYLE_GPT
Definition: imports.h:202
@ PARTITION_STYLE_MBR
Definition: imports.h:201
#define min(a, b)
Definition: monoChain.cc:55
#define _Inout_
Definition: ms_sal.h:378
#define _Out_
Definition: ms_sal.h:345
#define _In_
Definition: ms_sal.h:308
#define FILE_AUTOGENERATED_DEVICE_NAME
Definition: iotypes.h:138
DRIVER_DISPATCH(nfs41_FsdDispatch)
NTSYSAPI VOID NTAPI RtlInitUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
NTSYSAPI VOID NTAPI RtlFreeUnicodeString(PUNICODE_STRING UnicodeString)
#define FILE_REMOVABLE_MEDIA
Definition: nt_native.h:807
#define IOCTL_DISK_SET_DRIVE_LAYOUT
Definition: ntdddisk.h:205
#define IsContainerPartition(PartitionType)
Definition: ntdddisk.h:316
#define IOCTL_DISK_GET_DRIVE_LAYOUT
Definition: ntdddisk.h:91
#define IOCTL_DISK_CREATE_DISK
Definition: ntdddisk.h:55
struct _PARTITION_INFORMATION PARTITION_INFORMATION
#define IOCTL_DISK_SET_DRIVE_LAYOUT_EX
Definition: ntdddisk.h:208
#define IOCTL_DISK_GET_PARTITION_INFO
Definition: ntdddisk.h:106
#define IOCTL_DISK_DELETE_DRIVE_LAYOUT
Definition: ntdddisk.h:58
#define IOCTL_DISK_UPDATE_PROPERTIES
Definition: ntdddisk.h:242
#define IOCTL_STORAGE_GET_DEVICE_NUMBER
Definition: ntddstor.h:143
@ SynchronizationEvent
#define IRP_MN_SURPRISE_REMOVAL
Definition: ntifs_ex.h:408
#define IoSkipCurrentIrpStackLocation(Irp)
Definition: ntifs_ex.h:421
PDEVICE_OBJECT NTAPI IoAttachDeviceToDeviceStack(IN PDEVICE_OBJECT SourceDevice, IN PDEVICE_OBJECT TargetDevice)
Definition: device.c:966
NTSTATUS NTAPI IoCreateDevice(IN PDRIVER_OBJECT DriverObject, IN ULONG DeviceExtensionSize, IN PUNICODE_STRING DeviceName, IN DEVICE_TYPE DeviceType, IN ULONG DeviceCharacteristics, IN BOOLEAN Exclusive, OUT PDEVICE_OBJECT *DeviceObject)
Definition: device.c:1031
VOID NTAPI IoDetachDevice(IN PDEVICE_OBJECT TargetDevice)
Definition: device.c:1296
VOID NTAPI IoDeleteDevice(IN PDEVICE_OBJECT DeviceObject)
Definition: device.c:1251
NTSTATUS NTAPI IoRegisterDeviceInterface(IN PDEVICE_OBJECT PhysicalDeviceObject, IN CONST GUID *InterfaceClassGuid, IN PUNICODE_STRING ReferenceString OPTIONAL, OUT PUNICODE_STRING SymbolicLinkName)
Definition: deviface.c:955
NTSTATUS NTAPI IoSetDeviceInterfaceState(IN PUNICODE_STRING SymbolicLinkName, IN BOOLEAN Enable)
Definition: deviface.c:1311
#define IoCompleteRequest
Definition: irp.c:1240
BOOLEAN NTAPI IoForwardIrpSynchronously(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
Definition: irp.c:1625
#define IoCallDriver
Definition: irp.c:1225
VOID NTAPI PoStartNextPowerIrp(IN PIRP Irp)
Definition: power.c:758
#define STATUS_DEVICE_REMOVED
Definition: ntstatus.h:809
#define STATUS_DEVICE_DOES_NOT_EXIST
Definition: ntstatus.h:428
static PDRIVE_LAYOUT_INFORMATION PartMgrConvertExtendedToLayout(_In_ CONST PDRIVE_LAYOUT_INFORMATION_EX LayoutEx)
Definition: partmgr.c:20
static NTSTATUS FdoIoctlDiskCreateDisk(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:785
static PDRIVE_LAYOUT_INFORMATION_EX PartMgrConvertLayoutToExtended(_In_ CONST PDRIVE_LAYOUT_INFORMATION Layout)
Definition: partmgr.c:72
static NTSTATUS NTAPI PartMgrAddDevice(_In_ PDRIVER_OBJECT DriverObject, _In_ PDEVICE_OBJECT PhysicalDeviceObject)
Definition: partmgr.c:1076
static NTSTATUS FdoIoctlDiskSetDriveLayout(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:575
static NTSTATUS FdoHandleRemoveDevice(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:1018
static NTSTATUS FdoHandleDeviceRelations(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:935
VOID NTAPI PartMgrUnload(_In_ PDRIVER_OBJECT DriverObject)
Definition: partmgr.c:1373
static NTSTATUS NTAPI PartMgrReadWrite(_In_ PDEVICE_OBJECT DeviceObject, _In_ PIRP Irp)
Definition: partmgr.c:1270
static NTSTATUS PartMgrGetDriveLayout(_In_ PFDO_EXTENSION FdoExtension, _Out_ PDRIVE_LAYOUT_INFORMATION_EX *DriveLayout)
Definition: partmgr.c:322
static NTSTATUS FdoIoctlDiskDeleteDriveLayout(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:811
static VOID PartMgrUpdatePartitionDevices(_In_ PFDO_EXTENSION FdoExtension, _Inout_ PDRIVE_LAYOUT_INFORMATION_EX NewLayout)
Definition: partmgr.c:120
static NTSTATUS FdoIoctlDiskGetPartitionInfoEx(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:456
static NTSTATUS NTAPI PartMgrPnp(_In_ PDEVICE_OBJECT DeviceObject, _In_ PIRP Irp)
Definition: partmgr.c:1199
static NTSTATUS FdoIoctlDiskUpdateProperties(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:768
DRIVER_DISPATCH PartMgrPower
Definition: partmgr.c:1295
static NTSTATUS FdoIoctlDiskGetPartitionInfo(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:421
static NTSTATUS FdoIoctlDiskGetDriveLayoutEx(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:539
static NTSTATUS FdoHandleSurpriseRemoval(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:1044
DRIVER_DISPATCH PartMgrShutdownFlush
Definition: partmgr.c:1336
static NTSTATUS FdoHandleStartDevice(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:833
static NTSTATUS FdoIoctlDiskGetDriveGeometryEx(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:358
static NTSTATUS PartMgrRefreshDiskData(_In_ PFDO_EXTENSION FdoExtension)
Definition: partmgr.c:886
static NTSTATUS FdoIoctlDiskSetDriveLayoutEx(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:659
static NTSTATUS FdoIoctlDiskGetDriveLayout(_In_ PFDO_EXTENSION FdoExtension, _In_ PIRP Irp)
Definition: partmgr.c:486
static NTSTATUS NTAPI PartMgrDeviceControl(_In_ PDEVICE_OBJECT DeviceObject, _In_ PIRP Irp)
Definition: partmgr.c:1125
#define TAG_PARTMGR
Definition: partmgr.h:23
FORCEINLINE VOID PartMgrReleaseLayoutLock(_In_ PFDO_EXTENSION FDOExtension)
Definition: partmgr.h:187
FORCEINLINE VOID PartMgrAcquireLayoutLock(_In_ PFDO_EXTENSION FDOExtension)
Definition: partmgr.h:177
FORCEINLINE BOOLEAN VerifyIrpInBufferSize(_In_ PIRP Irp, _In_ SIZE_T Size)
Definition: partmgr.h:162
NTSTATUS IssueSyncIoControlRequest(_In_ UINT32 IoControlCode, _In_ PDEVICE_OBJECT DeviceObject, _In_ PVOID InputBuffer, _In_ ULONG InputBufferLength, _In_ PVOID OutputBuffer, _In_ ULONG OutputBufferLength, _In_ BOOLEAN InternalDeviceIoControl)
Definition: utils.c:19
FORCEINLINE BOOLEAN VerifyIrpOutBufferSize(_In_ PIRP Irp, _In_ SIZE_T Size)
Definition: partmgr.h:147
#define CONST
Definition: pedump.c:81
VOID NTAPI IoInvalidateDeviceRelations(IN PDEVICE_OBJECT DeviceObject, IN DEVICE_RELATION_TYPE Type)
Definition: pnpmgr.c:1772
NTSTATUS NTAPI IoReportTargetDeviceChangeAsynchronous(IN PDEVICE_OBJECT PhysicalDeviceObject, IN PVOID NotificationStructure, IN PDEVICE_CHANGE_COMPLETE_CALLBACK Callback OPTIONAL, IN PVOID Context OPTIONAL)
Definition: pnpreport.c:498
#define FILE_DEVICE_BUS_EXTENDER
Definition: winioctl.h:148
#define IRP_MJ_CLOSE
Definition: rdpdr.c:45
#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
#define IRP_MJ_CREATE
Definition: rdpdr.c:44
#define STATUS_SUCCESS
Definition: shellext.h:65
#define STATUS_BUFFER_TOO_SMALL
Definition: shellext.h:69
#define TRACE(s)
Definition: solgame.cpp:4
PVOID DeviceExtension
Definition: env_spec_w32.h:418
PDEVICE_OBJECT Objects[1]
Definition: iotypes.h:2163
DISK_PARTITION_INFO Partition
Definition: disk.c:3667
DISK_GEOMETRY Geometry
Definition: winioctl.h:330
LARGE_INTEGER DiskSize
Definition: winioctl.h:331
ULONG BytesPerSector
Definition: ntdddisk.h:409
PARTITION_INFORMATION PartitionEntry[1]
Definition: ntdddisk.h:426
KEVENT SyncEvent
Definition: partmgr.h:40
PDEVICE_OBJECT PhysicalDiskDO
Definition: partmgr.h:39
PDEVICE_OBJECT DeviceObject
Definition: partmgr.h:37
PDEVICE_OBJECT LowerDevice
Definition: partmgr.h:38
BOOLEAN IsFDO
Definition: partmgr.h:36
struct _IO_STACK_LOCATION::@1564::@1565 DeviceIoControl
union _IO_STACK_LOCATION::@1564 Parameters
struct _IO_STACK_LOCATION::@3978::@4003 QueryDeviceRelations
struct _IO_STACK_LOCATION::@3978::@3982 Read
struct _PARTITION_EXTENSION::@1319::@1322 Mbr
UINT64 StartingOffset
Definition: partmgr.h:72
PDEVICE_OBJECT LowerDevice
Definition: partmgr.h:69
struct _PARTITION_EXTENSION::@1319::@1321 Gpt
SINGLE_LIST_ENTRY ListEntry
Definition: partmgr.h:74
UINT32 DetectedNumber
Definition: partmgr.h:76
BOOLEAN Attached
Definition: partmgr.h:80
UINT64 PartitionLength
Definition: partmgr.h:73
BOOLEAN IsEnumerated
Definition: partmgr.h:78
UINT32 OnDiskNumber
Definition: partmgr.h:77
PDEVICE_OBJECT DeviceObject
Definition: partmgr.h:68
LARGE_INTEGER StartingOffset
Definition: imports.h:221
PARTITION_STYLE PartitionStyle
Definition: imports.h:220
PARTITION_INFORMATION_MBR Mbr
Definition: imports.h:226
PARTITION_INFORMATION_GPT Gpt
Definition: imports.h:227
LARGE_INTEGER PartitionLength
Definition: imports.h:222
LARGE_INTEGER StartingOffset
Definition: ntdddisk.h:413
LARGE_INTEGER PartitionLength
Definition: ntdddisk.h:414
BOOLEAN RecognizedPartition
Definition: ntdddisk.h:419
BOOLEAN RewritePartition
Definition: ntdddisk.h:420
Definition: ntbasedef.h:628
struct _SINGLE_LIST_ENTRY * Next
Definition: ntbasedef.h:629
Definition: ps.c:97
#define FIELD_OFFSET(t, f)
Definition: typedefs.h:255
#define NTAPI
Definition: typedefs.h:36
#define RtlCopyMemory(Destination, Source, Length)
Definition: typedefs.h:263
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:262
#define RtlMoveMemory(Destination, Source, Length)
Definition: typedefs.h:264
#define CONTAINING_RECORD(address, type, field)
Definition: typedefs.h:260
#define STATUS_INVALID_DEVICE_REQUEST
Definition: udferr_usr.h:138
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
#define STATUS_INFO_LENGTH_MISMATCH
Definition: udferr_usr.h:133
#define STATUS_INSUFFICIENT_RESOURCES
Definition: udferr_usr.h:158
LONGLONG QuadPart
Definition: typedefs.h:114
_In_ PDEVICE_OBJECT DeviceObject
Definition: wdfdevice.h:2055
_Must_inspect_result_ _In_ PDRIVER_OBJECT _In_ PCUNICODE_STRING RegistryPath
Definition: wdfdriver.h:215
_Must_inspect_result_ _In_ PDRIVER_OBJECT DriverObject
Definition: wdfdriver.h:213
#define IRP_MN_CANCEL_STOP_DEVICE
@ BusRelations
Definition: iotypes.h:2152
#define IO_NO_INCREMENT
Definition: iotypes.h:598
#define IRP_MN_START_DEVICE
#define IRP_MN_REMOVE_DEVICE
#define IRP_MN_QUERY_DEVICE_RELATIONS
#define DO_POWER_PAGABLE
#define IRP_MN_QUERY_STOP_DEVICE
#define IRP_MN_SET_POWER
#define IRP_MJ_FLUSH_BUFFERS
#define IRP_MN_CANCEL_REMOVE_DEVICE
#define IRP_MN_STOP_DEVICE
#define IRP_MJ_SHUTDOWN
#define IRP_MJ_POWER
enum _DEVICE_RELATION_TYPE DEVICE_RELATION_TYPE
#define IRP_MN_QUERY_POWER
#define IRP_MN_QUERY_REMOVE_DEVICE
#define ObReferenceObject
Definition: obfuncs.h:204