All:
[reactos.git] / reactos / drivers / fs / vfat / iface.c
index d42ee5c..1069359 100644 (file)
@@ -1,4 +1,4 @@
-/* $Id: iface.c,v 1.61 2002/02/08 02:57:09 chorns Exp $
+/* $Id: iface.c,v 1.62 2002/03/18 22:37:12 hbirr Exp $
  *
  * COPYRIGHT:        See COPYING in the top level directory
  * PROJECT:          ReactOS kernel
 
 /* GLOBALS *****************************************************************/
 
-#define  CACHEPAGESIZE(pDeviceExt) ((pDeviceExt)->BytesPerCluster > PAGESIZE ? \
-                  (pDeviceExt)->BytesPerCluster : PAGESIZE)
 
-static PDRIVER_OBJECT VfatDriverObject;
+PVFAT_GLOBAL_DATA VfatGlobalData;
 
 /* FUNCTIONS ****************************************************************/
 
-static NTSTATUS
-VfatHasFileSystem(PDEVICE_OBJECT DeviceToMount,
-                 PBOOLEAN RecognizedFS)
-/*
- * FUNCTION: Tests if the device contains a filesystem that can be mounted
- *           by this fsd
- */
-{
-   BootSector *Boot;
-   NTSTATUS Status;
-
-   Boot = ExAllocatePool(NonPagedPool, 512);
-
-   Status = VfatReadSectors(DeviceToMount, 0, 1, (UCHAR *) Boot);
-   if (!NT_SUCCESS(Status))
-     {
-       return(Status);
-     }
-
-   DPRINT("Boot->SysType %.5s\n", Boot->SysType);
-   if (strncmp(Boot->SysType, "FAT12", 5) == 0 ||
-       strncmp(Boot->SysType, "FAT16", 5) == 0 ||
-       strncmp(((struct _BootSector32 *) (Boot))->SysType, "FAT32", 5) == 0)
-     {
-       *RecognizedFS = TRUE;
-     }
-   else
-     {
-       *RecognizedFS = FALSE;
-     }
-
-   ExFreePool(Boot);
-
-   return(STATUS_SUCCESS);
-}
-
-
-static NTSTATUS
-VfatMountDevice(PDEVICE_EXTENSION DeviceExt,
-               PDEVICE_OBJECT DeviceToMount)
-/*
- * FUNCTION: Mounts the device
- */
-{
-   NTSTATUS Status;
-
-   DPRINT("Mounting VFAT device...");
-   DPRINT("DeviceExt %x\n", DeviceExt);
-
-   DeviceExt->Boot = ExAllocatePool(NonPagedPool, 512);
-
-   Status = VfatReadSectors(DeviceToMount, 0, 1, (UCHAR *) DeviceExt->Boot);
-   if (!NT_SUCCESS(Status))
-     {
-       return(Status);
-     }
-
-   DeviceExt->FATStart = DeviceExt->Boot->ReservedSectors;
-   DeviceExt->rootDirectorySectors =
-     (DeviceExt->Boot->RootEntries * 32) / DeviceExt->Boot->BytesPerSector;
-   DeviceExt->rootStart =
-     DeviceExt->FATStart +
-     DeviceExt->Boot->FATCount * DeviceExt->Boot->FATSectors;
-   DeviceExt->dataStart =
-     DeviceExt->rootStart + DeviceExt->rootDirectorySectors;
-   DeviceExt->BytesPerSector = DeviceExt->Boot->BytesPerSector;
-   DeviceExt->FATEntriesPerSector = DeviceExt->Boot->BytesPerSector / 32;
-   DeviceExt->BytesPerCluster = DeviceExt->Boot->SectorsPerCluster *
-     DeviceExt->Boot->BytesPerSector;
-
-   if (DeviceExt->BytesPerCluster >= PAGESIZE && 
-       (DeviceExt->BytesPerCluster % PAGESIZE) != 0)
-     {
-       DbgPrint("Invalid cluster size\n");
-       KeBugCheck(0);
-     }
-   else if (DeviceExt->BytesPerCluster < PAGESIZE &&
-           (PAGESIZE % DeviceExt->BytesPerCluster) != 0)
-     {
-       DbgPrint("Invalid cluster size2\n");
-       KeBugCheck(0);
-     }
-
-   if (strncmp (DeviceExt->Boot->SysType, "FAT12", 5) == 0)
-     {
-       DPRINT("FAT12\n");
-       DeviceExt->FatType = FAT12;
-     }
-   else if (strncmp
-           (((struct _BootSector32 *) (DeviceExt->Boot))->SysType, "FAT32",
-           5) == 0)
-     {
-       DPRINT("FAT32\n");
-       DeviceExt->FatType = FAT32;
-       DeviceExt->rootDirectorySectors = DeviceExt->Boot->SectorsPerCluster;
-       DeviceExt->dataStart = DeviceExt->FATStart + DeviceExt->Boot->FATCount
-         * ((struct _BootSector32 *) (DeviceExt->Boot))->FATSectors32;
-       DeviceExt->rootStart = ClusterToSector (DeviceExt,
-         ((struct _BootSector32 *)(DeviceExt->Boot))->RootCluster);
-     }
-   else
-     {
-       DPRINT("FAT16\n");
-       DeviceExt->FatType = FAT16;
-     }
-
-   return(STATUS_SUCCESS);
-}
-
-
-static NTSTATUS
-VfatMount (PVFAT_IRP_CONTEXT IrpContext)
-/*
- * FUNCTION: Mount the filesystem
- */
-{
-  PDEVICE_OBJECT DeviceObject = NULL;
-  PDEVICE_EXTENSION DeviceExt = NULL;
-  BOOLEAN RecognizedFS;
-  NTSTATUS Status;
-  PVFATFCB Fcb = NULL;
-  PVFATCCB Ccb = NULL;
-
-  DPRINT("VfatMount(IrpContext %x)\n", IrpContext);
-
-  assert (IrpContext);
-
-  Status = VfatHasFileSystem (IrpContext->Stack->Parameters.Mount.DeviceObject, &RecognizedFS);
-  if (!NT_SUCCESS(Status))
-  {
-     goto ByeBye;
-  }
-
-  if (RecognizedFS == FALSE)
-  {
-     DPRINT("VFAT: Unrecognized Volume\n");
-     Status = STATUS_UNRECOGNIZED_VOLUME;
-     goto ByeBye;
-  }
-
-  DPRINT("VFAT: Recognized volume\n");
-
-  Status = IoCreateDevice(VfatDriverObject,
-                         sizeof (DEVICE_EXTENSION),
-                         NULL,
-                         FILE_DEVICE_FILE_SYSTEM,
-                         0,
-                         FALSE,
-                         &DeviceObject);
-  if (!NT_SUCCESS(Status))
-  {
-    goto ByeBye;
-  }
-
-  DeviceObject->Flags = DeviceObject->Flags | DO_DIRECT_IO;
-  DeviceExt = (PVOID) DeviceObject->DeviceExtension;
-  RtlZeroMemory(DeviceExt, sizeof(DEVICE_EXTENSION));
-
-  /* use same vpb as device disk */
-  DeviceObject->Vpb = IrpContext->Stack->Parameters.Mount.DeviceObject->Vpb;
-  Status = VfatMountDevice(DeviceExt, IrpContext->Stack->Parameters.Mount.DeviceObject);
-  if (!NT_SUCCESS(Status))
-  {
-    /* FIXME: delete device object */
-    goto ByeBye;
-  }
-
-#ifdef DBG
-  DbgPrint("BytesPerSector:     %d\n", DeviceExt->Boot->BytesPerSector);
-  DbgPrint("SectorsPerCluster:  %d\n", DeviceExt->Boot->SectorsPerCluster);
-  DbgPrint("ReservedSectors:    %d\n", DeviceExt->Boot->ReservedSectors);
-  DbgPrint("FATCount:           %d\n", DeviceExt->Boot->FATCount);
-  DbgPrint("RootEntries:        %d\n", DeviceExt->Boot->RootEntries);
-  DbgPrint("Sectors:            %d\n", DeviceExt->Boot->Sectors);
-  DbgPrint("FATSectors:         %d\n", DeviceExt->Boot->FATSectors);
-  DbgPrint("SectorsPerTrack:    %d\n", DeviceExt->Boot->SectorsPerTrack);
-  DbgPrint("Heads:              %d\n", DeviceExt->Boot->Heads);
-  DbgPrint("HiddenSectors:      %d\n", DeviceExt->Boot->HiddenSectors);
-  DbgPrint("SectorsHuge:        %d\n", DeviceExt->Boot->SectorsHuge);
-  DbgPrint("RootStart:          %d\n", DeviceExt->rootStart);
-  DbgPrint("DataStart:          %d\n", DeviceExt->dataStart);
-  if (DeviceExt->FatType == FAT32)
-    {
-      DbgPrint("FATSectors32:       %d\n",
-              ((struct _BootSector32*)(DeviceExt->Boot))->FATSectors32);
-      DbgPrint("RootCluster:        %d\n",
-              ((struct _BootSector32*)(DeviceExt->Boot))->RootCluster);
-      DbgPrint("FSInfoSector:       %d\n",
-              ((struct _BootSector32*)(DeviceExt->Boot))->FSInfoSector);
-      DbgPrint("BootBackup:         %d\n",
-              ((struct _BootSector32*)(DeviceExt->Boot))->BootBackup);
-    }
-#endif
-  DeviceObject->Vpb->Flags |= VPB_MOUNTED;
-  DeviceExt->StorageDevice = IoAttachDeviceToDeviceStack(DeviceObject, IrpContext->Stack->Parameters.Mount.DeviceObject);
-
-  DeviceExt->FATFileObject = IoCreateStreamFileObject(NULL, DeviceExt->StorageDevice);
-  Fcb = vfatNewFCB(NULL);
-  if (Fcb == NULL)
-  {
-    Status = STATUS_INSUFFICIENT_RESOURCES;
-    goto ByeBye;
-  }
-  Ccb = ExAllocatePoolWithTag (NonPagedPool, sizeof (VFATCCB), TAG_CCB);
-  if (Ccb == NULL)
-  {
-    Status =  STATUS_INSUFFICIENT_RESOURCES;
-    goto ByeBye;
-  }
-  memset(Ccb, 0, sizeof (VFATCCB));
-  DeviceExt->FATFileObject->Flags = DeviceExt->FATFileObject->Flags | FO_FCB_IS_VALID | FO_DIRECT_CACHE_PAGING_READ;
-  DeviceExt->FATFileObject->FsContext = (PVOID) &Fcb->RFCB;
-  DeviceExt->FATFileObject->FsContext2 = Ccb;
-  DeviceExt->FATFileObject->SectionObjectPointers = &Fcb->SectionObjectPointers;
-  Ccb->pFcb = Fcb;
-  Ccb->PtrFileObject = DeviceExt->FATFileObject;
-  Fcb->FileObject = DeviceExt->FATFileObject;
-  Fcb->pDevExt = (PDEVICE_EXTENSION)DeviceExt->StorageDevice;
-
-  Fcb->Flags = FCB_IS_FAT;
-
-  if (DeviceExt->Boot->Sectors != 0)
-  {
-    DeviceExt->NumberOfClusters = (DeviceExt->Boot->Sectors - DeviceExt->dataStart)
-                                    / DeviceExt->Boot->SectorsPerCluster + 2;
-  }
-  else
-  {
-    DeviceExt->NumberOfClusters = (DeviceExt->Boot->SectorsHuge - DeviceExt->dataStart)
-                                    / DeviceExt->Boot->SectorsPerCluster + 2;
-  }
-  if (DeviceExt->FatType == FAT32)
-  {
-    Fcb->RFCB.FileSize.QuadPart = ((struct _BootSector32 *)DeviceExt->Boot)->FATSectors32 * BLOCKSIZE;
-    Fcb->RFCB.ValidDataLength.QuadPart = ((struct _BootSector32 *)DeviceExt->Boot)->FATSectors32 * BLOCKSIZE;
-    Fcb->RFCB.AllocationSize.QuadPart = ROUND_UP(((struct _BootSector32 *)DeviceExt->Boot)->FATSectors32 * BLOCKSIZE, CACHEPAGESIZE(DeviceExt));
-    Status = CcRosInitializeFileCache(DeviceExt->FATFileObject, &Fcb->RFCB.Bcb, CACHEPAGESIZE(DeviceExt));
-  }
-  else
-  {
-    if (DeviceExt->FatType == FAT16)
-    {
-      Fcb->RFCB.FileSize.QuadPart = DeviceExt->Boot->FATSectors * BLOCKSIZE;
-      Fcb->RFCB.ValidDataLength.QuadPart = DeviceExt->Boot->FATSectors * BLOCKSIZE;
-      Fcb->RFCB.AllocationSize.QuadPart = ROUND_UP(DeviceExt->Boot->FATSectors * BLOCKSIZE, CACHEPAGESIZE(DeviceExt));
-      Status = CcRosInitializeFileCache(DeviceExt->FATFileObject, &Fcb->RFCB.Bcb, CACHEPAGESIZE(DeviceExt));
-    }
-    else
-    {
-      Fcb->RFCB.FileSize.QuadPart = DeviceExt->Boot->FATSectors * BLOCKSIZE;
-      Fcb->RFCB.ValidDataLength.QuadPart = DeviceExt->Boot->FATSectors * BLOCKSIZE;
-      Fcb->RFCB.AllocationSize.QuadPart = 2 * PAGESIZE;
-      Status = CcRosInitializeFileCache(DeviceExt->FATFileObject, &Fcb->RFCB.Bcb, 2 * PAGESIZE);
-    }
-  }
-  if (!NT_SUCCESS (Status))
-  {
-     DbgPrint ("CcRosInitializeFileCache failed\n");
-     goto ByeBye;
-  }
-
-  DeviceExt->LastAvailableCluster = 0;
-  ExInitializeResourceLite(&DeviceExt->DirResource);
-  ExInitializeResourceLite(&DeviceExt->FatResource);
-
-  KeInitializeSpinLock(&DeviceExt->FcbListLock);
-  InitializeListHead(&DeviceExt->FcbListHead);
-
-  /* read serial number */
-  if (DeviceExt->FatType == FAT12 || DeviceExt->FatType == FAT16)
-    DeviceObject->Vpb->SerialNumber =
-      ((struct _BootSector *) (DeviceExt->Boot))->VolumeID;
-  else if (DeviceExt->FatType == FAT32)
-    DeviceObject->Vpb->SerialNumber =
-      ((struct _BootSector32 *) (DeviceExt->Boot))->VolumeID;
-
-  /* read volume label */
-  ReadVolumeLabel(DeviceExt,  DeviceObject->Vpb);
-  Status = STATUS_SUCCESS;
-
-ByeBye:
-
-  if (!NT_SUCCESS(Status))
-  {
-     // cleanup
-     if (DeviceExt && DeviceExt->FATFileObject)
-        ObDereferenceObject (DeviceExt->FATFileObject);
-     if (Fcb)
-        ExFreePool(Fcb);
-     if (Ccb)
-        ExFreePool(Ccb);
-     if (DeviceObject)
-       IoDeleteDevice(DeviceObject);
-  }
-  return Status;
-}
-
-
-NTSTATUS VfatFileSystemControl(PVFAT_IRP_CONTEXT IrpContext)
-/*
- * FUNCTION: File system control
- */
-{
-
-   NTSTATUS Status;
-
-   DPRINT("VfatFileSystemControl(IrpContext %x)\n", IrpContext);
-
-   assert (IrpContext);
-
-   switch (IrpContext->MinorFunction)
-     {
-       case IRP_MN_USER_FS_REQUEST:
-          DPRINT("VFAT FSC: IRP_MN_USER_FS_REQUEST\n");
-          Status = STATUS_INVALID_DEVICE_REQUEST;
-          break;
-
-       case IRP_MN_MOUNT_VOLUME:
-          Status = VfatMount(IrpContext);
-          break;
-
-       case IRP_MN_VERIFY_VOLUME:
-          DPRINT("VFAT FSC: IRP_MN_VERIFY_VOLUME\n");
-          Status = STATUS_INVALID_DEVICE_REQUEST;
-          break;
-
-       default:
-          DPRINT("VFAT FSC: MinorFunction %d\n", IrpContext->MinorFunction);
-          Status = STATUS_INVALID_DEVICE_REQUEST;
-          break;
-     }
-
-   IrpContext->Irp->IoStatus.Status = Status;
-   IrpContext->Irp->IoStatus.Information = 0;
-
-   IoCompleteRequest (IrpContext->Irp, IO_NO_INCREMENT);
-   return (Status);
-}
-
-
 NTSTATUS STDCALL
-DriverEntry(PDRIVER_OBJECT _DriverObject,
+DriverEntry(PDRIVER_OBJECT DriverObject,
            PUNICODE_STRING RegistryPath)
 /*
  * FUNCTION: Called by the system to initalize the driver
@@ -399,14 +57,12 @@ DriverEntry(PDRIVER_OBJECT _DriverObject,
 
    DPRINT("VFAT 0.0.6\n");
 
-   VfatDriverObject = _DriverObject;
-
    RtlInitUnicodeString(&DeviceName,
                        L"\\Device\\Vfat");
-   Status = IoCreateDevice(VfatDriverObject,
-                          0,
+   Status = IoCreateDevice(DriverObject,
+                          sizeof(VFAT_GLOBAL_DATA),
                           &DeviceName,
-                          FILE_DEVICE_FILE_SYSTEM,
+                          FILE_DEVICE_DISK_FILE_SYSTEM,
                           0,
                           FALSE,
                           &DeviceObject);
@@ -414,32 +70,30 @@ DriverEntry(PDRIVER_OBJECT _DriverObject,
      {
        return (Status);
      }
+   VfatGlobalData = DeviceObject->DeviceExtension;
+   RtlZeroMemory (VfatGlobalData, sizeof(VFAT_GLOBAL_DATA));
+   VfatGlobalData->DriverObject = DriverObject;
+   VfatGlobalData->DeviceObject = DeviceObject;
 
    DeviceObject->Flags = DO_DIRECT_IO;
-   VfatDriverObject->MajorFunction[IRP_MJ_CLOSE] = VfatBuildRequest;
-   VfatDriverObject->MajorFunction[IRP_MJ_CREATE] = VfatBuildRequest;
-   VfatDriverObject->MajorFunction[IRP_MJ_READ] = VfatBuildRequest;
-   VfatDriverObject->MajorFunction[IRP_MJ_WRITE] = VfatBuildRequest;
-   VfatDriverObject->MajorFunction[IRP_MJ_FILE_SYSTEM_CONTROL] =
-     VfatBuildRequest;
-   VfatDriverObject->MajorFunction[IRP_MJ_QUERY_INFORMATION] =
-     VfatBuildRequest;
-   VfatDriverObject->MajorFunction[IRP_MJ_SET_INFORMATION] =
-     VfatBuildRequest;
-   VfatDriverObject->MajorFunction[IRP_MJ_DIRECTORY_CONTROL] =
-     VfatBuildRequest;
-   VfatDriverObject->MajorFunction[IRP_MJ_QUERY_VOLUME_INFORMATION] =
-     VfatBuildRequest;
-   VfatDriverObject->MajorFunction[IRP_MJ_SET_VOLUME_INFORMATION] =
-     VfatBuildRequest;
-   VfatDriverObject->MajorFunction[IRP_MJ_SHUTDOWN] = VfatShutdown;
-   VfatDriverObject->MajorFunction[IRP_MJ_CLEANUP] = VfatBuildRequest;
-
-   VfatDriverObject->DriverUnload = NULL;
+   DriverObject->MajorFunction[IRP_MJ_CLOSE] = VfatBuildRequest;
+   DriverObject->MajorFunction[IRP_MJ_CREATE] = VfatBuildRequest;
+   DriverObject->MajorFunction[IRP_MJ_READ] = VfatBuildRequest;
+   DriverObject->MajorFunction[IRP_MJ_WRITE] = VfatBuildRequest;
+   DriverObject->MajorFunction[IRP_MJ_FILE_SYSTEM_CONTROL] = VfatBuildRequest;
+   DriverObject->MajorFunction[IRP_MJ_QUERY_INFORMATION] = VfatBuildRequest;
+   DriverObject->MajorFunction[IRP_MJ_SET_INFORMATION] = VfatBuildRequest;
+   DriverObject->MajorFunction[IRP_MJ_DIRECTORY_CONTROL] = VfatBuildRequest;
+   DriverObject->MajorFunction[IRP_MJ_QUERY_VOLUME_INFORMATION] = VfatBuildRequest;
+   DriverObject->MajorFunction[IRP_MJ_SET_VOLUME_INFORMATION] = VfatBuildRequest;
+   DriverObject->MajorFunction[IRP_MJ_SHUTDOWN] = VfatShutdown;
+   DriverObject->MajorFunction[IRP_MJ_CLEANUP] = VfatBuildRequest;
+
+   DriverObject->DriverUnload = NULL;
 
    IoRegisterFileSystem(DeviceObject);
-
    return STATUS_SUCCESS;
 }
 
 /* EOF */
+