mirror of
https://github.com/reactos/reactos.git
synced 2025-07-31 12:02:02 +00:00
Patch by tinus.Fix media change support for CDROMs. This fixes bug #471. Patch by tinus.
svn path=/trunk/; revision=13097
This commit is contained in:
parent
968f3f7c24
commit
69688ce6ab
5 changed files with 132 additions and 43 deletions
|
@ -191,6 +191,19 @@ CdfsDeviceIoControl (IN PDEVICE_OBJECT DeviceObject,
|
||||||
*OutputBufferSize = IoStatus.Information;
|
*OutputBufferSize = IoStatus.Information;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (Status == STATUS_VERIFY_REQUIRED)
|
||||||
|
{
|
||||||
|
PDEVICE_OBJECT DeviceToVerify;
|
||||||
|
NTSTATUS NewStatus;
|
||||||
|
|
||||||
|
DPRINT1("STATUS_VERIFY_REQUIRED\n");
|
||||||
|
DeviceToVerify = IoGetDeviceToVerify(PsGetCurrentThread());
|
||||||
|
IoSetDeviceToVerify(PsGetCurrentThread(), NULL);
|
||||||
|
|
||||||
|
NewStatus = IoVerifyVolume(DeviceToVerify, FALSE);
|
||||||
|
DPRINT1("IoVerifyVolume() retuned (Status %lx)\n", NewStatus);
|
||||||
|
}
|
||||||
|
|
||||||
DPRINT("Returning Status %x\n", Status);
|
DPRINT("Returning Status %x\n", Status);
|
||||||
|
|
||||||
return Status;
|
return Status;
|
||||||
|
|
|
@ -140,28 +140,9 @@ CdfsOpenFile(PDEVICE_EXTENSION DeviceExt,
|
||||||
0,
|
0,
|
||||||
NULL,
|
NULL,
|
||||||
0,
|
0,
|
||||||
TRUE);
|
FALSE);
|
||||||
DPRINT ("Status %lx\n", Status);
|
DPRINT ("Status %lx\n", Status);
|
||||||
if (Status == STATUS_VERIFY_REQUIRED)
|
if (!NT_SUCCESS(Status))
|
||||||
{
|
|
||||||
PDEVICE_OBJECT DeviceToVerify;
|
|
||||||
|
|
||||||
DPRINT1 ("Media change detected!\n");
|
|
||||||
DPRINT1 ("Device %p\n", DeviceExt->VolumeDevice);
|
|
||||||
|
|
||||||
DeviceToVerify = IoGetDeviceToVerify (PsGetCurrentThread ());
|
|
||||||
IoSetDeviceToVerify (PsGetCurrentThread (),
|
|
||||||
NULL);
|
|
||||||
|
|
||||||
Status = IoVerifyVolume (DeviceToVerify,
|
|
||||||
FALSE);
|
|
||||||
if (!NT_SUCCESS(Status))
|
|
||||||
{
|
|
||||||
DPRINT1 ("Status %lx\n", Status);
|
|
||||||
return Status;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (!NT_SUCCESS(Status))
|
|
||||||
{
|
{
|
||||||
DPRINT1 ("Status %lx\n", Status);
|
DPRINT1 ("Status %lx\n", Status);
|
||||||
return Status;
|
return Status;
|
||||||
|
|
|
@ -345,6 +345,7 @@ CdfsMountVolume(PDEVICE_OBJECT DeviceObject,
|
||||||
goto ByeBye;
|
goto ByeBye;
|
||||||
|
|
||||||
NewDeviceObject->Flags = NewDeviceObject->Flags | DO_DIRECT_IO;
|
NewDeviceObject->Flags = NewDeviceObject->Flags | DO_DIRECT_IO;
|
||||||
|
NewDeviceObject->Flags &= ~DO_VERIFY_VOLUME;
|
||||||
DeviceExt = (PVOID)NewDeviceObject->DeviceExtension;
|
DeviceExt = (PVOID)NewDeviceObject->DeviceExtension;
|
||||||
RtlZeroMemory(DeviceExt,
|
RtlZeroMemory(DeviceExt,
|
||||||
sizeof(DEVICE_EXTENSION));
|
sizeof(DEVICE_EXTENSION));
|
||||||
|
|
|
@ -134,6 +134,10 @@ VOID STDCALL
|
||||||
CdromTimerRoutine(IN PDEVICE_OBJECT DeviceObject,
|
CdromTimerRoutine(IN PDEVICE_OBJECT DeviceObject,
|
||||||
IN PVOID Context);
|
IN PVOID Context);
|
||||||
|
|
||||||
|
VOID
|
||||||
|
CdromWorkItem(IN PDEVICE_OBJECT DeviceObject,
|
||||||
|
IN PVOID Context);
|
||||||
|
|
||||||
|
|
||||||
/* FUNCTIONS ****************************************************************/
|
/* FUNCTIONS ****************************************************************/
|
||||||
|
|
||||||
|
@ -1203,7 +1207,10 @@ CdromClassStartIo (IN PDEVICE_OBJECT DeviceObject,
|
||||||
Irp->IoStatus.Status = STATUS_VERIFY_REQUIRED;
|
Irp->IoStatus.Status = STATUS_VERIFY_REQUIRED;
|
||||||
|
|
||||||
/* FIXME: Update drive capacity */
|
/* FIXME: Update drive capacity */
|
||||||
|
IoCompleteRequest (Irp,
|
||||||
|
IO_DISK_INCREMENT);
|
||||||
|
IoStartNextPacket (DeviceObject,
|
||||||
|
FALSE);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1614,11 +1621,68 @@ CdromDeviceControlCompletion (IN PDEVICE_OBJECT DeviceObject,
|
||||||
|
|
||||||
|
|
||||||
VOID STDCALL
|
VOID STDCALL
|
||||||
CdromTimerRoutine(PDEVICE_OBJECT DeviceObject,
|
CdromTimerRoutine(IN PDEVICE_OBJECT DeviceObject,
|
||||||
PVOID Context)
|
IN PVOID Context)
|
||||||
{
|
{
|
||||||
DPRINT ("CdromTimerRoutine() called\n");
|
PIO_WORKITEM WorkItem;
|
||||||
|
|
||||||
|
DPRINT ("CdromTimerRoutine() called\n");
|
||||||
|
WorkItem = IoAllocateWorkItem(DeviceObject);
|
||||||
|
if (!WorkItem)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
IoQueueWorkItem(WorkItem,
|
||||||
|
CdromWorkItem,
|
||||||
|
DelayedWorkQueue,
|
||||||
|
WorkItem);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
VOID
|
||||||
|
CdromWorkItem(IN PDEVICE_OBJECT DeviceObject,
|
||||||
|
IN PVOID Context)
|
||||||
|
{
|
||||||
|
PIRP Irp;
|
||||||
|
KEVENT Event;
|
||||||
|
IO_STATUS_BLOCK IoStatus;
|
||||||
|
NTSTATUS Status;
|
||||||
|
|
||||||
|
DPRINT("CdromWorkItem() called\n");
|
||||||
|
|
||||||
|
IoFreeWorkItem((PIO_WORKITEM) Context);
|
||||||
|
|
||||||
|
KeInitializeEvent(&Event,
|
||||||
|
NotificationEvent,
|
||||||
|
FALSE);
|
||||||
|
|
||||||
|
Irp = IoBuildDeviceIoControlRequest(IOCTL_CDROM_CHECK_VERIFY,
|
||||||
|
DeviceObject,
|
||||||
|
NULL,
|
||||||
|
0,
|
||||||
|
NULL,
|
||||||
|
0,
|
||||||
|
FALSE,
|
||||||
|
&Event,
|
||||||
|
&IoStatus);
|
||||||
|
if (Irp == NULL)
|
||||||
|
{
|
||||||
|
DPRINT("IoBuildDeviceIoControlRequest failed\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Status = IoCallDriver(DeviceObject, Irp);
|
||||||
|
DPRINT("Status: %x\n", Status);
|
||||||
|
|
||||||
|
if (Status == STATUS_PENDING)
|
||||||
|
{
|
||||||
|
KeWaitForSingleObject(&Event,
|
||||||
|
Suspended,
|
||||||
|
KernelMode,
|
||||||
|
FALSE,
|
||||||
|
NULL);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* EOF */
|
/* EOF */
|
||||||
|
|
|
@ -1026,6 +1026,46 @@ ScsiClassInternalIoControl(IN PDEVICE_OBJECT DeviceObject,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Implements part of the directives on:
|
||||||
|
* http://msdn.microsoft.com/library/default.asp?url=/library/en-us/kmarch/hh/kmarch/other_c694d732-fa95-4841-8d61-2a55ee787905.xml.asp
|
||||||
|
*/
|
||||||
|
static VOID
|
||||||
|
ScsiClassInvalidateMedia(IN PDEVICE_OBJECT DeviceObject,
|
||||||
|
OUT NTSTATUS *Status)
|
||||||
|
{
|
||||||
|
PDEVICE_EXTENSION DeviceExtension;
|
||||||
|
PDEVICE_EXTENSION PhysicalExtension;
|
||||||
|
|
||||||
|
DeviceExtension = (PDEVICE_EXTENSION)DeviceObject->DeviceExtension;
|
||||||
|
PhysicalExtension = (PDEVICE_EXTENSION)DeviceExtension->PhysicalDevice->DeviceExtension;
|
||||||
|
|
||||||
|
if (DeviceObject->Characteristics & FILE_REMOVABLE_MEDIA)
|
||||||
|
{
|
||||||
|
DPRINT("Invalidate: test char yields TRUE\n");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
DPRINT("Invalidate: test char yields FALSE\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((DeviceObject->Characteristics & FILE_REMOVABLE_MEDIA) &&
|
||||||
|
(DeviceObject->Vpb->Flags & VPB_MOUNTED))
|
||||||
|
{
|
||||||
|
DPRINT("Set DO_VERIFY_VOLUME\n");
|
||||||
|
DeviceObject->Flags |= DO_VERIFY_VOLUME;
|
||||||
|
*Status = STATUS_VERIFY_REQUIRED;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
*Status = STATUS_IO_DEVICE_ERROR;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Increment the media change count */
|
||||||
|
PhysicalExtension->MediaChangeCount++;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* @implemented
|
* @implemented
|
||||||
*/
|
*/
|
||||||
|
@ -1106,7 +1146,10 @@ ScsiClassInterpretSenseInfo(IN PDEVICE_OBJECT DeviceObject,
|
||||||
|
|
||||||
case SCSI_ADSENSE_NO_MEDIA_IN_DEVICE:
|
case SCSI_ADSENSE_NO_MEDIA_IN_DEVICE:
|
||||||
DPRINT("SCSI_ADSENSE_NO_MEDIA_IN_DEVICE\n");
|
DPRINT("SCSI_ADSENSE_NO_MEDIA_IN_DEVICE\n");
|
||||||
*Status = STATUS_NO_MEDIA_IN_DEVICE;
|
ScsiClassInvalidateMedia(DeviceObject,
|
||||||
|
Status);
|
||||||
|
|
||||||
|
*Status = STATUS_NO_MEDIA_IN_DEVICE;
|
||||||
Retry = FALSE;
|
Retry = FALSE;
|
||||||
|
|
||||||
if((DeviceExtension->MediaChangeEvent != NULL) &&
|
if((DeviceExtension->MediaChangeEvent != NULL) &&
|
||||||
|
@ -1200,22 +1243,9 @@ ScsiClassInterpretSenseInfo(IN PDEVICE_OBJECT DeviceObject,
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((DeviceObject->Characteristics & FILE_REMOVABLE_MEDIA) &&
|
ScsiClassInvalidateMedia(DeviceObject,
|
||||||
(DeviceObject->Vpb->Flags & VPB_MOUNTED))
|
Status);
|
||||||
{
|
Retry = FALSE;
|
||||||
DPRINT("SCSI_SENSE_UNIT_ATTENTION set DoVerifyVol\n");
|
|
||||||
|
|
||||||
DeviceObject->Flags |= DO_VERIFY_VOLUME;
|
|
||||||
*Status = STATUS_VERIFY_REQUIRED;
|
|
||||||
Retry = FALSE;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
*Status = STATUS_IO_DEVICE_ERROR;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Increment the media change count */
|
|
||||||
PhysicalExtension->MediaChangeCount++;
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case SCSI_SENSE_DATA_PROTECT:
|
case SCSI_SENSE_DATA_PROTECT:
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue