CH376操作键盘问题

初始化完成后,键盘LED也点亮了,获取报告一直获取不了。 下面是获取子程序: u8 get_int_in(u8 tog,u8 endp_int) { UINT8 s,t,j; tog = tog ? 0x80 : 0x00; issue_token(tog,( endp_int << 4 ) | DEF_USB_PID_IN); s = wait_interrupt( ); if(s == USB_INT_SUCCESS) { t = RD_USB_DATA(data_buf); //键盘中断端点数据长度一般为8字节,鼠标为4字节 for(j=0;j!=t;j++) printf("%02x ",(unsigned short)data_buf[j]); if( endp_int == Device_Atti.Device[0].Device_endp ) Device_Atti.Device[0].tog = Device_Atti.Device[0].tog ? FALSE : TRUE; else Device_Atti.Device[1].tog = Device_Atti.Device[1].tog ? FALSE : TRUE; } return s; } 很是郁闷,求高人指点!!

调用时,是跟例程差不多的。 第1次调用参数是(0,端点地址) 第2次调用参数是(1,端点地址) 第3次调用参数是(0,端点地址) 第4次调用参数是(1,端点地址) . . . .


您把端点地址打印出来看下,与您操作的键盘端点地址是否对应的。


接口描述符:09,04,00,00,01,03,01,01,00, 群组描述符:09,21,10,01,00,01,22,36,00, 端点描述符:07,05,81,03,08,00,0A, /*第3个字节为端点号*/

报告描述符:(长度:54) 05,01,09,06,A1,01,05,08,19,01,29,03,15,00,25,01,75,01,95,03,91,02,95,05,91,01,05 ,07,19,E0,29,E7,95,08,81,02,75,08,95,01,81,01,19,00,29,91,26,FF,00,95,06,81,00,C 0, set idle success 此USB设备为复合设备! 接口描述符2:09,04,01,00,01,03,01,02,00, 群组描述符2:09,21,10,01,00,01,22,6C,00, 端点描述符2:07,05,82,03,05,00,0A, /*第3个字节为端点号*/

报告描述符2:(长度:108) 05,01,09,02,A1,01,85,03,09,01,A1,00,05,09,19,01,29,03,15,00,25,01,95,03,75,01,81 ,02,95,01,75,05,81,01,05,01,09,30,09,31,09,38,15,81,25,7F,75,08,95,03,81,06,C0,C 0,05,01,09,80,A1,01,85,02,19,81,29,83,15,00,25,01,75,01,95,03,81,02,75,01,95,05, 81,01,C0,05,0C,09,01,A1,01,85,01,19,00,2A,3C,02,15,00,26,3C,02,95,01,75,10,81,00 ,C0, 初始化成功!

端点号:81 <-----第一次调用打印出来的端点号,正确 端点号:82 <-----第二次调用打印出来的端点号,正确


在获取数据的时候,您看这个位置的的端点地址是多少,是不是 1? 【第1次调用参数是(0,端点地址) 第2次调用参数是(1,端点地址)】

另外,这个键盘是个复合的设备,同步标志位应该是两个独立的。并且是在获取到数据之后进行切换。


UploadImages/201322811274173.rar 您试下这个程序。


端点地址是0x81 ----------<问题会不会出在这儿>

同步标志是跟您说的一样的。


5楼的那个代码试过没?端点地址是0x81是对的。


我用的是STM32处理器,不过就是根据那个例程一步步来的。


如果您用的是论坛上的那个例程的话, UINT8 data_buf[90],这个地方的缓冲区小了,在您获取报表的时候会溢出。 您把这个缓冲区定义大点。超过【报告描述符2:(长度:108)】108就可以了。 获取键值数据跟几个因素有关,端点地址、同步标志位、设备速度类型。 或者您换个鼠标试试,看能不能获取到数据。


************************************************** 主程序开始… CH376版本号:3

s=15H,USB设备以插入! 98H,1.5Mbps低速USB设备,,设置完毕! Len=34 ---<鼠标> set USB config error

设备描述符:12,01,00,02,00,00,00,08,6D,04,5A,C0,00,54,01,02,00,01, 配置描述符:09,02,22,00,01,01,00,A0,31, 接口描述符:09,04,00,00,01,03,01,02,00, 群组描述符:09,21,11,01,00,01,22,43,00, 端点描述符:07,05,81,03,06,00,0A,

报告描述符:(长度:67) 05,01,09,02,A1,01,09,01,A1,00,05,09,19,01,29,08,15,00,25,01,75,01,95,08,81,02,05 ,01,16,01,F8,26,FF,07,75,0C,95,02,09,30,09,31,81,06,15,81,25,7F,75,08,95,01,09,3 8,81,06,05,0C,0A,38,02,95,01,81,06,C0,C0, 初始化成功!

插上鼠标是这个样子的,不过还是读不出报告来。。。很是郁闷! 还有就是接受报告难道不用发接受报告命令吗?按照例程中的思想,好像是直接接受的。[Emot]1[/Emot] 单步走的话调用u8 get_int_in(u8 tog,u8 endp_int)中的 issue_token(tog,( endp_int << 4 ) | DEF_USB_PID_IN); s = Wait376Interrupt();---------->0x2A(应该是0x14才对,0x2A是超时响应吗?) if(s==0x14)....


1)set USB config error是设置配置错误?前面初始化就出问题了。 s = set_config( Device_Atti.Cfg_value ); 您看下设置配置返回值是多少 【s】 2)98H,1.5Mbps低速USB设备,,设置完毕! 如果您按例程来写的,那么程序默认的是设备是低速设备,您用万用表量下UD+ UD-上的电压。检测下是不是低速设备。 3)如果您有usb分析仪,可以抓取整个过程的数据看看问题出在哪。 4)接收报告是主机不断向设备发送命令的, void issue_token(UINT8 endptog, UINT8 endp_and_pid ) { CH376_WR_CMD_PORT( CMD2H_ISSUE_TKN_X ); CH376_WR_DAT_PORT( endptog ); CH376_WR_DAT_PORT( endp_and_pid ); mDelay2uS(); }


1)上面是鼠标才配置错误的,插键盘就没错误的。错误时【S】= 2E 2)速度是对的,如果把设置低速模式的那条代码注释掉,是不可以通讯的,设备描述符也读不出来。D+低、D-高 3)我没有USB分析仪呢 4)执行 IN 事务,是接收数据啊

小弟不才,多谢大哥相助!


1)s = Wait376Interrupt();---------->0x2A(应该是0x14才对,0x2A是超时响应吗?) 返回2a是对的,在没有数据的时候设备给一个NAK信号。只有当键盘有按键,或者鼠标移动的时候,主机才能获取到数据,此时返回的才是0x14.

2)上面是鼠标才配置错误的,插键盘就没错误的。错误时【S】= 2E 返回0x2e 说明设备给您返回了一个stall信号。可能是您发的命令有问题。设备不识别。

3)您把代码发至我邮箱吧,我给您看下 zfl@wch.cn


这是问题困惑我的第11天了,郁闷……

首先感谢大哥相助!

看了你给的资料,发现我的初始化程序好像有问题。 按下键盘按键不产生中断,我把前面的

set_addr(5);//设置地址

/* 设置USB配置 */ s = set_config( ((PUSB_ITF_DESCR)Interface_desc)->bInterfaceClass ); if(s != 0x14)printf("\n\r set USB config error -->S=%02X\n",s); /* 设置HID类设备的IDLE*/ s = set_idle(0); if(s != 0)printf("\n\r set idle error \n"); --------<这些设置注释掉,使用了下面一句>

s = Wait376InterruptCMD(CMD0H_AUTO_SETUP);//自动配置USB设备 if(s!=USB_INT_SUCCESS)return; 结果按下按键可以正常中断,但是中断的状态是S=0x16,意思是设备以断开!(不按按键不会中断)


1)如果前面初始化就出问题了,那么您先做下测试命令(往下发0x06的命令);如果不正确检查下您的硬件以及接口程序。如果是对的,那么检查初始化过程在那出现了问题,返回错误是什么。 2)如果前面的初始化不过的话,后面按下按键是获取不到数据的。先把前面的初始化调好了再去检查后面的问题。


只有登录才能回复,可以选择微信账号登录