Hello guys!
I'm writting Usb LowFilters driver and in AddDevice routine i want send directly to usb mass storage device some scsi command :
(before this I configurate usb mass storage device and get pipes handles - pipeIn/pipeOut)
May be I don't undestan transaction mechanism?
This code for TEST UNIT READY :
And when I try to read some info from device :
Please guys help me!
I'm writting Usb LowFilters driver and in AddDevice routine i want send directly to usb mass storage device some scsi command :
(before this I configurate usb mass storage device and get pipes handles - pipeIn/pipeOut)
Code: Select all
...
typedef struct _CBW //command block wrapper
{
unsigned int Signature;
unsigned int Tag;
unsigned int dataTransferLength;
unsigned char Flags;
unsigned char Lun;
unsigned char cbdLength; //scsi command block length
unsigned char cbd[16]; //scsi command block data
} CBW, * PCBW;
...
typedef struct _CSW //command status wrapper
{
unsigned int Signature;
unsigned int Tag;
unsigned int dataResidue;
unsigned char Status;
} CSW, * PCSW;
Code: Select all
And it work fine ((statusBlock->Status == 0 and buffer include inqury info)! But if I want to get TEST UNIT READY command or REPORT LUNS command it failed...URB urb;
NTSTATUS ntStatus = STATUS_SUCCESS;
PCBW commandBlock;
PCSW statusBlock;
char* buffer;
int dataLen = 36; //INQURY data len
commandBlock = (PCBW *)ExAllocatePool(PagedPool,sizeof(CBW ));
statusBlock = (PCSW *)ExAllocatePool(PagedPool,sizeof(CSW));
buffer = (char*) ExAllocatePool(PagedPool,sizeof(char)*dataLen );
commandBlock->Signature = 0x43425355; // command block signature 'USBC'
commandBlock->Flags = 0x80;//80->data in
commandBlock->Lun = 0; //default Logical Unit Number
RtlZeroMemory(commandBlock->cbd,16);
//[b]now i try get INQURY iinfo from device[/b]
commandBlock->Tag = - TAG_INQUIRY; // TAG_INQUIRY = 18
commandBlock->dataTransferLength = 36; //INQUIRY_REPLY_LENGTH
commandBlock->Flags = 0x80; //inquiry data will flow In
commandBlock->cbdLength = 6; //inquiry command length
[i]//scsi command block[/i]
commandBlock->cbd[0] = 0x12; //inquiry operation code
commandBlock->cbd[1] = 0; //lun/reserved
commandBlock->cbd[2] = 0; //page code
commandBlock->cbd[3] = 0; //reserved
commandBlock->cbd[4] = 36; //inquiry reply length
commandBlock->cbd[5] = 0; //reserved/flag/link/
//[b]start mass storage transaction - CBW-DATA-CSW[/b]
[i]//scsi command block[/i]
UsbBuildInterruptOrBulkTransferRequest(&urb,
sizeof(struct _URB_BULK_OR_INTERRUPT_TRANSFER),
pipeOut,
block,
NULL,
31,
USBD_TRANSFER_DIRECTION_OUT,
NULL);
ntStatus = SendAndWaitUrb(deviceObject, &urb,TRUE);
[i]//data[/i]
if (NT_SUCCESS(ntStatus))
{
UsbBuildInterruptOrBulkTransferRequest(&urb,
sizeof(struct _URB_BULK_OR_INTERRUPT_TRANSFER),
pipeIn,
buffer,
NULL,
dataLen,
USBD_TRANSFER_DIRECTION_IN | USBD_SHORT_TRANSFER_OK,
NULL);
ntStatus = SendAndWaitUrb(deviceObject, &urb,TRUE);
}
[i]//status command block[/i]
statusBlock->Signature = 0x53425355 // 'USBS'
statusBlock->Tag = -TAG_CSW; // TAG_CSW = 37
statusBlock->dataResidue = 0;//residue;
statusBlock->Status = 0;
if (NT_SUCCESS(ntStatus))
{
UsbBuildInterruptOrBulkTransferRequest(&urb,
sizeof(_URB_BULK_OR_INTERRUPT_TRANSFER),
pipeIn,
packet,
NULL,
13,
USBD_TRANSFER_DIRECTION_IN | USBD_SHORT_TRANSFER_OK,
NULL);
ntStatus = SendAndWaitUrb(deviceObject, &urb,TRUE);
}
ASSERT(statusBlock->Status == 0); [b]//FINE!Info recived![/b]
.....
May be I don't undestan transaction mechanism?
This code for TEST UNIT READY :
Code: Select all
Usb mass storage device 'A' hase 1 LUN - 0,but TEST UNIT READY return 1 for this,usb mass storage device 'B' hase 2 LUNs,but TEST UNIT READY 1 for each lun...URB urb;
NTSTATUS ntStatus = STATUS_SUCCESS;
PCBW commandBlock;
PCSW statusBlock;
char* buffer;
commandBlock = (PCBW *)ExAllocatePool(PagedPool,sizeof(CBW ));
statusBlock = (PCSW *)ExAllocatePool(PagedPool,sizeof(CSW));
commandBlock->Signature = 0x43425355; // command block signature 'USBC'
commandBlock->Flags = 0x80;//80->data in
commandBlock->Lun = 0; //Logical Unit Number
RtlZeroMemory(commandBlock->cbd,16);
//[b]now i try send TEST UNIT READY[/b]
commandBlock->Tag = - TAG_UNIT_READY; // TAG_INQUIRY = 25
commandBlock->dataTransferLength = 0; //INQUIRY_REPLY_LENGTH
commandBlock->Flags = 0x80; //inquiry data will flow In
commandBlock->cbdLength = 6; //test unit ready command length
[i]//scsi command block[/i]
commandBlock->cbd[0] = 0x0; //inquiry operation code
commandBlock->cbd[1] = 0; //lun/reserved
commandBlock->cbd[2] = 0; //page code
commandBlock->cbd[3] = 0; //reserved
commandBlock->cbd[4] = 0; //inquiry reply length
commandBlock->cbd[5] = 0; //reserved/flag/link/
//[b]start mass storage transaction - CBW-DATA-CSW[/b]
[i]//scsi command block[/i]
UsbBuildInterruptOrBulkTransferRequest(&urb,
sizeof(struct _URB_BULK_OR_INTERRUPT_TRANSFER),
pipeOut,
block,
NULL,
31,
USBD_TRANSFER_DIRECTION_OUT,
NULL);
ntStatus = SendAndWaitUrb(deviceObject, &urb,TRUE);
[i]//status command block[/i]
statusBlock->Signature = 0x53425355 // 'USBS'
statusBlock->Tag = -TAG_CSW; // TAG_CSW = 37
statusBlock->dataResidue = 0;//residue;
statusBlock->Status = 0;
if (NT_SUCCESS(ntStatus))
{
UsbBuildInterruptOrBulkTransferRequest(&urb,
sizeof(_URB_BULK_OR_INTERRUPT_TRANSFER),
pipeIn,
packet,
NULL,
13,
USBD_TRANSFER_DIRECTION_IN | USBD_SHORT_TRANSFER_OK,
NULL);
ntStatus = SendAndWaitUrb(deviceObject, &urb,TRUE);
}
ASSERT(statusBlock->Status == 0); // [b]status always return 1 for LUN =0 and other LUN (0...256), but sometimes return 0 for LUN = 0 and etc. - it's WRONG [/b]
...
And when I try to read some info from device :
Code: Select all
In this case (read 6 command) after send command block I'm recived in buffer 'USBS' signature,but WHY?URB urb;
NTSTATUS ntStatus = STATUS_SUCCESS;
PCBW commandBlock;
PCSW statusBlock;
char* buffer;
int dataLen = 128;
commandBlock = (PCBW *)ExAllocatePool(PagedPool,sizeof(CBW ));
statusBlock = (PCSW *)ExAllocatePool(PagedPool,sizeof(CSW));
buffer = (char*) ExAllocatePool(PagedPool,sizeof(char)*dataLen );
commandBlock->Signature = 0x43425355; // command block signature 'USBC'
commandBlock->Flags = 0x80;//80->data in
commandBlock->Lun = 0; //Logical Unit Number
RtlZeroMemory(commandBlock->cbd,16);
//[b]now i try get INQURY iinfo from device[/b]
commandBlock->Tag = - TAG_READ_6; // TAG_INQUIRY = 14
commandBlock->dataTransferLength = dataLen ; //READ LEN
commandBlock->Flags = 0x80; //read data will flow In
commandBlock->cbdLength = 6; //read command length
[i]//scsi command block[/i]
commandBlock->cbd[0] = 0x28; //read 6 operation code
commandBlock->cbd[1] = 0; //lun/reserved
commandBlock->cbd[2] = 0; //page code
commandBlock->cbd[3] = 0; //try read first sector
commandBlock->cbd[4] = dataLen; //readreply length
commandBlock->cbd[5] = 0; //reserved/flag/link/
//[b]start mass storage transaction - CBW-DATA-CSW[/b]
[i]//scsi command block[/i]
UsbBuildInterruptOrBulkTransferRequest(&urb,
sizeof(struct _URB_BULK_OR_INTERRUPT_TRANSFER),
pipeOut,
block,
NULL,
31,
USBD_TRANSFER_DIRECTION_OUT,
NULL);
ntStatus = SendAndWaitUrb(deviceObject, &urb,TRUE);
[i]//read data[/i]
if (NT_SUCCESS(ntStatus))
{
UsbBuildInterruptOrBulkTransferRequest(&urb,
sizeof(struct _URB_BULK_OR_INTERRUPT_TRANSFER),
pipeIn,
buffer,
NULL,
dataLen,
USBD_TRANSFER_DIRECTION_IN | USBD_SHORT_TRANSFER_OK,
NULL);
ntStatus = SendAndWaitUrb(deviceObject, &urb,TRUE);
[b][i]//now buffer contain 'USBS' signature in first bytes![/i][/b]
}
[i]//status command block[/i]
statusBlock->Signature = 0x53425355 // 'USBS'
statusBlock->Tag = -TAG_CSW; // TAG_CSW = 37
statusBlock->dataResidue = 0;//residue;
statusBlock->Status = 0;
if (NT_SUCCESS(ntStatus))
{
UsbBuildInterruptOrBulkTransferRequest(&urb,
sizeof(_URB_BULK_OR_INTERRUPT_TRANSFER),
pipeIn,
packet,
NULL,
13,
USBD_TRANSFER_DIRECTION_IN | USBD_SHORT_TRANSFER_OK,
NULL);
ntStatus = SendAndWaitUrb(deviceObject, &urb,TRUE); // ***
}
[b][i]//and now i'm don't return from SendAndWaitUrb(***)....deadlock [/i][/b]
.....
Please guys help me!