xref: /reactos/drivers/storage/partmgr/partmgr.h (revision e80cd676)
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 header
5  * COPYRIGHT:   2020 Victor Perevertkin (victor.perevertkin@reactos.org)
6  */
7 
8 #ifndef _PARTMGR_H_
9 #define _PARTMGR_H_
10 
11 #include <ntifs.h>
12 #include <mountdev.h>
13 #include <ntddvol.h>
14 #include <ntdddisk.h>
15 #include <ndk/psfuncs.h>
16 #include <ndk/section_attribs.h>
17 #include <ioevent.h>
18 #include <stdio.h>
19 #include <debug/driverdbg.h>
20 
21 #include "debug.h"
22 
23 #define TAG_PARTMGR 'MtrP'
24 
25 // from disk.sys
26 typedef struct _DISK_GEOMETRY_EX_INTERNAL
27 {
28     DISK_GEOMETRY Geometry;
29     INT64 DiskSize;
30     DISK_PARTITION_INFO Partition;
31     DISK_DETECTION_INFO Detection;
32 } DISK_GEOMETRY_EX_INTERNAL, *PDISK_GEOMETRY_EX_INTERNAL;
33 
34 // Unique ID data for basic (disk partition-based) volumes.
35 // It is stored in the MOUNTDEV_UNIQUE_ID::UniqueId member
36 // as an array of bytes.
37 #include <pshpack1.h>
38 typedef union _BASIC_VOLUME_UNIQUE_ID
39 {
40     struct
41     {
42         ULONG Signature;
43         ULONGLONG StartingOffset;
44     } Mbr;
45     struct
46     {
47         ULONGLONG Signature; // UCHAR[8] // "DMIO:ID:"
48         GUID PartitionGuid;
49     } Gpt;
50 } BASIC_VOLUME_UNIQUE_ID, *PBASIC_VOLUME_UNIQUE_ID;
51 #include <poppack.h>
52 C_ASSERT(RTL_FIELD_SIZE(BASIC_VOLUME_UNIQUE_ID, Mbr) == 0x0C);
53 C_ASSERT(RTL_FIELD_SIZE(BASIC_VOLUME_UNIQUE_ID, Gpt) == 0x18);
54 
55 #define DMIO_ID_SIGNATURE   (*(ULONGLONG*)"DMIO:ID:")
56 
57 typedef struct _FDO_EXTENSION
58 {
59     BOOLEAN IsFDO;
60     PDEVICE_OBJECT DeviceObject;
61     PDEVICE_OBJECT LowerDevice;
62     PDEVICE_OBJECT PhysicalDiskDO;
63     KEVENT SyncEvent;
64 
65     BOOLEAN LayoutValid;
66     PDRIVE_LAYOUT_INFORMATION_EX LayoutCache;
67 
68     SINGLE_LIST_ENTRY PartitionList;
69     UINT32 EnumeratedPartitionsTotal;
70     BOOLEAN IsSuperFloppy;
71 
72     struct {
73         UINT64 DiskSize;
74         UINT32 DeviceNumber;
75         UINT32 BytesPerSector;
76         PARTITION_STYLE PartitionStyle;
77         union {
78             struct {
79                 UINT32 Signature;
80             } Mbr;
81             struct {
82                 GUID DiskId;
83             } Gpt;
84         };
85     } DiskData;
86     UNICODE_STRING DiskInterfaceName;
87 } FDO_EXTENSION, *PFDO_EXTENSION;
88 
89 typedef struct _PARTITION_EXTENSION
90 {
91     BOOLEAN IsFDO;
92     PDEVICE_OBJECT DeviceObject;
93     PDEVICE_OBJECT LowerDevice;
94     PDEVICE_OBJECT Part0Device;
95 
96     UINT64 StartingOffset;
97     UINT64 PartitionLength;
98     SINGLE_LIST_ENTRY ListEntry;
99 
100     UINT32 VolumeNumber; // Volume number in the "\Device\HarddiskVolumeN" device name
101     UINT32 DetectedNumber;
102     UINT32 OnDiskNumber; // partition number for issuing Io requests to the kernel
103     BOOLEAN IsEnumerated; // reported via IRP_MN_QUERY_DEVICE_RELATIONS
104     BOOLEAN SymlinkCreated;
105     BOOLEAN Attached; // attached to PartitionList of the FDO
106     union
107     {
108         struct
109         {
110             GUID PartitionType;
111             GUID PartitionId;
112             UINT64 Attributes;
113             WCHAR Name[36];
114         } Gpt;
115         struct
116         {
117             UINT8 PartitionType;
118             BOOLEAN BootIndicator;
119             BOOLEAN RecognizedPartition;
120             UINT32 HiddenSectors;
121         } Mbr;
122     };
123     UNICODE_STRING PartitionInterfaceName;
124     UNICODE_STRING VolumeInterfaceName;
125     UNICODE_STRING DeviceName;
126 } PARTITION_EXTENSION, *PPARTITION_EXTENSION;
127 
128 CODE_SEG("PAGE")
129 NTSTATUS
130 PartitionCreateDevice(
131     _In_ PDEVICE_OBJECT FDObject,
132     _In_ PPARTITION_INFORMATION_EX PartitionEntry,
133     _In_ UINT32 OnDiskNumber,
134     _In_ PARTITION_STYLE PartitionStyle,
135     _Out_ PDEVICE_OBJECT *PDO);
136 
137 CODE_SEG("PAGE")
138 NTSTATUS
139 PartitionHandleRemove(
140     _In_ PPARTITION_EXTENSION PartExt,
141     _In_ BOOLEAN FinalRemove);
142 
143 CODE_SEG("PAGE")
144 NTSTATUS
145 PartitionHandlePnp(
146     _In_ PDEVICE_OBJECT DeviceObject,
147     _In_ PIRP Irp);
148 
149 NTSTATUS
150 PartitionHandleDeviceControl(
151     _In_ PDEVICE_OBJECT DeviceObject,
152     _In_ PIRP Irp);
153 
154 NTSTATUS
155 NTAPI
156 ForwardIrpAndForget(
157     _In_ PDEVICE_OBJECT DeviceObject,
158     _In_ PIRP Irp);
159 
160 NTSTATUS
161 IssueSyncIoControlRequest(
162     _In_ UINT32 IoControlCode,
163     _In_ PDEVICE_OBJECT DeviceObject,
164     _In_ PVOID InputBuffer,
165     _In_ ULONG InputBufferLength,
166     _In_ PVOID OutputBuffer,
167     _In_ ULONG OutputBufferLength,
168     _In_ BOOLEAN InternalDeviceIoControl);
169 
170 FORCEINLINE
171 BOOLEAN
VerifyIrpOutBufferSize(_In_ PIRP Irp,_In_ SIZE_T Size)172 VerifyIrpOutBufferSize(
173     _In_ PIRP Irp,
174     _In_ SIZE_T Size)
175 {
176     PIO_STACK_LOCATION ioStack = IoGetCurrentIrpStackLocation(Irp);
177     if (ioStack->Parameters.DeviceIoControl.OutputBufferLength < Size)
178     {
179         Irp->IoStatus.Information = Size;
180         return FALSE;
181     }
182     return TRUE;
183 }
184 
185 FORCEINLINE
186 BOOLEAN
VerifyIrpInBufferSize(_In_ PIRP Irp,_In_ SIZE_T Size)187 VerifyIrpInBufferSize(
188     _In_ PIRP Irp,
189     _In_ SIZE_T Size)
190 {
191     PIO_STACK_LOCATION ioStack = IoGetCurrentIrpStackLocation(Irp);
192     if (ioStack->Parameters.DeviceIoControl.InputBufferLength < Size)
193     {
194         Irp->IoStatus.Information = Size;
195         return FALSE;
196     }
197     return TRUE;
198 }
199 
200 FORCEINLINE
201 VOID
PartMgrAcquireLayoutLock(_In_ PFDO_EXTENSION FDOExtension)202 PartMgrAcquireLayoutLock(
203     _In_ PFDO_EXTENSION FDOExtension)
204 {
205     PAGED_CODE();
206 
207     KeWaitForSingleObject(&FDOExtension->SyncEvent, Executive, KernelMode, FALSE, NULL);
208 }
209 
210 FORCEINLINE
211 VOID
PartMgrReleaseLayoutLock(_In_ PFDO_EXTENSION FDOExtension)212 PartMgrReleaseLayoutLock(
213     _In_ PFDO_EXTENSION FDOExtension)
214 {
215     PAGED_CODE();
216 
217     KeSetEvent(&FDOExtension->SyncEvent, IO_NO_INCREMENT, FALSE);
218 }
219 
220 #endif // _PARTMGR_H_
221