Windows主机端与自定义USB

如题,因为要跟usb设备通讯,怎么在前后相继里面获得只怕安装设备的告知描述符在找到设备createFile后,writeFile重临87错误,英特网查找到相应是本人未曾在发送的数码第一人带上报告ID,但是作者怎么获得这么些报告ID呢??

Windows主机端与自定义USB HID设备通信精解

 

说明:

–          以下结论都以依赖 Windows XP
系统所搜查捕获的,不保险在其余系统的适用性。

–          在这里切磋的是 HID 自定义设备,对刘阳规配备,譬喻 USB
鼠标和键盘,由于操作系统对其独自占领,多数操作未必能正确试行。

 

1 .   所使用的出色 Windows API

CreateFile

ReadFile

WriteFile

以下函数是 DDK 的内容:

HidD_SetFeature

HidD_GetFeature

HidD_SetOutputReport

HidD_GetInputReport

个中, CreateFile 用于张开设备; ReadFile 、 HidD_GetFeature 、
HidD_GetInputReport 用于器具到主机方向的数额通信; WriteFile 、
HidD_SetFeature 、 HidD_SetOutputReport
用于主机到道具方向的数量通讯。鉴于实际运用,后文首要斟酌 CreateFile ,
WriteFile , ReadFile , HidD_SetFeature
多个函数,明白了这两个函数,此外的能够类推之。

 

2 .   几个不乏先例错误

       当使用上述 API 时,即便操作战败,调用 GetLastError(卡塔尔国会获得以下平淡无奇错误:

       6 :          句柄无效

       23 :        数据失实(循环冗余码检查)

       87 :        参数错误

       1784 :     顾客提供的 buffer 无效

       后文将会详细表明这么些不当情形。

 

3.         主机端设备枚举程序流程

 

 图片 1

4.         函数使用验证

CreateFile(devDetail->DevicePath,                                        
// 设备路径

               GENERIC_READ | GENERIC_W奥迪Q3ITE,                    //
访谈方式

               FILE_SHARE_READ | FILE_SHARE_WPAJEROITE,         //
分享方式

               NULL,

               OPEN_EXISTING,                                          
// 文件子虚乌有时,重回战败

               FILE_FLAG_OVEMuranoL应用软件ED,                                
// 以重叠(异步)格局张开

               NULL);

 

在此边, CreateFile 用于展开 HID 设备,其中设备路线通过函数
SetupDiGetInterfaceDeviceDetail 拿到。 CreateFile 有以下几点须要在乎:

 

–     访问形式:
假使是系统独自占领设备,比如鼠标、键盘等等,应将此参数设置为 0
,不然继续函数操作将战败(例如 HidD_GetAttributes
);相当于说,无法对独自占领设备实行除了查询以外的别的操作,所以能够利用的函数也是超级轻易的,下文的有的函数并不一定适合这几个设备。在那顺便列出
MSDN 上关于此参数的表达:

If this parameter is zero, the application can query file and device
attributes without accessing the device. This is useful if an
application wants to determine the size of a floppy disk drive and the
formats it supports without requiring a floppy in the drive. It can also
be used to test for the file’s or directory’s existence without opening
it for read or write access 。

–         
重叠(异步)情势:此参数并不会在那间表现出显然的意义,它至关心珍视借使对持续的
WriteFile , ReadFile 有影响。假若这里安装为重叠(异步)形式,那么在应用
WriteFile , ReadFile 时也理应运用重叠(异步)方式,反之亦然。那第大器晚成必要WriteFile , ReadFile 的尾声三个参数无法为空( NULL )。不然,便会回来
87 (参数错误)错误号。当然, 87
号错误并不代表正是此参数不科学,更加多的音信就要实际陈述那八个函数时提议。此参数为
0 时,代表一齐情势,即 WriteFile , ReadFile
操作会在数量管理到位今后才回去,不然梗塞在函数内部。

 

ReadFile(hDev,                                 // 设备句柄,即
CreateFile 的重临值

              recvBuffer,                          // 用于接受数据的
buffer

              IN_REPORT_LEN,              // 要读取数据的长短

              &recvBytes,                         //
实际摄取的多寡的字节数

              &ol卡塔尔(英语:State of Qatar);                                  // 异步格局

 

在此边, ReadFile 用于读取 HID 设备经过暂停 IN 传输发来的输入报告
。有以下几点要留意:

 

1 、 ReadFile 的调用不会挑起设备的别的反应,即 HID 设备与主机之间的中断
IN 传输不与 ReadFile
打交道。实际上主机缘在最大间隔时间(由器材的端点描述符来钦赐)内轮询设备,发出中断
IN 传输的号召。“读取”即表示从有个别 buffer 里面取回数据,实际上这个buffer 就是 HID 设备驱动中的 buffer 。这一个 buffer 的轻重能够由此HidD_SetNumInputBuffers 来改造。在 XP 上缺省值是 32 (个告知)。

 

2
、读取的数码对象是输入报告,也即透过暂停输入管道传入的数额。所以,若是设备不支持中断
IN 传输,那么是无力回Smart用此函数来收获预期结果的。实际上这种处境不容许在
HID 中现身,因为合同指明了足足要有四个抛锚 IN 端点。

 

3 、 IN_REPORT_LEN 代表要读取的数量的长短(实际的数目正文 + 一个 byte
的告诉 ID
),这里是一个常数,首假如因为设备固件的音信笔者是全然清楚的,当然知道要读取多少多少(也等于告诉的尺寸);可是也得以由此此外的函数(
HidD_GetPreparsedData
)来事情发生在此以前获得报告的长度,这里不做详细座谈。因为很难想象在不打听固件消息的情景下来做自定义设备的
HID 通讯,在实质上运用中貌似的话就是固件与 PC
程序相称着来开垦。此参数倘诺设置过大,不会有实质性的荒谬,在 recvBytes
参数中会输出实际读到的尺寸;要是设置过小,即小于报告的长短,会回去 1784
号错误(客户提供的 buffer 无效)。

 

4 、关于异步格局。后边已经提过,此参数的设置必需与 CreateFile
时的设置相呼应,不然会再次来到 87
号错误(参数错误)。假设不须要异步方式,此参数需置为 NULL
。在这种景况下, ReadFile
会一贯等待直到数据读取成功,所以会拥塞住程序的脚下进度。

 

       WriteFile(hDev,                                 // 设备句柄,即
CreateFile 的再次回到值

                     reportBuf,                           //
存有待发送数据的 buffer

                     OUT_REPORT_LEN,           // 待发送数据的尺寸

                     &sendBytes,                        //
实际吸取的数据的字节数

                     &ol卡塔尔(قطر‎;                                  // 异步形式

 

       在此, WriteFile 用于传输二个输出报告 给 HID
设备。有以下几点要小心:

 

1、  与 ReadFile 不一样, WriteFile
函数被调用后,纵然也是由此驱动程序,然而最后会反映到设备中。也正是说,调用
WriteFile 后,设备会收取到输出报告的央求。假诺设备使用了中断 OUT
传输,则 WriteFile 会通过暂停 OUT 管道来开展传输;不然会动用 SetReport
央求通过操纵管道来传输。

 

2、  OUT_REPORT_LEN 代表要写入的多长(实际的多少正文 + 叁个 byte
的告诉 ID
)。要是超过实际报告的尺寸,则接收实际报告长度;借使低于实际报告长度,会回来
1784 号错误(客户提供的 buffer 无效)。

 

3、  reportBuf [0] 必须存有待发送报告的 ID ,并且此报告 ID
提醒的必须是出口报告,不然会回到 87
号错误(参数错误)。这种情状只怕轻便被技术员忽略,结果不知错误号所反映的是怎样,网络也时不经常有雷同难题的帖子。顺便建议,输入报告、输入报告、特征报告那几个告诉项目,是体今后HID 设备的告诉描述符中。后文将做比方商讨。

 

4、  关于异步情势。后边已经提过,此参数的装置必须与 CreateFile
时的设置相对应,不然会回去 87
号错误(参数错误)。假如无需异步情势,此参数需置为 NULL
。在这里种情况下, WriteFile
会一向等候直到数据读取成功,所以会堵塞住程序的近来过程。

 

HidD_SetFeature(hDev,                                    //
设备句柄,即 CreateFile 的再次来到值

                     reportBuf,                                   //
存有待发送数据的 buffer

                     FEATURE_REPORT_LEN);        //buffer 的长度

发表评论

电子邮件地址不会被公开。 必填项已用*标注