diff --git a/reactos/drivers/storage/fdc/fdc/CMakeLists.txt b/reactos/drivers/storage/fdc/fdc/CMakeLists.txt index 63eb32d526a..8dc87de1a9f 100644 --- a/reactos/drivers/storage/fdc/fdc/CMakeLists.txt +++ b/reactos/drivers/storage/fdc/fdc/CMakeLists.txt @@ -2,6 +2,7 @@ add_library(fdc SHARED fdc.c fdo.c + misc.c pdo.c fdc.rc) diff --git a/reactos/drivers/storage/fdc/fdc/fdc.h b/reactos/drivers/storage/fdc/fdc/fdc.h index 8a9cfbe77dc..e63099c3ac0 100644 --- a/reactos/drivers/storage/fdc/fdc/fdc.h +++ b/reactos/drivers/storage/fdc/fdc/fdc.h @@ -22,9 +22,10 @@ typedef struct _DRIVE_INFO { struct _CONTROLLER_INFO *ControllerInfo; UCHAR UnitNumber; /* 0,1,2,3 */ -// LARGE_INTEGER MotorStartTime; - PDEVICE_OBJECT DeviceObject; + ULONG PeripheralNumber; + PDEVICE_OBJECT DeviceObject; CM_FLOPPY_DEVICE_DATA FloppyDeviceData; +// LARGE_INTEGER MotorStartTime; // DISK_GEOMETRY DiskGeometry; // UCHAR BytesPerSectorCode; // WCHAR SymLinkBuffer[MAX_DEVICE_NAME]; @@ -98,20 +99,30 @@ typedef struct _PDO_DEVICE_EXTENSION UNICODE_STRING CompatibleIds; // REG_MULTI_SZ } PDO_DEVICE_EXTENSION, *PPDO_DEVICE_EXTENSION; +#define FDC_TAG 'acdF' /* fdo.c */ NTSTATUS NTAPI -FdcFdoPnp(IN PDEVICE_OBJECT DeviceObject, - IN PIRP Irp); +FdcFdoPnp( + IN PDEVICE_OBJECT DeviceObject, + IN PIRP Irp); + +/* misc.c */ + +NTSTATUS +DuplicateUnicodeString( + IN ULONG Flags, + IN PCUNICODE_STRING SourceString, + OUT PUNICODE_STRING DestinationString); /* pdo.c */ NTSTATUS NTAPI -FdcPdoPnp(IN PDEVICE_OBJECT DeviceObject, - IN PIRP Irp); +FdcPdoPnp( + IN PDEVICE_OBJECT DeviceObject, + IN PIRP Irp); - -/* EOF */ \ No newline at end of file +/* EOF */ diff --git a/reactos/drivers/storage/fdc/fdc/fdo.c b/reactos/drivers/storage/fdc/fdc/fdo.c index bc9c700135e..58d04b289c6 100644 --- a/reactos/drivers/storage/fdc/fdc/fdo.c +++ b/reactos/drivers/storage/fdc/fdc/fdo.c @@ -232,6 +232,7 @@ FdcFdoConfigCallback( DriveInfo->ControllerInfo = &DeviceExtension->ControllerInfo; DriveInfo->UnitNumber = i; + DriveInfo->PeripheralNumber = PeripheralNumber; DriveInfo->FloppyDeviceData.MaxDensity = FloppyDeviceData->MaxDensity; DriveInfo->FloppyDeviceData.MountDensity = FloppyDeviceData->MountDensity; @@ -261,6 +262,63 @@ FdcFdoConfigCallback( } +static +NTSTATUS +PciCreateHardwareIDsString(PUNICODE_STRING HardwareIDs) +{ + WCHAR Buffer[256]; + UNICODE_STRING BufferU; + ULONG Index; + + Index = 0; + Index += swprintf(&Buffer[Index], + L"FDC\\GENERIC_FLOPPY_DRIVE"); + Index++; + + Buffer[Index] = UNICODE_NULL; + + BufferU.Length = BufferU.MaximumLength = (USHORT) Index * sizeof(WCHAR); + BufferU.Buffer = Buffer; + + return DuplicateUnicodeString(0, &BufferU, HardwareIDs); +} + + +static +NTSTATUS +PciCreateCompatibleIDsString(PUNICODE_STRING CompatibleIDs) +{ + WCHAR Buffer[256]; + UNICODE_STRING BufferU; + ULONG Index; + + Index = 0; + Index += swprintf(&Buffer[Index], + L"GenFloppyDisk"); + Index++; + + Buffer[Index] = UNICODE_NULL; + + BufferU.Length = BufferU.MaximumLength = (USHORT)Index * sizeof(WCHAR); + BufferU.Buffer = Buffer; + + return DuplicateUnicodeString(0, &BufferU, CompatibleIDs); +} + + +static +NTSTATUS +PciCreateInstanceIDString(PUNICODE_STRING InstanceID, + ULONG PeripheralNumber) +{ + WCHAR Buffer[3]; + + swprintf(Buffer, L"%02X", PeripheralNumber & 0xff); + + return RtlCreateUnicodeString(InstanceID, Buffer) ? STATUS_SUCCESS : STATUS_INSUFFICIENT_RESOURCES; +} + + static NTSTATUS FdcFdoQueryBusRelations( @@ -352,6 +410,59 @@ FdcFdoQueryBusRelations( Pdo->Flags |= DO_DIRECT_IO; Pdo->Flags |= DO_POWER_PAGABLE; Pdo->Flags &= ~DO_DEVICE_INITIALIZING; + + /* Add Device ID string */ + RtlCreateUnicodeString(&PdoDeviceExtension->DeviceId, + L"FDC\\GENERIC_FLOPPY_DRIVE"); + DPRINT1("DeviceID: %S\n", PdoDeviceExtension->DeviceId.Buffer); + + /* Add Hardware IDs string */ + Status = PciCreateHardwareIDsString(&PdoDeviceExtension->HardwareIds); + if (!NT_SUCCESS(Status)) + { +// ErrorStatus = Status; +// ErrorOccurred = TRUE; + break; + } + + /* Add Compatible IDs string */ + Status = PciCreateCompatibleIDsString(&PdoDeviceExtension->CompatibleIds); + if (!NT_SUCCESS(Status)) + { +// ErrorStatus = Status; +// ErrorOccurred = TRUE; + break; + } + + /* Add Instance ID string */ + Status = PciCreateInstanceIDString(&PdoDeviceExtension->InstanceId, + DriveInfo->PeripheralNumber); + if (!NT_SUCCESS(Status)) + { +// ErrorStatus = Status; +// ErrorOccurred = TRUE; + break; + } + +#if 0 + /* Add device description string */ + Status = PciCreateDeviceDescriptionString(&PdoDeviceExtension->DeviceDescription, Device); + if (!NT_SUCCESS(Status)) + { +// ErrorStatus = Status; +// ErrorOccurred = TRUE; + break; + } + + /* Add device location string */ + Status = PciCreateDeviceLocationString(&PdoDeviceExtension->DeviceLocation, Device); + if (!NT_SUCCESS(Status)) + { +// ErrorStatus = Status; +// ErrorOccurred = TRUE; + break; + } +#endif } ObReferenceObject(DriveInfo->DeviceObject); diff --git a/reactos/drivers/storage/fdc/fdc/misc.c b/reactos/drivers/storage/fdc/fdc/misc.c new file mode 100644 index 00000000000..fc45531215c --- /dev/null +++ b/reactos/drivers/storage/fdc/fdc/misc.c @@ -0,0 +1,66 @@ +/* + * PROJECT: ReactOS Floppy Disk Controller Driver + * LICENSE: GNU GPLv2 only as published by the Free Software Foundation + * FILE: drivers/storage/fdc/fdc/misc.c + * PURPOSE: Misc Routines + * PROGRAMMERS: Eric Kohl + */ + +/* INCLUDES *******************************************************************/ + +#include "fdc.h" + +#define NDEBUG +#include + +/* FUNCTIONS ******************************************************************/ + +NTSTATUS +DuplicateUnicodeString( + IN ULONG Flags, + IN PCUNICODE_STRING SourceString, + OUT PUNICODE_STRING DestinationString) +{ + USHORT DestMaxLength; + + if (SourceString == NULL || + DestinationString == NULL || + SourceString->Length > SourceString->MaximumLength || + (SourceString->Length == 0 && SourceString->MaximumLength > 0 && SourceString->Buffer == NULL) || + Flags == RTL_DUPLICATE_UNICODE_STRING_ALLOCATE_NULL_STRING || + Flags >= 4) + { + return STATUS_INVALID_PARAMETER; + } + + if ((SourceString->Length == 0) && + (Flags != (RTL_DUPLICATE_UNICODE_STRING_NULL_TERMINATE | + RTL_DUPLICATE_UNICODE_STRING_ALLOCATE_NULL_STRING))) + { + DestinationString->Length = 0; + DestinationString->MaximumLength = 0; + DestinationString->Buffer = NULL; + } + else + { + DestMaxLength = SourceString->Length; + + if (Flags & RTL_DUPLICATE_UNICODE_STRING_NULL_TERMINATE) + DestMaxLength += sizeof(UNICODE_NULL); + + DestinationString->Buffer = ExAllocatePoolWithTag(PagedPool, DestMaxLength, FDC_TAG); + if (DestinationString->Buffer == NULL) + return STATUS_NO_MEMORY; + + RtlCopyMemory(DestinationString->Buffer, SourceString->Buffer, SourceString->Length); + DestinationString->Length = SourceString->Length; + DestinationString->MaximumLength = DestMaxLength; + + if (Flags & RTL_DUPLICATE_UNICODE_STRING_NULL_TERMINATE) + DestinationString->Buffer[DestinationString->Length / sizeof(WCHAR)] = 0; + } + + return STATUS_SUCCESS; +} + +/* EOF */ diff --git a/reactos/drivers/storage/fdc/fdc/pdo.c b/reactos/drivers/storage/fdc/fdc/pdo.c index 86ef7110783..8b3d3d536a7 100644 --- a/reactos/drivers/storage/fdc/fdc/pdo.c +++ b/reactos/drivers/storage/fdc/fdc/pdo.c @@ -12,14 +12,182 @@ /* FUNCTIONS ******************************************************************/ +static +NTSTATUS +FdcPdoQueryCapabilities( + IN PDEVICE_OBJECT DeviceObject, + PIO_STACK_LOCATION IrpSp) +{ + PPDO_DEVICE_EXTENSION DeviceExtension; + PDEVICE_CAPABILITIES DeviceCapabilities; + + DPRINT("Called\n"); + + DeviceExtension = (PPDO_DEVICE_EXTENSION)DeviceObject->DeviceExtension; + DeviceCapabilities = IrpSp->Parameters.DeviceCapabilities.Capabilities; + + if (DeviceCapabilities->Version != 1) + return STATUS_UNSUCCESSFUL; + + DeviceCapabilities->UniqueID = FALSE; + DeviceCapabilities->Address = DeviceExtension->DriveInfo->PeripheralNumber; + + return STATUS_SUCCESS; +} + + +static +NTSTATUS +FdcPdoQueryId( + IN PDEVICE_OBJECT DeviceObject, + IN PIO_STACK_LOCATION IrpSp, + OUT ULONG_PTR *Information) +{ + PPDO_DEVICE_EXTENSION DeviceExtension; + PUNICODE_STRING SourceString; + UNICODE_STRING String; + NTSTATUS Status; + + DeviceExtension = (PPDO_DEVICE_EXTENSION)DeviceObject->DeviceExtension; + RtlInitUnicodeString(&String, NULL); + + switch (IrpSp->Parameters.QueryId.IdType) + { + case BusQueryDeviceID: + DPRINT1("IRP_MJ_PNP / IRP_MN_QUERY_ID / BusQueryDeviceID\n"); + SourceString = &DeviceExtension->DeviceId; + break; + + case BusQueryHardwareIDs: + DPRINT1("IRP_MJ_PNP / IRP_MN_QUERY_ID / BusQueryHardwareIDs\n"); + SourceString = &DeviceExtension->HardwareIds; + break; + + case BusQueryCompatibleIDs: + DPRINT1("IRP_MJ_PNP / IRP_MN_QUERY_ID / BusQueryCompatibleIDs\n"); + SourceString = &DeviceExtension->CompatibleIds; + break; + + case BusQueryInstanceID: + DPRINT1("IRP_MJ_PNP / IRP_MN_QUERY_ID / BusQueryInstanceID\n"); + SourceString = &DeviceExtension->InstanceId; + break; + + default: + DPRINT1("IRP_MJ_PNP / IRP_MN_QUERY_ID / unknown query id type 0x%lx\n", + IrpSp->Parameters.QueryId.IdType); + ASSERT(FALSE); + return STATUS_NOT_SUPPORTED; + } + + Status = DuplicateUnicodeString(RTL_DUPLICATE_UNICODE_STRING_NULL_TERMINATE, + SourceString, + &String); + + *Information = (ULONG_PTR)String.Buffer; + + return Status; +} + + NTSTATUS NTAPI FdcPdoPnp( IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp) { - NTSTATUS Status = STATUS_NOT_SUPPORTED; + PIO_STACK_LOCATION IrpSp; + ULONG_PTR Information = 0; + NTSTATUS Status; + DPRINT1("FdcPdoPnp()\n"); + + Status = Irp->IoStatus.Status; + + IrpSp = IoGetCurrentIrpStackLocation(Irp); + + switch (IrpSp->MinorFunction) + { + case IRP_MN_DEVICE_USAGE_NOTIFICATION: + DPRINT1("Unimplemented IRP_MN_DEVICE_USAGE_NOTIFICATION received\n"); + break; + + case IRP_MN_EJECT: + DPRINT1("Unimplemented IRP_MN_EJECT received\n"); + break; + + case IRP_MN_QUERY_BUS_INFORMATION: + DPRINT1("IRP_MN_QUERY_BUS_INFORMATION received\n"); + break; + + case IRP_MN_QUERY_CAPABILITIES: + DPRINT1("IRP_MN_QUERY_CAPABILITIES received\n"); + Status = FdcPdoQueryCapabilities(DeviceObject, IrpSp); + break; + + case IRP_MN_QUERY_DEVICE_RELATIONS: + DPRINT1("IRP_MN_QUERY_DEVICE_RELATIONS received\n"); + break; + + case IRP_MN_QUERY_DEVICE_TEXT: + DPRINT1("IRP_MN_QUERY_DEVICE_TEXT received\n"); + break; + + case IRP_MN_QUERY_ID: + DPRINT1("IRP_MN_QUERY_ID received\n"); + Status = FdcPdoQueryId(DeviceObject, IrpSp, &Information); + break; + + case IRP_MN_QUERY_PNP_DEVICE_STATE: + DPRINT1("Unimplemented IRP_MN_QUERY_ID received\n"); + break; + + case IRP_MN_QUERY_RESOURCE_REQUIREMENTS: + DPRINT1("IRP_MN_QUERY_RESOURCE_REQUIREMENTS received\n"); + break; + + case IRP_MN_QUERY_RESOURCES: + DPRINT1("IRP_MN_QUERY_RESOURCES received\n"); + break; + + case IRP_MN_SET_LOCK: + DPRINT1("Unimplemented IRP_MN_SET_LOCK received\n"); + break; + + case IRP_MN_START_DEVICE: + DPRINT1("IRP_MN_START_DEVICE received\n"); + break; + + case IRP_MN_QUERY_STOP_DEVICE: + case IRP_MN_CANCEL_STOP_DEVICE: + case IRP_MN_STOP_DEVICE: + case IRP_MN_QUERY_REMOVE_DEVICE: + case IRP_MN_CANCEL_REMOVE_DEVICE: + case IRP_MN_SURPRISE_REMOVAL: + Status = STATUS_SUCCESS; + break; + + case IRP_MN_REMOVE_DEVICE: + DPRINT1("IRP_MN_REMOVE_DEVICE received\n"); + break; + + case IRP_MN_FILTER_RESOURCE_REQUIREMENTS: + DPRINT1("IRP_MN_FILTER_RESOURCE_REQUIREMENTS received\n"); + /* Nothing to do */ + Irp->IoStatus.Status = Status; + break; + + default: + DPRINT1("Unknown IOCTL 0x%lx\n", IrpSp->MinorFunction); + break; + } + + Irp->IoStatus.Information = Information; + Irp->IoStatus.Status = Status; + IoCompleteRequest(Irp, IO_NO_INCREMENT); + + DPRINT1("Leaving. Status 0x%X\n", Status); + return Status; }