Hi
I have built a bulk usb driver based on BulkUsb. I am developing it
for a bulk communication with my camera device.
I have Implemented that driver for 2014208 bytes size.my driver usually run well,but sometime when ReadWriteCompletion routines call,I find NT_SUCCESS(ntStatus)=FALSE,and it got cancelled status and a error code C0000120.
in this case,the driver return tranfer size is zero.
I have not define and canceling routine yet.
will is it the problem of my driver or may be something from device side? but it run well in linux system. my hardware team saying that the hardware is perfect.
please tell me what should be the solutions
Thanks
stone
NTSTATUS
BulkUsb_ReadWriteCompletion(
IN PDEVICE_OBJECT DeviceObject,
IN PIRP Irp,
IN PVOID Context
)
/*++
Routine Description:
This is the completion routine for reads/writes
If the irp completes with success, we check if we
need to recirculate this irp for another stage of
transfer. In this case return STATUS_MORE_PROCESSING_REQUIRED.
if the irp completes in error, free all memory allocs and
return the status.
Arguments:
DeviceObject - pointer to device object
Irp - I/O request packet
Context - context passed to the completion routine.
Return Value:
NT status value
–*/
{
ULONG stageLength;
NTSTATUS ntStatus;
PIO_STACK_LOCATION nextStack;
PBULKUSB_RW_CONTEXT rwContext;
//
// initialize variables
//
rwContext = (PBULKUSB_RW_CONTEXT) Context;
ntStatus = Irp->IoStatus.Status;
UNREFERENCED_PARAMETER(DeviceObject);
BulkUsb_DbgPrint(3, (“BulkUsb_ReadWriteCompletion - begins\n”));
//
// successfully performed a stageLength of transfer.
// check if we need to recirculate the irp.
//
if(NT_SUCCESS(ntStatus)) { //error NT_SUCCESS(ntStatus)=FALSE
if(rwContext) {
rwContext->Numxfer +=
rwContext->Urb->UrbBulkOrInterruptTransfer.TransferBufferLength;
if(rwContext->Length) {
//
// another stage transfer
//
BulkUsb_DbgPrint(3, (“Another stage transfer…\n”));
if(rwContext->Length > BULKUSB_MAX_TRANSFER_SIZE) {
stageLength = BULKUSB_MAX_TRANSFER_SIZE;
}
else {
stageLength = rwContext->Length;
}
IoBuildPartialMdl(Irp->MdlAddress,
rwContext->Mdl,
(PVOID) rwContext->VirtualAddress,
stageLength);
//
// reinitialize the urb
//
rwContext->Urb->UrbBulkOrInterruptTransfer.TransferBufferLength
= stageLength;
rwContext->VirtualAddress += stageLength;
rwContext->Length -= stageLength;
nextStack = IoGetNextIrpStackLocation(Irp);
nextStack->MajorFunction = IRP_MJ_INTERNAL_DEVICE_CONTROL;
nextStack->Parameters.Others.Argument1 = rwContext->Urb;
nextStack->Parameters.DeviceIoControl.IoControlCode =
IOCTL_INTERNAL_USB_SUBMIT_URB;
IoSetCompletionRoutine(Irp,
BulkUsb_ReadWriteCompletion,
rwContext,
TRUE,
TRUE,
TRUE);
IoCallDriver(rwContext->DeviceExtension->TopOfStackDeviceObject,
Irp);
return STATUS_MORE_PROCESSING_REQUIRED;
}
else {
//
// this is the last transfer
//
Irp->IoStatus.Information = rwContext->Numxfer;
}
}
}
else {
BulkUsb_DbgPrint(1, (“ReadWriteCompletion - failed with status = %X\n”, ntStatus)); //status =C0000120
}
if(rwContext) {
//
// dump rwContext
//
BulkUsb_DbgPrint(3, (“rwContext->Urb = %X\n”,
rwContext->Urb));
BulkUsb_DbgPrint(3, (“rwContext->Mdl = %X\n”,
rwContext->Mdl));
BulkUsb_DbgPrint(3, (“rwContext->Length = %d\n”,
rwContext->Length));
BulkUsb_DbgPrint(3, (“rwContext->Numxfer = %d\n”,
rwContext->Numxfer));
BulkUsb_DbgPrint(3, (“rwContext->VirtualAddress = %X\n”,
rwContext->VirtualAddress));
BulkUsb_DbgPrint(3, (“rwContext->DeviceExtension = %X\n”,
rwContext->DeviceExtension));
BulkUsb_DbgPrint(3, (“BulkUsb_ReadWriteCompletion::”));
BulkUsb_IoDecrement(rwContext->DeviceExtension);
ExFreePool(rwContext->Urb);
IoFreeMdl(rwContext->Mdl);
ExFreePool(rwContext);
}
BulkUsb_DbgPrint(3, (“BulkUsb_ReadWriteCompletion - ends\n”));
return ntStatus;
}