mirror of
https://github.com/reactos/reactos.git
synced 2024-07-12 07:35:10 +00:00
[USBSTOR]
- Start implementing SCSI read svn path=/branches/usb-bringup/; revision=51654
This commit is contained in:
parent
45f27e8b8c
commit
fc34f0177d
|
@ -103,6 +103,35 @@ USBSTOR_HandleExecuteSCSI(
|
|||
Request->SrbStatus = SRB_STATUS_ERROR;
|
||||
}
|
||||
}
|
||||
else if (pCDB->MODE_SENSE.OperationCode == SCSIOP_READ)
|
||||
{
|
||||
DPRINT1("SCSIOP_READ DataTransferLength %lu\n", Request->DataTransferLength);
|
||||
ASSERT(Request->DataBuffer);
|
||||
|
||||
//
|
||||
// send read command
|
||||
//
|
||||
Status = USBSTOR_SendReadCmd(DeviceObject, Request, &TransferredLength);
|
||||
DPRINT1("USBSTOR_SendReadCmd Status %x BytesReturned %lu\n", Status, TransferredLength);
|
||||
|
||||
if (NT_SUCCESS(Status))
|
||||
{
|
||||
//
|
||||
// store returned info length
|
||||
//
|
||||
Irp->IoStatus.Information = TransferredLength;
|
||||
Request->SrbStatus = SRB_STATUS_SUCCESS;
|
||||
}
|
||||
else
|
||||
{
|
||||
//
|
||||
// failed to retrieve sense data
|
||||
//
|
||||
Irp->IoStatus.Information = 0;
|
||||
Request->SrbStatus = SRB_STATUS_ERROR;
|
||||
}
|
||||
}
|
||||
|
||||
else
|
||||
{
|
||||
UNIMPLEMENTED;
|
||||
|
|
|
@ -489,6 +489,12 @@ USBSTOR_SendCapacityCmd(
|
|||
CapacityData->BytesPerBlock = Response->BlockLength;
|
||||
}
|
||||
|
||||
//
|
||||
// store result in device extension
|
||||
//
|
||||
PDODeviceExtension->LastLogicBlockAddress = NTOHL(Response->LastLogicalBlockAddress);
|
||||
PDODeviceExtension->BlockLength = NTOHL(Response->BlockLength);
|
||||
|
||||
//
|
||||
// send csw
|
||||
//
|
||||
|
@ -672,3 +678,138 @@ USBSTOR_SendModeSenseCmd(
|
|||
return Status;
|
||||
}
|
||||
|
||||
NTSTATUS
|
||||
USBSTOR_SendReadCmd(
|
||||
IN PDEVICE_OBJECT DeviceObject,
|
||||
IN OUT PSCSI_REQUEST_BLOCK Request,
|
||||
OUT PULONG TransferBufferLength)
|
||||
{
|
||||
UFI_READ_CMD Cmd;
|
||||
CSW CSW;
|
||||
NTSTATUS Status;
|
||||
PVOID Response;
|
||||
PPDO_DEVICE_EXTENSION PDODeviceExtension;
|
||||
PCBW OutControl;
|
||||
PCDB pCDB;
|
||||
ULONG BlockCount;
|
||||
|
||||
//
|
||||
// get SCSI command data block
|
||||
//
|
||||
pCDB = (PCDB)Request->Cdb;
|
||||
|
||||
//
|
||||
// get PDO device extension
|
||||
//
|
||||
PDODeviceExtension = (PPDO_DEVICE_EXTENSION)DeviceObject->DeviceExtension;
|
||||
|
||||
//
|
||||
// allocate read buffer response from non paged pool
|
||||
//
|
||||
Response = (PUFI_CAPACITY_RESPONSE)AllocateItem(NonPagedPool, Request->DataTransferLength);
|
||||
if (!Response)
|
||||
{
|
||||
//
|
||||
// no memory
|
||||
//
|
||||
return STATUS_INSUFFICIENT_RESOURCES;
|
||||
}
|
||||
|
||||
//
|
||||
// FIXME: support more logical blocks
|
||||
//
|
||||
ASSERT(Request->DataTransferLength == PDODeviceExtension->BlockLength);
|
||||
|
||||
//
|
||||
// block count
|
||||
//
|
||||
BlockCount = Request->DataTransferLength / PDODeviceExtension->BlockLength;
|
||||
|
||||
//
|
||||
// initialize read sense cmd
|
||||
//
|
||||
RtlZeroMemory(&Cmd, sizeof(UFI_READ_CMD));
|
||||
Cmd.Code = SCSIOP_READ;
|
||||
Cmd.LUN = (PDODeviceExtension->LUN & MAX_LUN);
|
||||
Cmd.ContiguousLogicBlocks = _byteswap_ushort(BlockCount);
|
||||
|
||||
RtlCopyMemory(&Cmd.LogicalBlockAddress, pCDB->READ12.LogicalBlock, sizeof(UCHAR) * 4);
|
||||
|
||||
DPRINT1("BlockAddress %lu BlockCount %lu BlockLength %lu\n", NTOHL(Cmd.LogicalBlockAddress), BlockCount, PDODeviceExtension->BlockLength);
|
||||
|
||||
//
|
||||
// now send read cmd
|
||||
//
|
||||
Status = USBSTOR_SendCBW(DeviceObject, UFI_READ_CMD_LEN, (PUCHAR)&Cmd, Request->DataTransferLength, &OutControl);
|
||||
if (!NT_SUCCESS(Status))
|
||||
{
|
||||
//
|
||||
// failed to send CBW
|
||||
//
|
||||
DPRINT1("USBSTOR_SendReadCmd> USBSTOR_SendCBW failed with %x\n", Status);
|
||||
FreeItem(Response);
|
||||
ASSERT(FALSE);
|
||||
return Status;
|
||||
}
|
||||
|
||||
//
|
||||
// now read the logical block
|
||||
//
|
||||
Status = USBSTOR_SendData(DeviceObject, Request->DataTransferLength, Response);
|
||||
if (!NT_SUCCESS(Status))
|
||||
{
|
||||
//
|
||||
// failed to read logical block
|
||||
//
|
||||
DPRINT1("USBSTOR_SendReadCmd> USBSTOR_SendData failed with %x\n", Status);
|
||||
FreeItem(Response);
|
||||
ASSERT(FALSE);
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
||||
DbgBreakPoint();
|
||||
|
||||
//
|
||||
// send csw
|
||||
//
|
||||
Status = USBSTOR_SendCSW(DeviceObject, OutControl, 512, &CSW);
|
||||
|
||||
DPRINT1("------------------------\n");
|
||||
DPRINT1("CSW %p\n", &CSW);
|
||||
DPRINT1("Signature %x\n", CSW.Signature);
|
||||
DPRINT1("Tag %x\n", CSW.Tag);
|
||||
DPRINT1("DataResidue %x\n", CSW.DataResidue);
|
||||
DPRINT1("Status %x\n", CSW.Status);
|
||||
|
||||
//
|
||||
// FIXME: handle error
|
||||
//
|
||||
ASSERT(CSW.Status == 0);
|
||||
ASSERT(CSW.DataResidue == 0);
|
||||
|
||||
//
|
||||
// calculate transfer length
|
||||
//
|
||||
*TransferBufferLength = Request->DataTransferLength - CSW.DataResidue;
|
||||
|
||||
//
|
||||
// copy buffer
|
||||
//
|
||||
RtlCopyMemory(Request->DataBuffer, Response, *TransferBufferLength);
|
||||
|
||||
//
|
||||
// free item
|
||||
//
|
||||
FreeItem(OutControl);
|
||||
|
||||
//
|
||||
// free response
|
||||
//
|
||||
FreeItem(Response);
|
||||
|
||||
//
|
||||
// done
|
||||
//
|
||||
return Status;
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue