Restricted mounting of file systems (e.g. don't try to mount a cdrom file system to a harddisk).

Moved helper functions of IoVerifyVolume().
Minor improvements to IoVerifyVolume().

svn path=/trunk/; revision=2858
This commit is contained in:
Eric Kohl 2002-04-19 10:10:29 +00:00
parent 3665f8cac4
commit b88eb21a16
2 changed files with 175 additions and 124 deletions

View file

@ -1,4 +1,4 @@
/* $Id: device.c,v 1.37 2002/04/10 09:57:31 ekohl Exp $ /* $Id: device.c,v 1.38 2002/04/19 10:10:29 ekohl Exp $
* *
* COPYRIGHT: See COPYING in the top level directory * COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS kernel * PROJECT: ReactOS kernel
@ -749,31 +749,4 @@ IoQueryDeviceEnumInfo (
} }
PDEVICE_OBJECT STDCALL
IoGetDeviceToVerify (PETHREAD Thread)
/*
* FUNCTION: Returns a pointer to the device, representing a removable-media
* device, that is the target of the given thread's I/O request
*/
{
return(Thread->DeviceToVerify);
}
VOID STDCALL
IoSetDeviceToVerify(IN PETHREAD Thread,
IN PDEVICE_OBJECT DeviceObject)
{
Thread->DeviceToVerify = DeviceObject;
}
VOID STDCALL
IoSetHardErrorOrVerifyDevice(PIRP Irp,
PDEVICE_OBJECT DeviceObject)
{
Irp->Tail.Overlay.Thread->DeviceToVerify = DeviceObject;
}
/* EOF */ /* EOF */

View file

@ -1,4 +1,4 @@
/* $Id: fs.c,v 1.22 2002/04/10 09:57:31 ekohl Exp $ /* $Id: fs.c,v 1.23 2002/04/19 10:10:29 ekohl Exp $
* *
* COPYRIGHT: See COPYING in the top level directory * COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS kernel * PROJECT: ReactOS kernel
@ -18,20 +18,22 @@
#define NDEBUG #define NDEBUG
#include <internal/debug.h> #include <internal/debug.h>
/* TYPES *******************************************************************/ /* TYPES *******************************************************************/
typedef struct typedef struct _FILE_SYSTEM_OBJECT
{ {
PDEVICE_OBJECT DeviceObject; PDEVICE_OBJECT DeviceObject;
LIST_ENTRY Entry; LIST_ENTRY Entry;
} FILE_SYSTEM_OBJECT; } FILE_SYSTEM_OBJECT, *PFILE_SYSTEM_OBJECT;
typedef struct typedef struct _FS_CHANGE_NOTIFY_ENTRY
{ {
LIST_ENTRY FsChangeNotifyList; LIST_ENTRY FsChangeNotifyList;
PDRIVER_OBJECT DriverObject; PDRIVER_OBJECT DriverObject;
PFSDNOTIFICATIONPROC FSDNotificationProc; PFSDNOTIFICATIONPROC FSDNotificationProc;
} FS_CHANGE_NOTIFY_ENTRY, *PFS_CHANGE_NOTIFY_ENTRY; } FS_CHANGE_NOTIFY_ENTRY, *PFS_CHANGE_NOTIFY_ENTRY;
/* GLOBALS ******************************************************************/ /* GLOBALS ******************************************************************/
@ -45,8 +47,10 @@ static LIST_ENTRY FsChangeNotifyListHead;
#define TAG_FS_CHANGE_NOTIFY TAG('F', 'S', 'C', 'N') #define TAG_FS_CHANGE_NOTIFY TAG('F', 'S', 'C', 'N')
static VOID IopNotifyFileSystemChange(PDEVICE_OBJECT DeviceObject, static VOID
BOOLEAN DriverActive); IopNotifyFileSystemChange(PDEVICE_OBJECT DeviceObject,
BOOLEAN DriverActive);
/* FUNCTIONS *****************************************************************/ /* FUNCTIONS *****************************************************************/
@ -219,9 +223,9 @@ IoAskFileSystemToMountDevice(PDEVICE_OBJECT DeviceObject,
NTSTATUS NTSTATUS
IoAskFileSystemToLoad(PDEVICE_OBJECT DeviceObject) IoAskFileSystemToLoad(IN PDEVICE_OBJECT DeviceObject)
{ {
UNIMPLEMENTED; UNIMPLEMENTED;
} }
@ -235,46 +239,78 @@ IoTryToMountStorageDevice(IN PDEVICE_OBJECT DeviceObject,
* RETURNS: Status * RETURNS: Status
*/ */
{ {
KIRQL oldlvl; KIRQL oldlvl;
PLIST_ENTRY current_entry; PLIST_ENTRY current_entry;
FILE_SYSTEM_OBJECT* current; FILE_SYSTEM_OBJECT* current;
NTSTATUS Status; NTSTATUS Status;
DEVICE_TYPE MatchingDeviceType;
assert_irql(PASSIVE_LEVEL);
assert_irql(PASSIVE_LEVEL);
DPRINT1("IoTryToMountStorageDevice(DeviceObject %x)\n",DeviceObject);
DPRINT("IoTryToMountStorageDevice(DeviceObject %x)\n",DeviceObject);
KeAcquireSpinLock(&FileSystemListLock,&oldlvl);
current_entry = FileSystemListHead.Flink; switch (DeviceObject->DeviceType)
while (current_entry!=(&FileSystemListHead)) {
{ case FILE_DEVICE_DISK:
current = CONTAINING_RECORD(current_entry,FILE_SYSTEM_OBJECT,Entry); case FILE_DEVICE_VIRTUAL_DISK: /* ?? */
KeReleaseSpinLock(&FileSystemListLock,oldlvl); MatchingDeviceType = FILE_DEVICE_DISK_FILE_SYSTEM;
Status = IoAskFileSystemToMountDevice(current->DeviceObject, break;
DeviceObject);
KeAcquireSpinLock(&FileSystemListLock,&oldlvl); case FILE_DEVICE_CD_ROM:
switch (Status) MatchingDeviceType = FILE_DEVICE_CD_ROM_FILE_SYSTEM;
{ break;
case STATUS_FS_DRIVER_REQUIRED:
KeReleaseSpinLock(&FileSystemListLock,oldlvl); case FILE_DEVICE_NETWORK:
(void)IoAskFileSystemToLoad(DeviceObject); MatchingDeviceType = FILE_DEVICE_NETWORK_FILE_SYSTEM;
KeAcquireSpinLock(&FileSystemListLock,&oldlvl); break;
current_entry = FileSystemListHead.Flink;
break; case FILE_DEVICE_TAPE:
MatchingDeviceType = FILE_DEVICE_TAPE_FILE_SYSTEM;
case STATUS_SUCCESS: break;
DeviceObject->Vpb->Flags = DeviceObject->Vpb->Flags |
VPB_MOUNTED; default:
KeReleaseSpinLock(&FileSystemListLock,oldlvl); CPRINT("No matching file system type found for device type: %x\n",
return(STATUS_SUCCESS); DeviceObject->DeviceType);
return(STATUS_UNRECOGNIZED_VOLUME);
case STATUS_UNRECOGNIZED_VOLUME: }
default:
current_entry = current_entry->Flink; KeAcquireSpinLock(&FileSystemListLock,&oldlvl);
} current_entry = FileSystemListHead.Flink;
} while (current_entry!=(&FileSystemListHead))
KeReleaseSpinLock(&FileSystemListLock,oldlvl); {
return(STATUS_UNRECOGNIZED_VOLUME); current = CONTAINING_RECORD(current_entry,FILE_SYSTEM_OBJECT,Entry);
if (current->DeviceObject->DeviceType != MatchingDeviceType)
{
current_entry = current_entry->Flink;
continue;
}
KeReleaseSpinLock(&FileSystemListLock,oldlvl);
Status = IoAskFileSystemToMountDevice(current->DeviceObject,
DeviceObject);
KeAcquireSpinLock(&FileSystemListLock,&oldlvl);
switch (Status)
{
case STATUS_FS_DRIVER_REQUIRED:
KeReleaseSpinLock(&FileSystemListLock,oldlvl);
(void)IoAskFileSystemToLoad(DeviceObject);
KeAcquireSpinLock(&FileSystemListLock,&oldlvl);
current_entry = FileSystemListHead.Flink;
break;
case STATUS_SUCCESS:
DeviceObject->Vpb->Flags = DeviceObject->Vpb->Flags |
VPB_MOUNTED;
KeReleaseSpinLock(&FileSystemListLock,oldlvl);
return(STATUS_SUCCESS);
case STATUS_UNRECOGNIZED_VOLUME:
default:
current_entry = current_entry->Flink;
}
}
KeReleaseSpinLock(&FileSystemListLock,oldlvl);
return(STATUS_UNRECOGNIZED_VOLUME);
} }
@ -300,11 +336,9 @@ NTSTATUS STDCALL
IoVerifyVolume(IN PDEVICE_OBJECT DeviceObject, IoVerifyVolume(IN PDEVICE_OBJECT DeviceObject,
IN BOOLEAN AllowRawMount) IN BOOLEAN AllowRawMount)
{ {
#if 0 IO_STATUS_BLOCK IoStatusBlock;
IO_STATUS_BLOCK IoStatusBlock, PKEVENT Event;
KEVENT Event;
PIRP Irp; PIRP Irp;
#endif
NTSTATUS Status; NTSTATUS Status;
DPRINT1("IoVerifyVolume(DeviceObject %x AllowRawMount %x)\n", DPRINT1("IoVerifyVolume(DeviceObject %x AllowRawMount %x)\n",
@ -321,18 +355,30 @@ IoVerifyVolume(IN PDEVICE_OBJECT DeviceObject,
if (DeviceObject->Vpb->Flags & VPB_MOUNTED) if (DeviceObject->Vpb->Flags & VPB_MOUNTED)
{ {
/* FIXME: Issue verify request to the FSD */ /* Issue verify request to the FSD */
#if 0 Event = ExAllocatePool(NonPagedPool,
KeInitializeEvent(&Event,...); sizeof(KEVENT));
if (Event == NULL)
return(STATUS_INSUFFICIENT_RESOURCES);
KeInitializeEvent(Event,
NotificationEvent,
FALSE);
Irp = IoBuildFilesystemControlRequest(IRP_MN_VERIFY_VOLUME, Irp = IoBuildFilesystemControlRequest(IRP_MN_VERIFY_VOLUME,
DeviceObject, DeviceObject,
&Event, Event,
&IoStatusBlock, &IoStatusBlock,
&DeviceToMount) NULL); //DeviceToMount);
Status = IoCallDriver(DeviceObject,
#endif Irp);
if (Status==STATUS_PENDING)
{
KeWaitForSingleObject(Event,Executive,KernelMode,FALSE,NULL);
Status = IoStatusBlock.Status;
}
ExFreePool(Event);
if (NT_SUCCESS(Status)) if (NT_SUCCESS(Status))
{ {
@ -346,6 +392,8 @@ IoVerifyVolume(IN PDEVICE_OBJECT DeviceObject,
if (Status == STATUS_WRONG_VOLUME) if (Status == STATUS_WRONG_VOLUME)
{ {
/* FIXME: Replace existing VPB by a new one */ /* FIXME: Replace existing VPB by a new one */
DPRINT1("Wrong volume!\n");
} }
@ -361,49 +409,79 @@ IoVerifyVolume(IN PDEVICE_OBJECT DeviceObject,
} }
VOID STDCALL PDEVICE_OBJECT STDCALL
IoRegisterFileSystem(PDEVICE_OBJECT DeviceObject) IoGetDeviceToVerify(IN PETHREAD Thread)
/*
* FUNCTION: Returns a pointer to the device, representing a removable-media
* device, that is the target of the given thread's I/O request
*/
{ {
FILE_SYSTEM_OBJECT* fs; return(Thread->DeviceToVerify);
DPRINT("IoRegisterFileSystem(DeviceObject %x)\n",DeviceObject);
fs = ExAllocatePoolWithTag(NonPagedPool, sizeof(FILE_SYSTEM_OBJECT),
TAG_FILE_SYSTEM);
assert(fs!=NULL);
fs->DeviceObject = DeviceObject;
ExInterlockedInsertTailList(&FileSystemListHead,&fs->Entry,
&FileSystemListLock);
IopNotifyFileSystemChange(DeviceObject, TRUE);
} }
VOID STDCALL VOID STDCALL
IoUnregisterFileSystem(PDEVICE_OBJECT DeviceObject) IoSetDeviceToVerify(IN PETHREAD Thread,
IN PDEVICE_OBJECT DeviceObject)
{ {
KIRQL oldlvl; Thread->DeviceToVerify = DeviceObject;
PLIST_ENTRY current_entry; }
FILE_SYSTEM_OBJECT* current;
DPRINT("IoUnregisterFileSystem(DeviceObject %x)\n",DeviceObject);
VOID STDCALL
KeAcquireSpinLock(&FileSystemListLock,&oldlvl); IoSetHardErrorOrVerifyDevice(IN PIRP Irp,
current_entry = FileSystemListHead.Flink; IN PDEVICE_OBJECT DeviceObject)
while (current_entry!=(&FileSystemListHead)) {
{ Irp->Tail.Overlay.Thread->DeviceToVerify = DeviceObject;
current = CONTAINING_RECORD(current_entry,FILE_SYSTEM_OBJECT,Entry); }
if (current->DeviceObject == DeviceObject)
{
RemoveEntryList(current_entry); VOID STDCALL
ExFreePool(current); IoRegisterFileSystem(IN PDEVICE_OBJECT DeviceObject)
KeReleaseSpinLock(&FileSystemListLock,oldlvl); {
IopNotifyFileSystemChange(DeviceObject, FALSE); PFILE_SYSTEM_OBJECT Fs;
return;
} DPRINT("IoRegisterFileSystem(DeviceObject %x)\n",DeviceObject);
current_entry = current_entry->Flink;
} Fs = ExAllocatePoolWithTag(NonPagedPool,
KeReleaseSpinLock(&FileSystemListLock,oldlvl); sizeof(FILE_SYSTEM_OBJECT),
TAG_FILE_SYSTEM);
assert(Fs!=NULL);
Fs->DeviceObject = DeviceObject;
ExInterlockedInsertTailList(&FileSystemListHead,
&Fs->Entry,
&FileSystemListLock);
IopNotifyFileSystemChange(DeviceObject,
TRUE);
}
VOID STDCALL
IoUnregisterFileSystem(IN PDEVICE_OBJECT DeviceObject)
{
KIRQL oldlvl;
PLIST_ENTRY current_entry;
PFILE_SYSTEM_OBJECT current;
DPRINT("IoUnregisterFileSystem(DeviceObject %x)\n",DeviceObject);
KeAcquireSpinLock(&FileSystemListLock,&oldlvl);
current_entry = FileSystemListHead.Flink;
while (current_entry!=(&FileSystemListHead))
{
current = CONTAINING_RECORD(current_entry,FILE_SYSTEM_OBJECT,Entry);
if (current->DeviceObject == DeviceObject)
{
RemoveEntryList(current_entry);
ExFreePool(current);
KeReleaseSpinLock(&FileSystemListLock,oldlvl);
IopNotifyFileSystemChange(DeviceObject, FALSE);
return;
}
current_entry = current_entry->Flink;
}
KeReleaseSpinLock(&FileSystemListLock,oldlvl);
} }