diff --git a/reactos/drivers/storage/class/cdrom/cdrom.c b/reactos/drivers/storage/class/cdrom/cdrom.c index b24dfe2a8f2..f86f2decf5e 100644 --- a/reactos/drivers/storage/class/cdrom/cdrom.c +++ b/reactos/drivers/storage/class/cdrom/cdrom.c @@ -2181,9 +2181,7 @@ ScsiCdRomStartIo( } case IOCTL_DISK_GET_LENGTH_INFO: - case IOCTL_DISK_GET_DRIVE_GEOMETRY_EX: case IOCTL_DISK_GET_DRIVE_GEOMETRY: - case IOCTL_CDROM_GET_DRIVE_GEOMETRY_EX: case IOCTL_CDROM_GET_DRIVE_GEOMETRY: { // @@ -3041,6 +3039,131 @@ CdRomDeviceControlCompletion( switch (realIrpStack->Parameters.DeviceIoControl.IoControlCode) { + case IOCTL_DISK_GET_LENGTH_INFO: { + + PREAD_CAPACITY_DATA readCapacityBuffer = srb->DataBuffer; + ULONG lastSector; + ULONG bps; + ULONG lastBit; + ULONG tmp; + + // + // Swizzle bytes from Read Capacity and translate into + // the necessary geometry information in the device extension. + // + + tmp = readCapacityBuffer->BytesPerBlock; + ((PFOUR_BYTE)&bps)->Byte0 = ((PFOUR_BYTE)&tmp)->Byte3; + ((PFOUR_BYTE)&bps)->Byte1 = ((PFOUR_BYTE)&tmp)->Byte2; + ((PFOUR_BYTE)&bps)->Byte2 = ((PFOUR_BYTE)&tmp)->Byte1; + ((PFOUR_BYTE)&bps)->Byte3 = ((PFOUR_BYTE)&tmp)->Byte0; + + // + // Insure that bps is a power of 2. + // This corrects a problem with the HP 4020i CDR where it + // returns an incorrect number for bytes per sector. + // + + if (!bps) { + bps = 2048; + } else { + lastBit = (ULONG) -1; + while (bps) { + lastBit++; + bps = bps >> 1; + } + + bps = 1 << lastBit; + } + deviceExtension->DiskGeometry->Geometry.BytesPerSector = bps; + + DebugPrint((2, + "CdRomDeviceControlCompletion: Calculated bps %#x\n", + deviceExtension->DiskGeometry->Geometry.BytesPerSector)); + + // + // Copy last sector in reverse byte order. + // + + tmp = readCapacityBuffer->LogicalBlockAddress; + ((PFOUR_BYTE)&lastSector)->Byte0 = ((PFOUR_BYTE)&tmp)->Byte3; + ((PFOUR_BYTE)&lastSector)->Byte1 = ((PFOUR_BYTE)&tmp)->Byte2; + ((PFOUR_BYTE)&lastSector)->Byte2 = ((PFOUR_BYTE)&tmp)->Byte1; + ((PFOUR_BYTE)&lastSector)->Byte3 = ((PFOUR_BYTE)&tmp)->Byte0; + + // + // Calculate sector to byte shift. + // + + WHICH_BIT(bps, deviceExtension->SectorShift); + + DebugPrint((2,"SCSI ScsiClassReadDriveCapacity: Sector size is %d\n", + deviceExtension->DiskGeometry->Geometry.BytesPerSector)); + + DebugPrint((2,"SCSI ScsiClassReadDriveCapacity: Number of Sectors is %d\n", + lastSector + 1)); + + // + // Calculate media capacity in bytes. + // + + deviceExtension->PartitionLength.QuadPart = (LONGLONG)(lastSector + 1); + + // + // Calculate number of cylinders. + // + + deviceExtension->DiskGeometry->Geometry.Cylinders.QuadPart = (LONGLONG)((lastSector + 1)/(32 * 64)); + + deviceExtension->PartitionLength.QuadPart = + (deviceExtension->PartitionLength.QuadPart << deviceExtension->SectorShift); + + if (DeviceObject->Characteristics & FILE_REMOVABLE_MEDIA) { + + // + // This device supports removable media. + // + + deviceExtension->DiskGeometry->Geometry.MediaType = RemovableMedia; + + } else { + + // + // Assume media type is fixed disk. + // + + deviceExtension->DiskGeometry->Geometry.MediaType = FixedMedia; + } + + // + // Assume sectors per track are 32; + // + + deviceExtension->DiskGeometry->Geometry.SectorsPerTrack = 32; + + // + // Assume tracks per cylinder (number of heads) is 64. + // + + deviceExtension->DiskGeometry->Geometry.TracksPerCylinder = 64; + + // + // Copy the device extension's geometry info into the user buffer. + // + + RtlMoveMemory(realIrp->AssociatedIrp.SystemBuffer, + &deviceExtension->PartitionLength, + sizeof(GET_LENGTH_INFORMATION)); + + // + // update information field. + // + + realIrp->IoStatus.Information = sizeof(DISK_GEOMETRY); + break; + } + + case IOCTL_DISK_GET_DRIVE_GEOMETRY: case IOCTL_CDROM_GET_DRIVE_GEOMETRY: { PREAD_CAPACITY_DATA readCapacityBuffer = srb->DataBuffer;