Synchronize up to trunk's revision r57756.
[reactos.git] / drivers / filesystems / cdfs / volinfo.c
1 /*
2 * ReactOS kernel
3 * Copyright (C) 2002, 2003 ReactOS Team
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License along
16 * with this program; if not, write to the Free Software Foundation, Inc.,
17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 */
19 /* $Id$
20 *
21 * COPYRIGHT: See COPYING in the top level directory
22 * PROJECT: ReactOS kernel
23 * FILE: services/fs/vfat/volume.c
24 * PURPOSE: CDROM (ISO 9660) filesystem driver
25 * PROGRAMMER: Art Yerkes
26 * Eric Kohl
27 */
28
29 /* INCLUDES *****************************************************************/
30
31 #include "cdfs.h"
32
33 #define NDEBUG
34 #include <debug.h>
35
36 /* FUNCTIONS ****************************************************************/
37
38 static NTSTATUS
39 CdfsGetFsVolumeInformation(PDEVICE_OBJECT DeviceObject,
40 PFILE_FS_VOLUME_INFORMATION FsVolumeInfo,
41 PULONG BufferLength)
42 {
43 DPRINT("CdfsGetFsVolumeInformation() called\n");
44 DPRINT("FsVolumeInfo = %p\n", FsVolumeInfo);
45 DPRINT("BufferLength %lu\n", *BufferLength);
46
47 DPRINT("Vpb %p\n", DeviceObject->Vpb);
48
49 DPRINT("Required length %lu\n", (sizeof(FILE_FS_VOLUME_INFORMATION) + DeviceObject->Vpb->VolumeLabelLength));
50 DPRINT("LabelLength %hu\n", DeviceObject->Vpb->VolumeLabelLength);
51 DPRINT("Label %*.S\n", DeviceObject->Vpb->VolumeLabelLength / sizeof(WCHAR), DeviceObject->Vpb->VolumeLabel);
52
53 if (*BufferLength < sizeof(FILE_FS_VOLUME_INFORMATION))
54 return STATUS_INFO_LENGTH_MISMATCH;
55
56 if (*BufferLength < (sizeof(FILE_FS_VOLUME_INFORMATION) + DeviceObject->Vpb->VolumeLabelLength))
57 return STATUS_BUFFER_OVERFLOW;
58
59 /* valid entries */
60 FsVolumeInfo->VolumeSerialNumber = DeviceObject->Vpb->SerialNumber;
61 FsVolumeInfo->VolumeLabelLength = DeviceObject->Vpb->VolumeLabelLength;
62 memcpy(FsVolumeInfo->VolumeLabel,
63 DeviceObject->Vpb->VolumeLabel,
64 DeviceObject->Vpb->VolumeLabelLength);
65
66 /* dummy entries */
67 FsVolumeInfo->VolumeCreationTime.QuadPart = 0;
68 FsVolumeInfo->SupportsObjects = FALSE;
69
70 DPRINT("Finished FsdGetFsVolumeInformation()\n");
71
72 *BufferLength -= (sizeof(FILE_FS_VOLUME_INFORMATION) + DeviceObject->Vpb->VolumeLabelLength);
73
74 DPRINT("BufferLength %lu\n", *BufferLength);
75
76 return(STATUS_SUCCESS);
77 }
78
79
80 static NTSTATUS
81 CdfsGetFsAttributeInformation(PDEVICE_EXTENSION DeviceExt,
82 PFILE_FS_ATTRIBUTE_INFORMATION FsAttributeInfo,
83 PULONG BufferLength)
84 {
85 DPRINT("CdfsGetFsAttributeInformation()\n");
86 DPRINT("FsAttributeInfo = %p\n", FsAttributeInfo);
87 DPRINT("BufferLength %lu\n", *BufferLength);
88 DPRINT("Required length %lu\n", (sizeof(FILE_FS_ATTRIBUTE_INFORMATION) + 8));
89
90 if (*BufferLength < sizeof (FILE_FS_ATTRIBUTE_INFORMATION))
91 return STATUS_INFO_LENGTH_MISMATCH;
92
93 if (*BufferLength < (sizeof(FILE_FS_ATTRIBUTE_INFORMATION) + 8))
94 return STATUS_BUFFER_OVERFLOW;
95
96 FsAttributeInfo->FileSystemAttributes =
97 FILE_CASE_PRESERVED_NAMES | FILE_UNICODE_ON_DISK;
98 FsAttributeInfo->MaximumComponentNameLength = 255;
99 FsAttributeInfo->FileSystemNameLength = 8;
100
101 memcpy(FsAttributeInfo->FileSystemName, L"CDFS", 8);
102
103 DPRINT("Finished FsdGetFsAttributeInformation()\n");
104
105 *BufferLength -= (sizeof(FILE_FS_ATTRIBUTE_INFORMATION) + 8);
106 DPRINT("BufferLength %lu\n", *BufferLength);
107
108 return(STATUS_SUCCESS);
109 }
110
111
112 static NTSTATUS
113 CdfsGetFsSizeInformation(PDEVICE_OBJECT DeviceObject,
114 PFILE_FS_SIZE_INFORMATION FsSizeInfo,
115 PULONG BufferLength)
116 {
117 PDEVICE_EXTENSION DeviceExt;
118 NTSTATUS Status = STATUS_SUCCESS;
119
120 DPRINT("CdfsGetFsSizeInformation()\n");
121 DPRINT("FsSizeInfo = %p\n", FsSizeInfo);
122
123 if (*BufferLength < sizeof(FILE_FS_SIZE_INFORMATION))
124 return(STATUS_BUFFER_OVERFLOW);
125
126 DeviceExt = DeviceObject->DeviceExtension;
127
128 FsSizeInfo->AvailableAllocationUnits.QuadPart = 0;
129 FsSizeInfo->TotalAllocationUnits.QuadPart = DeviceExt->CdInfo.VolumeSpaceSize;
130 FsSizeInfo->SectorsPerAllocationUnit = 1;
131 FsSizeInfo->BytesPerSector = BLOCKSIZE;
132
133 DPRINT("Finished FsdGetFsSizeInformation()\n");
134 if (NT_SUCCESS(Status))
135 *BufferLength -= sizeof(FILE_FS_SIZE_INFORMATION);
136
137 return(Status);
138 }
139
140
141 static NTSTATUS
142 CdfsGetFsDeviceInformation
143 (
144 PDEVICE_OBJECT DeviceObject,
145 PFILE_FS_DEVICE_INFORMATION FsDeviceInfo,
146 PULONG BufferLength
147 )
148 {
149 DPRINT("CdfsGetFsDeviceInformation()\n");
150 DPRINT("FsDeviceInfo = %p\n", FsDeviceInfo);
151 DPRINT("BufferLength %lu\n", *BufferLength);
152 DPRINT("Required length %lu\n", sizeof(FILE_FS_DEVICE_INFORMATION));
153
154 if (*BufferLength < sizeof(FILE_FS_DEVICE_INFORMATION))
155 return(STATUS_BUFFER_OVERFLOW);
156
157 FsDeviceInfo->DeviceType = FILE_DEVICE_CD_ROM;
158 FsDeviceInfo->Characteristics = DeviceObject->Characteristics;
159
160 DPRINT("FsdGetFsDeviceInformation() finished.\n");
161
162 *BufferLength -= sizeof(FILE_FS_DEVICE_INFORMATION);
163 DPRINT("BufferLength %lu\n", *BufferLength);
164
165 return(STATUS_SUCCESS);
166 }
167
168
169 NTSTATUS NTAPI
170 CdfsQueryVolumeInformation(PDEVICE_OBJECT DeviceObject,
171 PIRP Irp)
172 {
173 FS_INFORMATION_CLASS FsInformationClass;
174 PIO_STACK_LOCATION Stack;
175 NTSTATUS Status = STATUS_SUCCESS;
176 PVOID SystemBuffer;
177 ULONG BufferLength;
178
179 DPRINT("CdfsQueryVolumeInformation() called\n");
180
181 Stack = IoGetCurrentIrpStackLocation(Irp);
182 FsInformationClass = Stack->Parameters.QueryVolume.FsInformationClass;
183 BufferLength = Stack->Parameters.QueryVolume.Length;
184 SystemBuffer = Irp->AssociatedIrp.SystemBuffer;
185
186 DPRINT("FsInformationClass %d\n", FsInformationClass);
187 DPRINT("SystemBuffer %x\n", SystemBuffer);
188
189 switch (FsInformationClass)
190 {
191 case FileFsVolumeInformation:
192 Status = CdfsGetFsVolumeInformation(DeviceObject,
193 SystemBuffer,
194 &BufferLength);
195 break;
196
197 case FileFsAttributeInformation:
198 Status = CdfsGetFsAttributeInformation(DeviceObject->DeviceExtension,
199 SystemBuffer,
200 &BufferLength);
201 break;
202
203 case FileFsSizeInformation:
204 Status = CdfsGetFsSizeInformation(DeviceObject,
205 SystemBuffer,
206 &BufferLength);
207 break;
208
209 case FileFsDeviceInformation:
210 Status = CdfsGetFsDeviceInformation(DeviceObject,
211 SystemBuffer,
212 &BufferLength);
213 break;
214
215 default:
216 Status = STATUS_NOT_SUPPORTED;
217 }
218
219 Irp->IoStatus.Status = Status;
220 if (NT_SUCCESS(Status))
221 Irp->IoStatus.Information =
222 Stack->Parameters.QueryVolume.Length - BufferLength;
223 else
224 Irp->IoStatus.Information = 0;
225 IoCompleteRequest(Irp, IO_NO_INCREMENT);
226
227 return(Status);
228 }
229
230
231 NTSTATUS NTAPI
232 CdfsSetVolumeInformation(PDEVICE_OBJECT DeviceObject,
233 PIRP Irp)
234 {
235 DPRINT("CdfsSetVolumeInformation() called\n");
236
237 Irp->IoStatus.Status = STATUS_NOT_SUPPORTED;
238 Irp->IoStatus.Information = 0;
239 IoCompleteRequest(Irp, IO_NO_INCREMENT);
240
241 return(STATUS_NOT_SUPPORTED);
242 }
243
244 /* EOF */