USB应用层开发
+ -

Windows下USB驱动同步URB转IRP请求函数代码

2021-08-30 438 0

URB和IRP类似,只不过一个应用于通用的Windows驱动,一个专职于USB。
USB的URB的负载是IRP,其通过负载到IRP时,然后使用通用的Windows IRP请求发向下层目标USB设备。
USB与IRP的关联是通过IRP的IO_STACK_LOCATION的 IoStack->Parameters.Others.Argument1字段建立联系的。
常见的代码如下:

 IoStack = IoGetNextIrpStackLocation(Irp);
 ....
 IoStack->Parameters.Others.Argument1 = (PVOID)UrbRequest;

这里我们对这层应用进行封装,形成一个私有公共函数,适用于Windows内核下USB设备驱动的开发。
SyncUrbRequest函数使用同步的方式调用,如果IRP被下层调备PENDING,则通过等待event事件来等待。

NTSTATUS
SyncUrbRequest(
    IN PDEVICE_OBJECT DeviceObject,
    OUT PURB UrbRequest)
{
    PIRP Irp;
    PIO_STACK_LOCATION IoStack;
    KEVENT Event;
    NTSTATUS Status;

    /* Allocate irp */
    Irp = IoAllocateIrp(DeviceObject->StackSize, FALSE);
    if (!Irp)
    {
        /* No memory */
        return STATUS_INSUFFICIENT_RESOURCES;
    }

    /* Initialize event */
    KeInitializeEvent(&Event, NotificationEvent, FALSE);

    /* Get next stack location */
    IoStack = IoGetNextIrpStackLocation(Irp);

    /* Initialize stack location */
    IoStack->MajorFunction = IRP_MJ_INTERNAL_DEVICE_CONTROL;
    IoStack->Parameters.DeviceIoControl.IoControlCode = IOCTL_INTERNAL_USB_SUBMIT_URB;
    IoStack->Parameters.Others.Argument1 = (PVOID)UrbRequest;
    IoStack->Parameters.DeviceIoControl.InputBufferLength = UrbRequest->UrbHeader.Length;
    Irp->IoStatus.Status = STATUS_SUCCESS;

    /* Setup completion routine */
    IoSetCompletionRoutine(Irp,
        IrpCompletionRoutine,
        &Event,
        TRUE,
        TRUE,
        TRUE);

    /* Call driver */
    Status = IoCallDriver(DeviceObject, Irp);

    /* Check if request is pending */
    if (Status == STATUS_PENDING)
    {
        /* Wait for completion */
        KeWaitForSingleObject(&Event, Executive, KernelMode, FALSE, NULL);

        /* Update status */
        Status = Irp->IoStatus.Status;
    }

    /* Free irp */
    IoFreeIrp(Irp);

    /* Done */
    return Status;
}

同步等待的event是在IRP的完成函数中激活,代码比较简单。

NTSTATUS
IrpCompletionRoutine(
    IN PDEVICE_OBJECT DeviceObject,
    IN PIRP           Irp,
    IN PVOID          Context
)
{
    UNREFERENCED_PARAMETER(Irp);
    UNREFERENCED_PARAMETER(DeviceObject);

    PKEVENT event = (PKEVENT)Context;
    if (event != NULL)
    {
        KeSetEvent(event, IO_NO_INCREMENT, FALSE);
    }

    return STATUS_MORE_PROCESSING_REQUIRED;
}

测试代码

在做USB驱动开发的时候,在IRP_MN_START_DEVICE中启动设备时,是需要将该IRP下发给底层的PDO。
如IRP_MN_START_DEVICE对应的回调函数:FdoStartDevice

NTSTATUS
FdoStartDevice(
        PDEVICE_OBJECT DeviceObject,
        PIRP Irp)
{
    NTSTATUS status;
    PIO_STACK_LOCATION IoStack ;
    PFDO_DEVICE_EXTENSION FDODeviceExtension;

    status = STATUS_SUCCESS;
    IoStack = IoGetCurrentIrpStackLocation(Irp);
    FDODeviceExtension = (PFDO_DEVICE_EXTENSION)DeviceObject->DeviceExtension;

    do
    {
        status = SyncForwardIrp(FDODeviceExtension->NextDeviceObject, Irp);
        if (!NT_SUCCESS(status))
        {
            DPrint1(("SyncForwardIrp err:[%08x]\n", status));
            break;
        }
        ..
    }while(0);

    ...

}
HID人机交互QQ群:564808376    UAC音频QQ群:218581009    UVC相机QQ群:331552032    BOT&UASP大容量存储QQ群:258159197    STC-USB单片机QQ群:315457461    USB技术交流QQ群2:580684376    USB技术交流QQ群:952873936   

0 篇笔记 写笔记

UVC 等时传输中的URB_ISOCH_TRANSFER
通过UVC规范可知,视频图像数据的读取可使用两种端点传输方式,分别为:BULK 块/批量传输方式ISO 等时/同步传输方式在Windows内核中,USB数据的读取是通过URB来进行传输的,其结构体是一个大大的共用体,根据数据传输的方式对应其不同的结构体,其内容如下:typedef _Struct_s......
IRP_MN_QUERY_CAPABILITIES和IRP_MN_QUERY_INTERFACE在USB总线驱动中的作用
在USB驱动总线开发中,IRP_MN_QUERY_BUS_INFORMATION和IRP_MN_QUERY_INTERFACE还挺重要的。对于HID设备,这两个IRP其实只要支持IRP_MN_QUERY_CAPABILITIES就行,而且这个CAPABILITIES不要额外的信息。但对于像UVC,......
USB总线FDO调用 IoInvalidateDeviceRelations通知PNP有新的设备后子设备收到的IRP
在USB FDO总线驱动中,创建了子设备PDO后,调用通知PNP管理器设备树发生了变化。这时系统会重新获取子设备关系树,然后对子设备进行信息收集,并启用。具体的过程如下:->FDO:IRP_MN_QUERY_DEVICE_RELATIONS PDO:IRP_MN_QUERY_ID......
Windows下USB驱动同步URBIRP请求函数代码
URBIRP类似,只不过一个应用于通用的Windows驱动,一个专职于USB。USB的URB的负载是IRP,其通过负载到IRP时,然后使用通用的Windows IRP请求发向下层目标USB设备。USB与IRP的关联是通过IRP的IO_STACK_LOCATION的 IoStack->Para......
Windows下USB驱动异步URBIRP请求函数代码
URB有同步请求,也有异步请求。这里微软官方提供了一个异步请求URB的代码示例// The SubmitUrbASync routine submits an URB asynchronously.//// Parameters://// Parameters:// Devic......
打印IRP_MJ_PNP所有子功能设备
PCHARPnPMinorFunctionString( UCHAR MinorFunction){ static char str[256]; switch (MinorFunction) { case IRP_MN_START_DEVICE: ......
Windows下USB驱动同步URBIRP请求函数代码-改进版
URB的同步调用一般使用:Windows下USB驱动同步URBIRP请求函数代码 http://www.usbzh.com/article/detail-547.html但是,在某些特定的情况下,有时会因为下底设备并没有完成而挂死。这里提供一种超时取消IRP的方法,同时考虑到了线和切换的情况。这里......
Windows下虚拟USB设备数据的读写请求调试笔记
到现在为止,本人已经在Windows下确切来说是Windows10 x64下开发了以下USB虚拟USB设备:USB虚拟UVC摄像头设备USB虚拟UAC麦克风设备USB虚拟HID键盘设备USB虚拟HID鼠标设备USB虚拟HID键盘鼠标复合设备USB虚拟HID单点触摸屏设备USB虚拟HID多点触摸屏......
手动分析使用BUSHOUND抓取同步传输的URB
BUSHOUND大家太熟了,使用它来进行数据抓包那不太太方便。但在BUSHOUND的抓取配置项中,有一个叫了URB的东西,我相信大家都没有选中过,因为一般来说,对WINDOWS USB驱动开发人员来说都不一定有用,更何况大家也只是用来抓取一下几个数据的输入输出,更没有必要进行USB的分析了。本人今天......
使用BUSHOUND手动分析USB控制传输的URB
USB的控制传输是最基本的传输类型,控制传输适用于设备的枚举和设备的状态控制。我里我们使用BUSHOUND来抓取USB控制传输的URB。同样的,我们使用的操作系统是Windows10 x64,和同步传输的URB抓包一样,我们先抓取数据,然后再分析数据结构。这里我插入电脑的U盘的枚举以获取设备描述符为......
使用BUSHOUND手动分析USB批量传输的URB
使用BUSHOUND抓取U盘的批量传输的URB数据,我们对其其进行数据分析:13 IN 55 53 42 53 40 0b ac 57 00 00 00 00 00 URB80 00 09 00 00 00 00 00 d8 f2 75 a0 77 7f 00 00 ......
USB摄像头同步传输的完成后URB参数
这几天不是闲来无事,一个工作的任务就是对手中一个USB摄像头进行驱动开发,并进行视频格式的转换。通过分析该USB摄像头可知,其采用的是同步传输,所以本人在开发的驱动中,使用同步的URB进行下发请求数据,然后在完成例程中获取数据。同步传输的URB本人在 手动分析使用BUSHOUND抓取同步传输的URB......
UAC麦克风同步传输的URB分析
之前写过同步传输的UVC摄像头的URB,文章名称为:手动分析使用BUSHOUND抓取同步传输的URB 。今天恰好手中有一个UVC麦克风,所以也拿来分析。也许和之前的文章有所重复,但是因为侧重点的不同,也许会有意想不到的小收获取。言归正转,我们知道,在UAC音频规范中,数据的传输不像UVC摄像头那样,......
USB摄像头同步传输H264遇到的花屏问题
以往拿到的摄像头数据传输都是批量传输,本人也只在音频驱动的开发中使用了同步传输。这次突然拿到一个摄像头,数据采用的是同步传输,本以为很简单的代码移植,却没有想到还是遇到了一个坑,自己花费了大力气来排查,在这期间自己也看了大量的资料,今天在这里做一个简单的总结。以前的摄像头拿到的USB摄像头如批量传......
USB2.0 D+和D-的差分信号J、K状态和Chirp J和Chirp K状态
J、K信号状态表示D+和D-两根差分信号数据线的数据发送状态。J、K状态在全速或者低速的模式下,当接收端收检测到D+信号线的电压比D-信号线的电压高出200mV时,表示差分信号“1”,当当接收端收检测到D-信号线的电压比D+信号线的电压高出200mV时,表示差分信号“0”.在高速的模式下,当接收......
关注公众号
取消
感谢您的支持,我会继续努力的!
扫码支持
扫码打赏,你说多少就多少

打开支付宝扫一扫,即可进行扫码打赏哦

您的支持,是我们前进的动力!