[求助]用ch372做单片机和PC机的usb通信的问题

各位做过类似电路的大哥,现在我碰到一个尴尬的问题,一直以来我的电路只要插上USB连线,电脑就提示“未识别的USB设备”,今天下午我把程序的延时部分加长了,第一次连上去的时候无法识别,我第二次连上,居然奇迹出现了,提示设备识别成功了(当时太激动,没看清楚是几个什么字,反正是能装驱动了),但是当我装完驱动,用调试工具的时候,设备再一次识别失败,我拔掉连线,再插上去,依然是无法识别。 我很郁闷,我同学说是我的电路不可靠,因为我没做PCB,为了图方便,只是用一个单片机最小系统的板子连上几根线再用万用板搭了一个372的最小系统。这样是不是不行啊,请有经验的大哥给个肯定的答复,如果做PCB能解决问题,我就做一块,如果是其他问题麻烦也告诉我,也好让我甘心啊!

首先,对于372芯片,只要模式设置成功之后,就应该会可以找到新的硬件的,一般的程序里面的延时是这样的:命令与命令,命令与数据之间的延时为2US,数据与数据之间的延时为1US,所以,如果延时不正确的话,模式也应该不会设置成功,如果是自己搭的板子的话,那么一定要注意共地性一定要好,尤其是在你设置好模式之后,USB线和你板子以及计算机之间的共地,还有就是线一定要为屏蔽线,还有就你的测试命令是通过的吗??


谢谢hcn,看来我的延时部分还是要继续完善。不过一般我都没有测试,因为不知道具体怎么去操作啊,呵呵,很弱智吧,是测试I/O口的引脚吗?通过与不通过有什么区别呢?麻烦解答下


我已经搞定了,发消息给我吧,看看我能帮上什么忙,最好把电路发给我看看

我就是采用标准电路,用AVR单片机,虽然我是用375但是做slave是一样的


你可以不用去做测试,你只要看下延时的反汇编就可以知道你的延时有多长时间了,如果硬件连线没有问题的话,那么测试命令的通过就是从数据口读出来的数据是你输入数据的取反,这个时候设置模式的话,UD+的电压应该为3。3V左右


哦,谢谢两位了,对hcn所说的,我用的是c51编程,程序就是你们给的例子,编译器是Keil uVision2,是不是模式设置对延时的要求很严格啊,如果延时不是恰恰好就会面临设置失败吗?还有,即使未识别设备的时候,UD+的电压也是3.3V左右的,所以我觉得很纳闷了

对里杰兄所说的,先谢谢了,呵呵,我由于是做个实验,所以就没画电路,具体连接是P2.0接A0,P2.6接CS#,int0接INT#,P3.6接WR#,P3.7接RD#,D0-D7直接接的P0.1—P0.7,我是想先能够让372工作,再考虑电路的其他部分,因为具体要实现什么功能导师和我还没商量好,请保持联系,我有了方案就给你发图,也有可能是用375,说不定跟兄台你做的差不多:)


USB协议里面在确定是不是USB设备的时候,只要在UD+电压为3V,UD-电压为0V的时候就认为是全速设备,相反为低速设备,但是主机真正识别到是什么样的设备的话,需要设备上传描述符之后才可以识别到,所以,即使你不接USB设备,直接将USB线的UD+电压拉到3V的话,也会识别到一个未知设备,所以,你可以将你的单片机拿下来,直接给372上电,你看下UD+的电压是多少?如果为3V的话,检查硬件,如果不是的话,那么你将单片机和372通信,必要条件是测试命令必须要过,我们提供给你的例子程序里面不一定都做了测试命令的,你可以看下程序,或者将你的程序贴出来,如果没加的话,我们可以帮你加下,在测试命令通过的情况下,设置好模式之后,UD+的电压就应该我3V左右了,如果这个时候还没有找到新硬件的话(提示装驱动),那么你就要检查USB口和计算机的连线是否为屏蔽线,UD+和UD-有没有接反以及372的晶振是否为12M?


嗯,按你的方法试了一下,拿下单片机,UD+是3V多,电脑果然是检测到未识别的USb设备,真是高人啊,呵呵。程序贴在下面,连接线是屏蔽线,而且晶振和UD+和UD-没接反,请问识别成功后在任务栏里面有没有一个提示符,就像U盘插进去的时候一样? #include #include #include #include #include "CH375INC.H" #define uchar unsigned char

uchar volatile xdata CH375_CMD_PORT _at_ 0xBDF1; /* CH375命令端口的I/O地址 CS接P2.1,A0接P2.0,D0-D7连P0-P7*/ uchar volatile xdata CH375_DAT_PORT _at_ 0xBCF0; /* CH375数据端口的I/O地址 */

/* 延时根据具体情况调节 */ void delay3us( ) { unsigned char i; for ( i = 3; i != 0; i -- ); /* 根据单片机的时钟选择初值 */ }

/* 与CH375有关的基本I/O操作 */

void CH375_WR_CMD_PORT(uchar cmd) { /* 向CH375的命令端口写入命令,周期不小于4uS,如果单片机较快则延时 */ delay3us( ); CH375_CMD_PORT=cmd; delay3us( ); }

void CH375_WR_DAT_PORT(uchar dat) { /* 向CH375的数据端口写入数据,周期不小于1.5uS,如果单片机较快则延时 */ _nop_(); _nop_(); CH375_DAT_PORT=dat; _nop_(); _nop_(); //delay1us( ); /* 如果是MCS51单片机,因其较慢,所以实际上无需延时 */ }

uchar CH375_RD_DAT_PORT( void ) { /* 从CH375的数据端口读出数据,周期不小于1.5uS,如果单片机较快则延时 */ //delay1us( ); /* 如果是MCS51单片机,因其较慢,所以实际上无需延时 */ _nop_(); _nop_(); return(CH375_DAT_PORT); }

/* 延时50毫秒,不精确 */ void Delay50ms( ) { unsigned char i, j; for ( i=200; i!=0; i-- ) for ( j=250; j!=0; j-- ); }

/* CH375初始化子程序 */ void CH375_Init( ) { uchar i; /* 测试CH375是否正常工作,可选操作,通常不需要 */ CH375_WR_CMD_PORT( CMD_CHECK_EXIST ); /* 测试CH375是否正常工作 */ CH375_WR_DAT_PORT( 0x55 ); /* 写入测试数据 */ i = ~ 0x55; /* 返回数据应该是测试数据取反 */ if ( CH375_RD_DAT_PORT( ) != i ) { /* CH375不正常 */ for ( i=80; i!=0; i-- ) { CH375_WR_CMD_PORT( CMD_RESET_ALL ); /* 多次重复发命令,执行硬件复位 */ CH375_RD_DAT_PORT( ); } CH375_WR_CMD_PORT(0);

Delay50ms( ); /* 延时50ms */ }

/* 设置USB工作模式, 必要操作 */ CH375_WR_CMD_PORT(CMD_SET_USB_MODE); CH375_WR_DAT_PORT(2); /* 设置为使用内置固件的USB设备方式 */

for ( i=100; i!=0; i-- ) { /* 等待操作成功,通常需要等待10uS-20uS */ if ( CH375_RD_DAT_PORT( ) == CMD_RET_SUCCESS ) break; } /* if ( i==0 ) { CH375存在硬件错误 }; */ /* 下述启用中断,假定CH375连接在INT0 */ IT0 = 0; /* 置外部信号为低电平触发 */ IE0 = 0; /* 清中断标志 */ EX0 = 1; /* 允许CH375中断 */ }

/* CH375中断服务程序,使用寄存器组1 */ void mCh375Interrupt( ) interrupt 0 using 1 { uchar InterruptStatus; uchar i, length; uchar data buffer[ 64 ];

CH375_WR_CMD_PORT( CMD_GET_STATUS ); /* 获取中断状态并取消中断请求 */ InterruptStatus = CH375_RD_DAT_PORT( ); /* 获取中断状态 */ switch ( InterruptStatus ) { /* 分析中断状态处理 */ case USB_INT_EP2_OUT: { /* 批量端点下传成功 */ CH375_WR_CMD_PORT( CMD_RD_USB_DATA ); /* 从当前USB中断的端点缓冲区读取数据块,并释放缓冲区 */ length = CH375_RD_DAT_PORT( ); /* 首先读取后续数据长度 */ for ( i = 0; i < length; i ++ ) buffer[ i ] = CH375_RD_DAT_PORT( ); /* 接收数据包 */ /* 测试数据正确性,将接收到的命令包数据取反后返回给PC机 */ CH375_WR_CMD_PORT( CMD_WR_USB_DATA7 ); /* 向USB端点2的发送缓冲区写入数据块 */ CH375_WR_DAT_PORT( length ); /* 首先写入后续数据长度,回传刚接收到的数据长度 */ for ( i = 0; i < length; i ++ ) CH375_WR_DAT_PORT( ~ buffer[ i ] ); /* 数据取反后返回,由计算机应用程序测试数据是否正确 */ break; } case USB_INT_EP2_IN: { /* 批量数据发送成功 */ CH375_WR_CMD_PORT( CMD_UNLOCK_USB ); /* 释放当前USB缓冲区 */ break; } default: { /* 其它中断,未用到,解锁后退出即可 */ CH375_WR_CMD_PORT( CMD_UNLOCK_USB ); /* 释放当前USB缓冲区 */ break; } } }

/*主程序*/ main( ) { Delay50ms( ); /* 延时等待CH375初始化完成,如果单片机由CH375提供复位信号则不必延时 */ CH375_Init( ); /* 初始化CH375 */ EA = 1; /* 允许中断 */ while ( 1 ); /* 以下指令开始工作循环,等待PC机命令进行操作 */ }


如果是这样的话,那么你要检查你的硬件了。仔细查USB口那边的问题


如果安装了驱动,识别成功的话,并不在任务栏里显示什么,而是在计算机的设备管理器中多了个外部接口,显示为:USB CH372\CH375。


嗯,谢谢了,那我的程序没问题吗?如果是硬件的问题,准备去做PCB,还有就是,有没有什么办法让它在电脑里比较明显的显示出来,毕竟每次去设备管理器里面找有些不方便啊,呵呵


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