xref: /reactos/drivers/filters/fltmgr/Volume.c (revision 64daf542)
1 /*
2 * PROJECT:         Filesystem Filter Manager
3 * LICENSE:         GPL - See COPYING in the top level directory
4 * FILE:            drivers/filters/fltmgr/Context.c
5 * PURPOSE:         Contains routines for the volume
6 * PROGRAMMERS:     Ged Murphy (gedmurphy@reactos.org)
7 */
8 
9 /* INCLUDES ******************************************************************/
10 
11 #include "fltmgr.h"
12 #include "fltmgrint.h"
13 
14 #define NDEBUG
15 #include <debug.h>
16 
17 
18 /* DATA *********************************************************************/
19 
20 
21 
22 /* EXPORTED FUNCTIONS ******************************************************/
23 
24 NTSTATUS
25 FLTAPI
26 FltGetVolumeProperties(
27     _In_ PFLT_VOLUME Volume,
28     _Out_writes_bytes_to_opt_(VolumePropertiesLength, *LengthReturned) PFLT_VOLUME_PROPERTIES VolumeProperties,
29     _In_ ULONG VolumePropertiesLength,
30     _Out_ PULONG LengthReturned
31 )
32 {
33     ULONG BufferRequired;
34     ULONG BytesWritten;
35     PCHAR Ptr;
36     NTSTATUS Status;
37 
38     /* Calculate the required buffer size */
39     BufferRequired = sizeof(FLT_VOLUME_PROPERTIES) +
40                      Volume->CDODriverName.Length +
41                      Volume->DeviceName.Length +
42                      Volume->CDODeviceName.Length;
43 
44     /* If we don't have enough buffer to fill in the fixed struct, return with the required size */
45     if (VolumePropertiesLength < sizeof(FLT_VOLUME_PROPERTIES))
46     {
47         *LengthReturned = BufferRequired;
48         return STATUS_BUFFER_TOO_SMALL;
49     }
50 
51     /* Clear out the buffer */
52     RtlZeroMemory(VolumeProperties, sizeof(FLT_VOLUME_PROPERTIES));
53 
54     /* Fill in the fixed data */
55     VolumeProperties->DeviceType = Volume->DeviceObject->DeviceType;
56     VolumeProperties->DeviceObjectFlags = Volume->DeviceObject->Flags;
57     VolumeProperties->AlignmentRequirement = Volume->DeviceObject->AlignmentRequirement;
58     VolumeProperties->SectorSize = Volume->DeviceObject->SectorSize;
59     if (Volume->DiskDeviceObject)
60     {
61         VolumeProperties->DeviceCharacteristics = Volume->DiskDeviceObject->Characteristics;
62     }
63     else
64     {
65         VolumeProperties->DeviceCharacteristics = Volume->DeviceObject->Characteristics;
66     }
67 
68     /* So far we've written the fixed struct data */
69     BytesWritten = sizeof(FLT_VOLUME_PROPERTIES);
70     Ptr = (PCHAR)(VolumeProperties + 1);
71 
72     /* Make sure we have enough room to add the dynamic data */
73     if (VolumePropertiesLength >= BufferRequired)
74     {
75         /* Add the FS device name */
76         VolumeProperties->FileSystemDeviceName.Length = 0;
77         VolumeProperties->FileSystemDeviceName.MaximumLength = Volume->CDODeviceName.Length;
78         VolumeProperties->FileSystemDeviceName.Buffer = (PWCH)Ptr;
79         RtlCopyUnicodeString(&VolumeProperties->FileSystemDeviceName, &Volume->CDODeviceName);
80         Ptr += VolumeProperties->FileSystemDeviceName.Length;
81 
82         /* Add the driver name */
83         VolumeProperties->FileSystemDriverName.Length = 0;
84         VolumeProperties->FileSystemDriverName.MaximumLength = Volume->CDODriverName.Length;
85         VolumeProperties->FileSystemDriverName.Buffer = (PWCH)Ptr;
86         RtlCopyUnicodeString(&VolumeProperties->FileSystemDriverName, &Volume->CDODriverName);
87         Ptr += VolumeProperties->FileSystemDriverName.Length;
88 
89         /* Add the volume name */
90         VolumeProperties->RealDeviceName.Length = 0;
91         VolumeProperties->RealDeviceName.MaximumLength = Volume->DeviceName.Length;
92         VolumeProperties->RealDeviceName.Buffer = (PWCH)Ptr;
93         RtlCopyUnicodeString(&VolumeProperties->RealDeviceName, &Volume->DeviceName);
94 
95         BytesWritten = BufferRequired;
96 
97         Status = STATUS_SUCCESS;
98     }
99     else
100     {
101         Status = STATUS_BUFFER_OVERFLOW;
102     }
103 
104     /* Set the number of bytes we wrote and return */
105     *LengthReturned = BytesWritten;
106     return Status;
107 }
108 
109 
110 /* INTERNAL FUNCTIONS ******************************************************/