📄 cioctl.c
字号:
PUSB_CONFIGURATION_DESCRIPTOR configurationDescriptor = NULL;
PDEVICE_EXTENSION pdx = fdo->DeviceExtension;
PURB urb = NULL;
USHORT urbSize;
ULONG numberOfPipes;
ULONG i,j;
NTSTATUS ntStatus;
//
// Get the configuration Descriptor
//
configurationDescriptor = GetConfigDescriptor(fdo);
if (!configurationDescriptor)
{
Ezusb_KdPrint (("Get Configuration Descriptor Failed\n"));
ntStatus = STATUS_UNSUCCESSFUL;
goto CleanupSetInterface;
}
//
// Get the interface Descriptor for the interface we want
//
interfaceDescriptor = USBD_ParseConfigurationDescriptorEx(
configurationDescriptor,
configurationDescriptor,
InterfaceNumber,
AlternateSetting,
-1,
-1,
-1);
if (!interfaceDescriptor)
{
ntStatus = STATUS_UNSUCCESSFUL;
goto CleanupSetInterface;
}
numberOfPipes = interfaceDescriptor->bNumEndpoints;
Ezusb_KdPrint (("numberOfPipes = %d\n", numberOfPipes));
urbSize = 12;
//urbSize = GET_SELECT_INTERFACE_REQUEST_SIZE(numberOfPipes);
// Ezusb_KdPrint (("urbSize = %d\n", urbSize));
//urb = ExAllocatePool(NonPagedPool,urbSize);
if (!urb)
{
ntStatus = STATUS_NO_MEMORY;
goto CleanupSetInterface;
}
// RtlZeroMemory(urb,urbSize);
UsbBuildSelectInterfaceRequest(urb,
urbSize,
pdx->ConfigurationHandle,
InterfaceNumber,
AlternateSetting);
interfaceInformation = &(urb->UrbSelectInterface.Interface);
//interfaceInformation->Length = GET_USBD_INTERFACE_SIZE(numberOfPipes);
for (i = 0 ;i < numberOfPipes ;i++ )
{
interfaceInformation->Pipes[i].MaximumTransferSize = (64*1024) -1;
}
ntStatus = Ezusb_CallUSBD(fdo, urb);
//
// If that succeeded, then update the Interface structure
// in the device extension.
//
if (NT_SUCCESS(ntStatus))
{
for (j=0; j<interfaceInformation->NumberOfPipes; j++)
{
PUSBD_PIPE_INFORMATION pipeInformation;
pipeInformation = &interfaceInformation->Pipes[j];
Ezusb_KdPrint (("---------\n"));
Ezusb_KdPrint (("PipeType 0x%x\n", pipeInformation->PipeType));
Ezusb_KdPrint (("EndpointAddress 0x%x\n", pipeInformation->EndpointAddress));
Ezusb_KdPrint (("MaxPacketSize 0x%x\n", pipeInformation->MaximumPacketSize));
Ezusb_KdPrint (("Interval 0x%x\n", pipeInformation->Interval));
Ezusb_KdPrint (("Handle 0x%x\n", pipeInformation->PipeHandle));
Ezusb_KdPrint (("MaximumTransferSize 0x%x\n", pipeInformation->MaximumTransferSize));
}
if (pdx->Interface)
{
ExFreePool(pdx->Interface);
}
pdx->Interface = NULL;
pdx->Interface = ExAllocatePool(NonPagedPool,interfaceInformation->Length);
if (!pdx->Interface)
{
ntStatus = STATUS_NO_MEMORY;
goto CleanupSetInterface;
}
RtlCopyMemory(pdx->Interface, interfaceInformation, interfaceInformation->Length);
}
CleanupSetInterface:
// Clean up and exit this routine
if (urb != NULL)
{
ExFreePool(urb);
}
if (configurationDescriptor != NULL)
{
ExFreePool(configurationDescriptor);
}
return(ntStatus);
}
PUSB_CONFIGURATION_DESCRIPTOR GetConfigDescriptor(
IN PDEVICE_OBJECT fdo
)
/*++
Routine Description:
Arguments:
Return Value:
NT status code
--*/
{
PDEVICE_EXTENSION pdx;
NTSTATUS ntStatus;
PURB urb;
ULONG siz;
PUSB_CONFIGURATION_DESCRIPTOR configurationDescriptor = NULL;
Ezusb_KdPrint (("Ezusb.SYS: enter Ezusb_GetConfigDescriptor\n"));
pdx = fdo->DeviceExtension;
urb = ExAllocatePool(NonPagedPool,
sizeof(struct _URB_CONTROL_DESCRIPTOR_REQUEST));
if (urb) {
siz = sizeof(USB_CONFIGURATION_DESCRIPTOR)+256;
get_config_descriptor_retry2:
configurationDescriptor = ExAllocatePool(NonPagedPool,
siz);
if (configurationDescriptor) {
UsbBuildGetDescriptorRequest(urb,
(USHORT) sizeof (struct _URB_CONTROL_DESCRIPTOR_REQUEST),
USB_CONFIGURATION_DESCRIPTOR_TYPE,
0,
0,
configurationDescriptor,
NULL,
siz,
NULL);
ntStatus = Ezusb_CallUSBD(fdo, urb);
Ezusb_KdPrint (("Ezusb.SYS: Configuration Descriptor = %x, len %x\n",
configurationDescriptor,
urb->UrbControlDescriptorRequest.TransferBufferLength));
} else {
ntStatus = STATUS_INSUFFICIENT_RESOURCES;
}
if (NT_SUCCESS(ntStatus) &&
(urb->UrbControlDescriptorRequest.TransferBufferLength >=
sizeof(USB_CONFIGURATION_DESCRIPTOR)) &&
(configurationDescriptor->wTotalLength >=
sizeof(USB_CONFIGURATION_DESCRIPTOR)))
{
//
// The Get Config Descriptor request did not return an error
// AND at least enough data was transferred to fill a Config
// Descriptor AND the Config Descriptor wLength is at least the
// size of a Config Descriptor
//
if (configurationDescriptor->wTotalLength > siz)
{
//
// The request buffer is not big enough to hold the
// entire set of descriptors. Free the current buffer
// and retry with a buffer which should be big enough.
//
siz = configurationDescriptor->wTotalLength;
ExFreePool(configurationDescriptor);
configurationDescriptor = NULL;
goto get_config_descriptor_retry2;
}
else if (configurationDescriptor->wTotalLength >
urb->UrbControlDescriptorRequest.TransferBufferLength)
{
//
// The request buffer is greater than or equal to the
// Config Descriptor wLength, but less data was transferred
// than wLength. Return NULL to indicate a device error.
//
ExFreePool(configurationDescriptor);
configurationDescriptor = NULL;
}
//
// else everything is OK with the Config Descriptor, return it.
//
}
else
{
//
// The Get Config Descriptor request returned an error OR
// not enough data was transferred to fill a Config Descriptor
// OR the Config Descriptor wLength is less than the size of
// a Config Descriptor. Return NULL to indicate a device error.
//
ExFreePool(configurationDescriptor);
configurationDescriptor = NULL;
}
ExFreePool(urb);
} else {
ntStatus = STATUS_INSUFFICIENT_RESOURCES;
}
Ezusb_KdPrint (("Ezusb.SYS: exit Ezusb_GetConfigDescriptor\n"));
return configurationDescriptor;
}
NTSTATUS c_SetFeature(
IN PDEVICE_OBJECT fdo,
IN PSET_FEATURE_CONTROL setFeatureControl
)
/*
Routine Description:
This routine performs a Set Feature control transfer
Arguments:
fdo - our device object
setFeatureControl - a data structure that contains the arguments for the
set featire command
Return Value:
NTSTATUS
*/
{
NTSTATUS ntStatus = STATUS_SUCCESS;
PURB urb = NULL;
ULONG length = 0;
PDEVICE_EXTENSION pdx = fdo->DeviceExtension;
Ezusb_KdPrint (("Enter Ezusb_SetFeature\n"));
urb = ExAllocatePool(NonPagedPool,
sizeof(struct _URB_CONTROL_FEATURE_REQUEST));
if (urb)
{
RtlZeroMemory(urb,sizeof(struct _URB_CONTROL_FEATURE_REQUEST));
urb->UrbHeader.Length = sizeof(struct _URB_CONTROL_FEATURE_REQUEST);
urb->UrbHeader.Function = URB_FUNCTION_SET_FEATURE_TO_DEVICE;
urb->UrbControlFeatureRequest.FeatureSelector = setFeatureControl->FeatureSelector;
urb->UrbControlFeatureRequest.Index = setFeatureControl->Index;
ntStatus = Ezusb_CallUSBD(fdo, urb);
}
else
{
ntStatus = STATUS_NO_MEMORY;
}
Ezusb_KdPrint (("Leaving Ezusb_SetFeature\n"));
return ntStatus;
}
NTSTATUS
c_ResetParentPort(
IN IN PDEVICE_OBJECT fdo
)
/*++
Routine Description:
Reset the our parent port
Arguments:
Return Value:
STATUS_SUCCESS if successful,
STATUS_UNSUCCESSFUL otherwise
--*/
{
NTSTATUS ntStatus, status = STATUS_SUCCESS;
PIRP irp;
KEVENT event;
IO_STATUS_BLOCK ioStatus;
PIO_STACK_LOCATION nextStack;
PDEVICE_EXTENSION pdx;
Ezusb_KdPrint (("EZUSB.SYS: enter Ezusb_ResetPort\n"));
pdx = fdo->DeviceExtension;
//
// issue a synchronous request
//
KeInitializeEvent(&event, NotificationEvent, FALSE);
irp = IoBuildDeviceIoControlRequest(
IOCTL_INTERNAL_USB_RESET_PORT,
pdx->StackDeviceObject,
// pdx->TopOfStackDeviceObject,
NULL,
0,
NULL,
0,
TRUE, /* INTERNAL */
&event,
&ioStatus);
//
// Call the class driver to perform the operation. If the returned status
// is PENDING, wait for the request to complete.
//
nextStack = IoGetNextIrpStackLocation(irp);
ASSERT(nextStack != NULL);
Ezusb_KdPrint (("EZUSB.SYS: calling USBD enable port api\n"));
ntStatus = IoCallDriver(pdx->StackDeviceObject,
irp);
Ezusb_KdPrint (("EZUSB.SYS: return from IoCallDriver USBD %x\n", ntStatus));
if (ntStatus == STATUS_PENDING) {
Ezusb_KdPrint (("EZUSB.SYS: Wait for single object\n"));
status = KeWaitForSingleObject(
&event,
Suspended,
KernelMode,
FALSE,
NULL);
Ezusb_KdPrint (("EZUSB.SYS: Wait for single object, returned %x\n", status));
} else {
ioStatus.Status = ntStatus;
}
//
// USBD maps the error code for us
//
ntStatus = ioStatus.Status;
Ezusb_KdPrint (("EZUSB.SYS: Ezusb_ResetPort (%x)\n", ntStatus));
return ntStatus;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -