1 /* $Id: rawfs.c,v 1.3 2003/06/07 11:34:36 chorns Exp $
3 * COPYRIGHT: See COPYING in the top level directory
4 * PROJECT: ReactOS kernel
5 * FILE: ntoskrnl/io/rawfs.c
6 * PURPOSE: Raw filesystem driver
7 * PROGRAMMER: Casper S. Hornstrup (chorns@users.sourceforge.net)
12 /* INCLUDES *****************************************************************/
14 #include <ddk/ntddk.h>
15 #include <ddk/ntifs.h>
16 #include <reactos/bugcodes.h>
19 #include <internal/debug.h>
21 /* TYPES *******************************************************************/
23 typedef struct _RAWFS_GLOBAL_DATA
25 PDRIVER_OBJECT DriverObject
;
26 PDEVICE_OBJECT DeviceObject
;
28 ERESOURCE VolumeListLock
;
29 LIST_ENTRY VolumeListHead
;
30 NPAGED_LOOKASIDE_LIST FcbLookasideList
;
31 NPAGED_LOOKASIDE_LIST CcbLookasideList
;
32 } RAWFS_GLOBAL_DATA
, *PRAWFS_GLOBAL_DATA
, VCB
, *PVCB
;
34 typedef struct _RAWFS_DEVICE_EXTENSION
36 KSPIN_LOCK FcbListLock
;
37 LIST_ENTRY FcbListHead
;
38 PDEVICE_OBJECT StorageDevice
;
40 struct _RAWFS_FCB
*VolumeFcb
;
41 LIST_ENTRY VolumeListEntry
;
42 } RAWFS_DEVICE_EXTENSION
, *PRAWFS_DEVICE_EXTENSION
;
44 typedef struct _RAWFS_IRP_CONTEXT
47 PDEVICE_OBJECT DeviceObject
;
48 PRAWFS_DEVICE_EXTENSION DeviceExt
;
50 WORK_QUEUE_ITEM WorkQueueItem
;
51 PIO_STACK_LOCATION Stack
;
54 PFILE_OBJECT FileObject
;
55 } RAWFS_IRP_CONTEXT
, *PRAWFS_IRP_CONTEXT
;
57 #define IRPCONTEXT_CANWAIT 0x0001
59 #define FCB_CACHE_INITIALIZED 0x0001
60 #define FCB_DELETE_PENDING 0x0002
61 #define FCB_IS_FAT 0x0004
62 #define FCB_IS_PAGE_FILE 0x0008
63 #define FCB_IS_VOLUME 0x0010
65 typedef struct _RAWFS_FCB
67 /* Start FCB header required by ReactOS/Windows NT */
68 FSRTL_COMMON_FCB_HEADER RFCB
;
69 SECTION_OBJECT_POINTERS SectionObjectPointers
;
70 ERESOURCE MainResource
;
71 ERESOURCE PagingIoResource
;
72 /* End FCB header required by ReactOS/Windows NT */
77 /* List of FCB's for this volume */
78 LIST_ENTRY FcbListEntry
;
80 /* Pointer to the parent fcb */
81 struct _RAWFS_FCB
* ParentFcb
;
83 /* Flags for the FCB */
86 /* Pointer to the file object which has initialized the fcb */
87 PFILE_OBJECT FileObject
;
88 } RAWFS_FCB
, *PRAWFS_FCB
;
90 typedef struct _RAWFS_CCB
92 LARGE_INTEGER CurrentByteOffset
;
93 } RAWFS_CCB
, *PRAWFS_CCB
;
95 /* GLOBALS ******************************************************************/
97 #define TAG_IRP TAG('R', 'I', 'R', 'P')
99 static PDRIVER_OBJECT RawFsDriverObject
;
100 static PDEVICE_OBJECT DiskDeviceObject
;
101 static PDEVICE_OBJECT CdromDeviceObject
;
102 static PDEVICE_OBJECT TapeDeviceObject
;
103 static NPAGED_LOOKASIDE_LIST IrpContextLookasideList
;
104 static LONG RawFsQueueCount
= 0;
106 /* FUNCTIONS *****************************************************************/
109 RawFsIsRawFileSystemDeviceObject(IN PDEVICE_OBJECT DeviceObject
)
111 DPRINT("RawFsIsRawFileSystemDeviceObject(DeviceObject %x)\n", DeviceObject
);
113 if (DeviceObject
== DiskDeviceObject
)
115 if (DeviceObject
== CdromDeviceObject
)
117 if (DeviceObject
== TapeDeviceObject
)
123 RawFsDispatchRequest(IN PRAWFS_IRP_CONTEXT IrpContext
);
126 RawFsReadDisk(IN PDEVICE_OBJECT pDeviceObject
,
127 IN PLARGE_INTEGER ReadOffset
,
129 IN OUT PUCHAR Buffer
)
131 IO_STATUS_BLOCK IoStatus
;
136 KeInitializeEvent(&Event
, NotificationEvent
, FALSE
);
138 DPRINT("RawFsReadDisk(pDeviceObject %x, Offset %I64x, Length %d, Buffer %x)\n",
139 pDeviceObject
, ReadOffset
->QuadPart
, ReadLength
, Buffer
);
141 DPRINT ("Building synchronous FSD Request...\n");
142 Irp
= IoBuildSynchronousFsdRequest(IRP_MJ_READ
,
151 DPRINT("IoBuildSynchronousFsdRequest() failed\n");
152 return STATUS_UNSUCCESSFUL
;
155 DPRINT("Calling IO Driver... with irp %x\n", Irp
);
156 Status
= IoCallDriver(pDeviceObject
, Irp
);
158 DPRINT("Waiting for IO Operation for %x\n", Irp
);
159 if (Status
== STATUS_PENDING
)
161 DPRINT("Operation pending\n");
162 KeWaitForSingleObject (&Event
, Suspended
, KernelMode
, FALSE
, NULL
);
163 DPRINT("Getting IO Status... for %x\n", Irp
);
164 Status
= IoStatus
.Status
;
167 if (!NT_SUCCESS(Status
))
169 DPRINT("RawFsReadDisk() failed. Status %x\n", Status
);
170 DPRINT("(pDeviceObject %x, Offset %I64x, Size %d, Buffer %x\n",
171 pDeviceObject
, ReadOffset
->QuadPart
, ReadLength
, Buffer
);
174 DPRINT("Block request succeeded for %x\n", Irp
);
175 return STATUS_SUCCESS
;
179 RawFsWriteDisk(IN PDEVICE_OBJECT pDeviceObject
,
180 IN PLARGE_INTEGER WriteOffset
,
181 IN ULONG WriteLength
,
184 IO_STATUS_BLOCK IoStatus
;
189 DPRINT("RawFsWriteDisk(pDeviceObject %x, Offset %I64x, Size %d, Buffer %x)\n",
190 pDeviceObject
, WriteOffset
->QuadPart
, WriteLength
, Buffer
);
192 KeInitializeEvent(&Event
, NotificationEvent
, FALSE
);
194 DPRINT("Building synchronous FSD Request...\n");
195 Irp
= IoBuildSynchronousFsdRequest(IRP_MJ_WRITE
,
204 DPRINT("IoBuildSynchronousFsdRequest()\n");
205 return(STATUS_UNSUCCESSFUL
);
208 DPRINT("Calling IO Driver...\n");
209 Status
= IoCallDriver(pDeviceObject
, Irp
);
211 DPRINT("Waiting for IO Operation...\n");
212 if (Status
== STATUS_PENDING
)
214 KeWaitForSingleObject(&Event
, Suspended
, KernelMode
, FALSE
, NULL
);
215 DPRINT("Getting IO Status...\n");
216 Status
= IoStatus
.Status
;
218 if (!NT_SUCCESS(Status
))
220 DPRINT("RawFsWriteDisk() failed. Status %x\n", Status
);
221 DPRINT("(pDeviceObject %x, Offset %I64x, Size %d, Buffer %x\n",
222 pDeviceObject
, WriteOffset
->QuadPart
, WriteLength
, Buffer
);
226 return STATUS_SUCCESS
;
230 RawFsBlockDeviceIoControl(IN PDEVICE_OBJECT DeviceObject
,
232 IN PVOID InputBuffer
,
233 IN ULONG InputBufferSize
,
234 IN OUT PVOID OutputBuffer
,
235 IN OUT PULONG pOutputBufferSize
)
237 ULONG OutputBufferSize
= 0;
240 IO_STATUS_BLOCK IoStatus
;
243 DPRINT("RawFsBlockDeviceIoControl(DeviceObject %x, CtlCode %x, "
244 "InputBuffer %x, InputBufferSize %x, OutputBuffer %x, "
245 "POutputBufferSize %x (%x)\n", DeviceObject
, CtlCode
,
246 InputBuffer
, InputBufferSize
, OutputBuffer
, pOutputBufferSize
,
247 pOutputBufferSize
? *pOutputBufferSize
: 0);
249 if (pOutputBufferSize
)
251 OutputBufferSize
= *pOutputBufferSize
;
254 KeInitializeEvent(&Event
, NotificationEvent
, FALSE
);
256 DPRINT("Building device I/O control request ...\n");
257 Irp
= IoBuildDeviceIoControlRequest(CtlCode
,
268 DPRINT("IoBuildDeviceIoControlRequest failed\n");
269 return STATUS_INSUFFICIENT_RESOURCES
;
272 DPRINT("Calling IO Driver... with irp %x\n", Irp
);
273 Status
= IoCallDriver(DeviceObject
, Irp
);
275 DPRINT("Waiting for IO Operation for %x\n", Irp
);
276 if (Status
== STATUS_PENDING
)
278 DPRINT("Operation pending\n");
279 KeWaitForSingleObject (&Event
, Suspended
, KernelMode
, FALSE
, NULL
);
280 DPRINT("Getting IO Status... for %x\n", Irp
);
281 Status
= IoStatus
.Status
;
283 if (OutputBufferSize
)
285 *pOutputBufferSize
= OutputBufferSize
;
287 DPRINT("Returning Status %x\n", Status
);
292 RawFsNewFCB(IN PRAWFS_GLOBAL_DATA pGlobalData
)
296 Fcb
= ExAllocateFromNPagedLookasideList(&pGlobalData
->FcbLookasideList
);
297 memset(Fcb
, 0, sizeof(RAWFS_FCB
));
298 ExInitializeResourceLite(&Fcb
->PagingIoResource
);
299 ExInitializeResourceLite(&Fcb
->MainResource
);
300 // FsRtlInitializeFileLock(&Fcb->FileLock, NULL, NULL);
305 RawFsDestroyFCB(IN PRAWFS_GLOBAL_DATA pGlobalData
, IN PRAWFS_FCB pFcb
)
307 //FsRtlUninitializeFileLock(&pFcb->FileLock);
308 ExDeleteResourceLite(&pFcb
->PagingIoResource
);
309 ExDeleteResourceLite(&pFcb
->MainResource
);
310 ExFreeToNPagedLookasideList(&pGlobalData
->FcbLookasideList
, pFcb
);
314 RawFsNewCCB(PRAWFS_GLOBAL_DATA pGlobalData
)
318 Ccb
= ExAllocateFromNPagedLookasideList(&pGlobalData
->CcbLookasideList
);
319 memset(Ccb
, 0, sizeof(RAWFS_CCB
));
324 RawFsDestroyCCB(PRAWFS_GLOBAL_DATA pGlobalData
, PRAWFS_CCB pCcb
)
326 ExFreeToNPagedLookasideList(&pGlobalData
->CcbLookasideList
, pCcb
);
329 static PRAWFS_IRP_CONTEXT
330 RawFsAllocateIrpContext(IN PDEVICE_OBJECT DeviceObject
, IN PIRP Irp
)
332 PRAWFS_GLOBAL_DATA GlobalData
;
333 PRAWFS_IRP_CONTEXT IrpContext
;
336 DPRINT("RawFsAllocateIrpContext(DeviceObject %x, Irp %x)\n", DeviceObject
, Irp
);
338 assert(DeviceObject
);
341 GlobalData
= (PRAWFS_GLOBAL_DATA
) DeviceObject
->DeviceExtension
;
342 IrpContext
= ExAllocateFromNPagedLookasideList(&IrpContextLookasideList
);
345 RtlZeroMemory(IrpContext
, sizeof(IrpContext
));
346 IrpContext
->Irp
= Irp
;
347 IrpContext
->DeviceObject
= DeviceObject
;
348 IrpContext
->DeviceExt
= DeviceObject
->DeviceExtension
;
349 IrpContext
->Stack
= IoGetCurrentIrpStackLocation(Irp
);
350 assert(IrpContext
->Stack
);
351 MajorFunction
= IrpContext
->MajorFunction
= IrpContext
->Stack
->MajorFunction
;
352 IrpContext
->MinorFunction
= IrpContext
->Stack
->MinorFunction
;
353 IrpContext
->FileObject
= IrpContext
->Stack
->FileObject
;
354 if (MajorFunction
== IRP_MJ_FILE_SYSTEM_CONTROL
||
355 MajorFunction
== IRP_MJ_DEVICE_CONTROL
||
356 MajorFunction
== IRP_MJ_SHUTDOWN
)
358 IrpContext
->Flags
|= IRPCONTEXT_CANWAIT
;
360 else if (MajorFunction
!= IRP_MJ_CLEANUP
&&
361 MajorFunction
!= IRP_MJ_CLOSE
&&
362 IoIsOperationSynchronous(Irp
))
364 IrpContext
->Flags
|= IRPCONTEXT_CANWAIT
;
371 RawFsFreeIrpContext(IN PRAWFS_IRP_CONTEXT IrpContext
)
373 DPRINT("RawFsFreeIrpContext(IrpContext %x)\n", IrpContext
);
377 ExFreeToNPagedLookasideList(&IrpContextLookasideList
, IrpContext
);
381 STDCALL
RawFsDoRequest(PVOID IrpContext
)
385 DPRINT("RawFsDoRequest(IrpContext %x), MajorFunction %x, %d\n",
386 IrpContext
, ((PRAWFS_IRP_CONTEXT
) IrpContext
)->MajorFunction
, Count
);
388 Count
= InterlockedDecrement(&RawFsQueueCount
);
389 RawFsDispatchRequest((PRAWFS_IRP_CONTEXT
) IrpContext
);
393 RawFsQueueRequest(PRAWFS_IRP_CONTEXT IrpContext
)
397 DPRINT("RawFsQueueRequest (IrpContext %x), %d\n", IrpContext
, Count
);
399 assert(IrpContext
!= NULL
);
400 assert(IrpContext
->Irp
!= NULL
);
402 Count
= InterlockedIncrement(&RawFsQueueCount
);
404 IrpContext
->Flags
|= IRPCONTEXT_CANWAIT
;
405 IoMarkIrpPending (IrpContext
->Irp
);
406 ExInitializeWorkItem (&IrpContext
->WorkQueueItem
, RawFsDoRequest
, IrpContext
);
407 ExQueueWorkItem(&IrpContext
->WorkQueueItem
, CriticalWorkQueue
);
408 return STATUS_PENDING
;
412 RawFsClose(IN PRAWFS_IRP_CONTEXT IrpContext
)
414 DPRINT("RawFsClose(IrpContext %x)\n", IrpContext
);
416 return STATUS_NOT_IMPLEMENTED
;
420 RawFsCreateFile(IN PRAWFS_IRP_CONTEXT IrpContext
)
422 PRAWFS_DEVICE_EXTENSION DeviceExt
;
423 PRAWFS_GLOBAL_DATA GlobalData
;
424 PIO_STACK_LOCATION IoSp
;
425 PFILE_OBJECT FileObject
;
426 ULONG RequestedDisposition
;
427 ULONG RequestedOptions
;
431 GlobalData
= (PRAWFS_GLOBAL_DATA
) IrpContext
->DeviceObject
->DeviceExtension
;
432 IoSp
= IoGetCurrentIrpStackLocation(IrpContext
->Irp
);
433 RequestedDisposition
= ((IoSp
->Parameters
.Create
.Options
>> 24) & 0xff);
434 RequestedOptions
= IoSp
->Parameters
.Create
.Options
& FILE_VALID_OPTION_FLAGS
;
435 FileObject
= IoSp
->FileObject
;
436 DeviceExt
= IrpContext
->DeviceObject
->DeviceExtension
;
438 if (FileObject
->FileName
.Length
== 0 &&
439 FileObject
->RelatedFileObject
== NULL
)
441 /* This a open operation for the volume itself */
442 if (RequestedDisposition
== FILE_CREATE
443 || RequestedDisposition
== FILE_OVERWRITE_IF
444 || RequestedDisposition
== FILE_SUPERSEDE
)
446 return STATUS_ACCESS_DENIED
;
448 if (RequestedOptions
& FILE_DIRECTORY_FILE
)
450 return STATUS_NOT_A_DIRECTORY
;
452 pFcb
= DeviceExt
->VolumeFcb
;
453 pCcb
= RawFsNewCCB(GlobalData
);
456 return (STATUS_INSUFFICIENT_RESOURCES
);
459 FileObject
->Flags
|= FO_FCB_IS_VALID
;
460 FileObject
->SectionObjectPointer
= &pFcb
->SectionObjectPointers
;
461 FileObject
->FsContext
= pFcb
;
462 FileObject
->FsContext2
= pCcb
;
465 IrpContext
->Irp
->IoStatus
.Information
= FILE_OPENED
;
466 return(STATUS_SUCCESS
);
469 /* This filesystem driver only supports volume access */
470 return(STATUS_INVALID_PARAMETER
);
474 RawFsCreate(IN PRAWFS_IRP_CONTEXT IrpContext
)
478 DPRINT("RawFsCreate(IrpContext %x)\n", IrpContext
);
482 if (RawFsIsRawFileSystemDeviceObject(IrpContext
->DeviceObject
))
484 /* DeviceObject represents FileSystem instead of logical volume */
485 DPRINT("RawFsCreate() called with file system\n");
486 IrpContext
->Irp
->IoStatus
.Information
= FILE_OPENED
;
487 IrpContext
->Irp
->IoStatus
.Status
= STATUS_SUCCESS
;
488 IoCompleteRequest(IrpContext
->Irp
, IO_DISK_INCREMENT
);
489 RawFsFreeIrpContext(IrpContext
);
490 return STATUS_SUCCESS
;
493 if (!(IrpContext
->Flags
& IRPCONTEXT_CANWAIT
))
495 return RawFsQueueRequest(IrpContext
);
498 IrpContext
->Irp
->IoStatus
.Information
= 0;
500 Status
= RawFsCreateFile(IrpContext
);
502 IrpContext
->Irp
->IoStatus
.Status
= Status
;
503 IoCompleteRequest(IrpContext
->Irp
,
504 NT_SUCCESS(Status
) ? IO_DISK_INCREMENT
: IO_NO_INCREMENT
);
505 RawFsFreeIrpContext(IrpContext
);
511 RawFsRead(IN PRAWFS_IRP_CONTEXT IrpContext
)
513 DPRINT("RawFsRead(IrpContext %x)\n", IrpContext
);
515 return STATUS_NOT_IMPLEMENTED
;
519 RawFsWrite(IN PRAWFS_IRP_CONTEXT IrpContext
)
521 DPRINT("RawFsWrite(IrpContext %x)\n", IrpContext
);
523 return STATUS_NOT_IMPLEMENTED
;
527 RawFsMount(IN PRAWFS_IRP_CONTEXT IrpContext
)
529 PRAWFS_GLOBAL_DATA GlobalData
;
530 PDEVICE_OBJECT DeviceObject
= NULL
;
531 PRAWFS_DEVICE_EXTENSION DeviceExt
= NULL
;
532 PRAWFS_FCB VolumeFcb
= NULL
;
533 PRAWFS_FCB Fcb
= NULL
;
534 PARTITION_INFORMATION PartitionInfo
;
535 DISK_GEOMETRY DiskGeometry
;
536 LARGE_INTEGER VolumeSize
;
540 DPRINT("RawFsMount(IrpContext %x)\n", IrpContext
);
544 if (!RawFsIsRawFileSystemDeviceObject(IrpContext
->DeviceObject
))
546 Status
= STATUS_INVALID_DEVICE_REQUEST
;
547 DPRINT("Not for me\n");
551 GlobalData
= (PRAWFS_GLOBAL_DATA
) IrpContext
->DeviceObject
->DeviceExtension
;
553 Status
= IoCreateDevice(GlobalData
->DriverObject
,
554 sizeof(RAWFS_DEVICE_EXTENSION
),
556 FILE_DEVICE_FILE_SYSTEM
,
560 if (!NT_SUCCESS(Status
))
565 DeviceObject
->Flags
|= DO_DIRECT_IO
;
566 DeviceExt
= (PVOID
) DeviceObject
->DeviceExtension
;
567 RtlZeroMemory(DeviceExt
, sizeof(RAWFS_DEVICE_EXTENSION
));
569 /* Use same vpb as device disk */
570 DeviceObject
->Vpb
= IrpContext
->Stack
->Parameters
.MountVolume
.DeviceObject
->Vpb
;
571 DeviceExt
->StorageDevice
= IrpContext
->Stack
->Parameters
.MountVolume
.DeviceObject
;
572 DeviceExt
->StorageDevice
->Vpb
->DeviceObject
= DeviceObject
;
573 DeviceExt
->StorageDevice
->Vpb
->RealDevice
= DeviceExt
->StorageDevice
;
574 DeviceExt
->StorageDevice
->Vpb
->Flags
|= VPB_MOUNTED
;
575 DeviceObject
->StackSize
= DeviceExt
->StorageDevice
->StackSize
+ 1;
576 DeviceObject
->Flags
&= ~DO_DEVICE_INITIALIZING
;
578 KeInitializeSpinLock(&DeviceExt
->FcbListLock
);
579 InitializeListHead(&DeviceExt
->FcbListHead
);
581 /* First try getting harddisk geometry then try getting CD-ROM geometry */
582 Size
= sizeof(DISK_GEOMETRY
);
583 Status
= RawFsBlockDeviceIoControl(
584 IrpContext
->Stack
->Parameters
.MountVolume
.DeviceObject
,
585 IOCTL_DISK_GET_DRIVE_GEOMETRY
,
590 if (!NT_SUCCESS(Status
))
592 DPRINT("RawFsBlockDeviceIoControl failed with status 0x%.08x\n", Status
);
595 if (DiskGeometry
.MediaType
== FixedMedia
)
597 // We have found a hard disk
598 Size
= sizeof(PARTITION_INFORMATION
);
599 Status
= RawFsBlockDeviceIoControl(
600 IrpContext
->Stack
->Parameters
.MountVolume
.DeviceObject
,
601 IOCTL_DISK_GET_PARTITION_INFO
,
606 if (!NT_SUCCESS(Status
))
608 DPRINT("RawFsBlockDeviceIoControl() failed (%x)\n", Status
);
612 DbgPrint("Partition Information:\n");
613 DbgPrint("StartingOffset %u\n", PartitionInfo
.StartingOffset
.QuadPart
);
614 DbgPrint("PartitionLength %u\n", PartitionInfo
.PartitionLength
.QuadPart
);
615 DbgPrint("HiddenSectors %u\n", PartitionInfo
.HiddenSectors
);
616 DbgPrint("PartitionNumber %u\n", PartitionInfo
.PartitionNumber
);
617 DbgPrint("PartitionType %u\n", PartitionInfo
.PartitionType
);
618 DbgPrint("BootIndicator %u\n", PartitionInfo
.BootIndicator
);
619 DbgPrint("RecognizedPartition %u\n", PartitionInfo
.RecognizedPartition
);
620 DbgPrint("RewritePartition %u\n", PartitionInfo
.RewritePartition
);
622 VolumeSize
.QuadPart
= PartitionInfo
.PartitionLength
.QuadPart
;
624 else if (DiskGeometry
.MediaType
> Unknown
&& DiskGeometry
.MediaType
<= RemovableMedia
)
626 Status
= STATUS_UNRECOGNIZED_VOLUME
;
630 VolumeFcb
= RawFsNewFCB(GlobalData
);
631 if (VolumeFcb
== NULL
)
633 Status
= STATUS_INSUFFICIENT_RESOURCES
;
637 VolumeFcb
->Flags
= FCB_IS_VOLUME
;
638 VolumeFcb
->RFCB
.FileSize
.QuadPart
= VolumeSize
.QuadPart
;
639 VolumeFcb
->RFCB
.ValidDataLength
.QuadPart
= VolumeFcb
->RFCB
.FileSize
.QuadPart
;
640 VolumeFcb
->RFCB
.AllocationSize
.QuadPart
= VolumeFcb
->RFCB
.FileSize
.QuadPart
;
641 DeviceExt
->VolumeFcb
= VolumeFcb
;
643 ExAcquireResourceExclusiveLite(&GlobalData
->VolumeListLock
, TRUE
);
644 InsertHeadList(&GlobalData
->VolumeListHead
, &DeviceExt
->VolumeListEntry
);
645 ExReleaseResourceLite(&GlobalData
->VolumeListLock
);
647 /* No serial number */
648 DeviceObject
->Vpb
->SerialNumber
= 0;
650 /* Set volume label (no label) */
651 *(DeviceObject
->Vpb
->VolumeLabel
) = 0;
652 DeviceObject
->Vpb
->VolumeLabelLength
= 0;
654 Status
= STATUS_SUCCESS
;
657 if (!NT_SUCCESS(Status
))
659 DPRINT("RAWFS: RawFsMount() Status 0x%.08x\n", Status
);
662 RawFsDestroyFCB(GlobalData
, Fcb
);
664 IoDeleteDevice(DeviceObject
);
666 RawFsDestroyFCB(GlobalData
, VolumeFcb
);
672 RawFsFileSystemControl(IN PRAWFS_IRP_CONTEXT IrpContext
)
676 DPRINT("RawFsFileSystemControl(IrpContext %x)\n", IrpContext
);
680 switch (IrpContext
->MinorFunction
)
682 case IRP_MN_USER_FS_REQUEST
:
683 DPRINT("RawFs FSC: IRP_MN_USER_FS_REQUEST\n");
684 Status
= STATUS_INVALID_DEVICE_REQUEST
;
687 case IRP_MN_MOUNT_VOLUME
:
688 DPRINT("RawFs FSC: IRP_MN_MOUNT_VOLUME\n");
689 Status
= RawFsMount(IrpContext
);
692 case IRP_MN_VERIFY_VOLUME
:
693 DPRINT("RawFs FSC: IRP_MN_VERIFY_VOLUME\n");
694 Status
= STATUS_INVALID_DEVICE_REQUEST
;
698 DPRINT("RawFs FSC: MinorFunction %d\n", IrpContext
->MinorFunction
);
699 Status
= STATUS_INVALID_DEVICE_REQUEST
;
703 IrpContext
->Irp
->IoStatus
.Status
= Status
;
704 IrpContext
->Irp
->IoStatus
.Information
= 0;
706 IoCompleteRequest(IrpContext
->Irp
, IO_NO_INCREMENT
);
707 RawFsFreeIrpContext(IrpContext
);
712 RawFsQueryInformation(IN PRAWFS_IRP_CONTEXT IrpContext
)
714 DPRINT("RawFsQueryInformation(IrpContext %x)\n", IrpContext
);
716 return STATUS_NOT_IMPLEMENTED
;
720 RawFsSetInformation(IN PRAWFS_IRP_CONTEXT IrpContext
)
722 DPRINT("RawFsSetInformation(IrpContext %x)\n", IrpContext
);
724 return STATUS_NOT_IMPLEMENTED
;
728 RawFsDirectoryControl(IN PRAWFS_IRP_CONTEXT IrpContext
)
730 DPRINT("RawFsDirectoryControl(IrpContext %x)\n", IrpContext
);
732 return STATUS_NOT_IMPLEMENTED
;
736 RawFsQueryVolumeInformation(IN PRAWFS_IRP_CONTEXT IrpContext
)
738 DPRINT("RawFsQueryVolumeInformation(IrpContext %x)\n", IrpContext
);
740 return STATUS_NOT_IMPLEMENTED
;
744 RawFsSetVolumeInformation(IN PRAWFS_IRP_CONTEXT IrpContext
)
746 DPRINT("RawFsSetVolumeInformation(IrpContext %x)\n", IrpContext
);
748 return STATUS_NOT_IMPLEMENTED
;
752 RawFsLockControl(IN PRAWFS_IRP_CONTEXT IrpContext
)
754 DPRINT("RawFsLockControl(IrpContext %x)\n", IrpContext
);
756 return STATUS_NOT_IMPLEMENTED
;
760 RawFsCleanup(IN PRAWFS_IRP_CONTEXT IrpContext
)
762 DPRINT("RawFsCleanup(IrpContext %x)\n", IrpContext
);
764 return STATUS_NOT_IMPLEMENTED
;
768 RawFsFlush(IN PRAWFS_IRP_CONTEXT IrpContext
)
770 DPRINT("RawFsFlush(IrpContext %x)\n", IrpContext
);
772 return STATUS_NOT_IMPLEMENTED
;
775 static NTSTATUS STDCALL
776 RawFsShutdown(IN PDEVICE_OBJECT DeviceObject
, IN PIRP Irp
)
778 DPRINT("RawFsShutdown(DeviceObject %x, Irp %x)\n", DeviceObject
, Irp
);
781 * Note: Do NOT call UNIMPLEMENTED here!
782 * This function must finish in order to shutdown ReactOS properly!
785 return STATUS_NOT_IMPLEMENTED
;
789 RawFsDispatchRequest(IN PRAWFS_IRP_CONTEXT IrpContext
)
791 DPRINT("RawFsDispatchRequest(IrpContext %x), MajorFunction %x\n",
792 IrpContext
, IrpContext
->MajorFunction
);
796 switch (IrpContext
->MajorFunction
)
799 return RawFsClose(IrpContext
);
801 return RawFsCreate (IrpContext
);
803 return RawFsRead (IrpContext
);
805 return RawFsWrite (IrpContext
);
806 case IRP_MJ_FILE_SYSTEM_CONTROL
:
807 return RawFsFileSystemControl(IrpContext
);
808 case IRP_MJ_QUERY_INFORMATION
:
809 return RawFsQueryInformation (IrpContext
);
810 case IRP_MJ_SET_INFORMATION
:
811 return RawFsSetInformation (IrpContext
);
812 case IRP_MJ_DIRECTORY_CONTROL
:
813 return RawFsDirectoryControl(IrpContext
);
814 case IRP_MJ_QUERY_VOLUME_INFORMATION
:
815 return RawFsQueryVolumeInformation(IrpContext
);
816 case IRP_MJ_SET_VOLUME_INFORMATION
:
817 return RawFsSetVolumeInformation(IrpContext
);
818 case IRP_MJ_LOCK_CONTROL
:
819 return RawFsLockControl(IrpContext
);
821 return RawFsCleanup(IrpContext
);
822 case IRP_MJ_FLUSH_BUFFERS
:
823 return RawFsFlush(IrpContext
);
825 DPRINT1("Unexpected major function %x\n", IrpContext
->MajorFunction
);
826 IrpContext
->Irp
->IoStatus
.Status
= STATUS_DRIVER_INTERNAL_ERROR
;
827 IoCompleteRequest(IrpContext
->Irp
, IO_NO_INCREMENT
);
828 RawFsFreeIrpContext(IrpContext
);
829 return STATUS_DRIVER_INTERNAL_ERROR
;
833 static NTSTATUS STDCALL
834 RawFsBuildRequest(IN PDEVICE_OBJECT DeviceObject
,
837 PRAWFS_IRP_CONTEXT IrpContext
;
840 DPRINT("RawFsBuildRequest(DeviceObject %x, Irp %x)\n", DeviceObject
, Irp
);
842 assert(DeviceObject
);
845 IrpContext
= RawFsAllocateIrpContext(DeviceObject
, Irp
);
846 if (IrpContext
== NULL
)
848 Status
= STATUS_INSUFFICIENT_RESOURCES
;
849 Irp
->IoStatus
.Status
= Status
;
850 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
854 if (KeGetCurrentIrql() <= PASSIVE_LEVEL
)
856 FsRtlEnterFileSystem();
860 DPRINT1("RawFs is entered at irql = %d\n", KeGetCurrentIrql());
862 Status
= RawFsDispatchRequest(IrpContext
);
863 if (KeGetCurrentIrql() <= PASSIVE_LEVEL
)
865 FsRtlExitFileSystem();
872 RawFsDriverEntry(IN PDRIVER_OBJECT DriverObject
,
873 IN PUNICODE_STRING RegistryPath
)
875 PRAWFS_GLOBAL_DATA DeviceData
;
878 RawFsDriverObject
= DriverObject
;
880 Status
= IoCreateDevice(DriverObject
,
881 sizeof(RAWFS_GLOBAL_DATA
),
883 FILE_DEVICE_DISK_FILE_SYSTEM
,
887 if (!NT_SUCCESS(Status
))
889 CPRINT("IoCreateDevice() failed with status 0x%.08x\n", Status
);
890 KeBugCheck(PHASE1_INITIALIZATION_FAILED
);
893 DeviceData
= DiskDeviceObject
->DeviceExtension
;
894 RtlZeroMemory(DeviceData
, sizeof(RAWFS_GLOBAL_DATA
));
895 DeviceData
->DriverObject
= DriverObject
;
896 DeviceData
->DeviceObject
= DiskDeviceObject
;
897 DiskDeviceObject
->Flags
|= DO_DIRECT_IO
;
900 Status
= IoCreateDevice(DriverObject
,
901 sizeof(RAWFS_GLOBAL_DATA
),
903 FILE_DEVICE_CD_ROM_FILE_SYSTEM
,
907 if (!NT_SUCCESS(Status
))
909 CPRINT("IoCreateDevice() failed with status 0x%.08x\n", Status
);
910 KeBugCheck(PHASE1_INITIALIZATION_FAILED
);
913 DeviceData
= CdromDeviceObject
->DeviceExtension
;
914 RtlZeroMemory (DeviceData
, sizeof(RAWFS_GLOBAL_DATA
));
915 DeviceData
->DriverObject
= DriverObject
;
916 DeviceData
->DeviceObject
= CdromDeviceObject
;
917 CdromDeviceObject
->Flags
|= DO_DIRECT_IO
;
920 Status
= IoCreateDevice(DriverObject
,
921 sizeof(RAWFS_GLOBAL_DATA
),
923 FILE_DEVICE_TAPE_FILE_SYSTEM
,
927 if (!NT_SUCCESS(Status
))
929 CPRINT("IoCreateDevice() failed with status 0x%.08x\n", Status
);
930 KeBugCheck(PHASE1_INITIALIZATION_FAILED
);
933 DeviceData
= TapeDeviceObject
->DeviceExtension
;
934 RtlZeroMemory (DeviceData
, sizeof(RAWFS_GLOBAL_DATA
));
935 DeviceData
->DriverObject
= DriverObject
;
936 DeviceData
->DeviceObject
= TapeDeviceObject
;
937 TapeDeviceObject
->Flags
|= DO_DIRECT_IO
;
940 DriverObject
->MajorFunction
[IRP_MJ_CLOSE
] = (PDRIVER_DISPATCH
) RawFsBuildRequest
;
941 DriverObject
->MajorFunction
[IRP_MJ_CREATE
] = (PDRIVER_DISPATCH
) RawFsBuildRequest
;
942 DriverObject
->MajorFunction
[IRP_MJ_READ
] = (PDRIVER_DISPATCH
) RawFsBuildRequest
;
943 DriverObject
->MajorFunction
[IRP_MJ_WRITE
] = (PDRIVER_DISPATCH
) RawFsBuildRequest
;
944 DriverObject
->MajorFunction
[IRP_MJ_FILE_SYSTEM_CONTROL
] = (PDRIVER_DISPATCH
) RawFsBuildRequest
;
945 DriverObject
->MajorFunction
[IRP_MJ_QUERY_INFORMATION
] = (PDRIVER_DISPATCH
) RawFsBuildRequest
;
946 DriverObject
->MajorFunction
[IRP_MJ_SET_INFORMATION
] = (PDRIVER_DISPATCH
) RawFsBuildRequest
;
947 DriverObject
->MajorFunction
[IRP_MJ_DIRECTORY_CONTROL
] = (PDRIVER_DISPATCH
) RawFsBuildRequest
;
948 DriverObject
->MajorFunction
[IRP_MJ_QUERY_VOLUME_INFORMATION
] = (PDRIVER_DISPATCH
) RawFsBuildRequest
;
949 DriverObject
->MajorFunction
[IRP_MJ_SET_VOLUME_INFORMATION
] = (PDRIVER_DISPATCH
) RawFsBuildRequest
;
950 DriverObject
->MajorFunction
[IRP_MJ_SHUTDOWN
] = (PDRIVER_DISPATCH
) RawFsShutdown
;
951 DriverObject
->MajorFunction
[IRP_MJ_LOCK_CONTROL
] = (PDRIVER_DISPATCH
) RawFsBuildRequest
;
952 DriverObject
->MajorFunction
[IRP_MJ_CLEANUP
] = (PDRIVER_DISPATCH
) RawFsBuildRequest
;
953 DriverObject
->MajorFunction
[IRP_MJ_FLUSH_BUFFERS
] = (PDRIVER_DISPATCH
) RawFsBuildRequest
;
954 DriverObject
->DriverUnload
= NULL
;
956 ExInitializeNPagedLookasideList(&IrpContextLookasideList
,
957 NULL
, NULL
, 0, sizeof(RAWFS_IRP_CONTEXT
), TAG_IRP
, 0);
960 IoRegisterFileSystem(DiskDeviceObject
);
961 IoRegisterFileSystem(CdromDeviceObject
);
962 IoRegisterFileSystem(TapeDeviceObject
);
964 return STATUS_SUCCESS
;