移植的51的库。
初始化,连接u盘,打开目录,打开文件都正常,
但是在使用CH376ByteRead函数时,发送CMD_BYTE_READ和数据长度后,中断一直不发生。
代码如下:请指点一下,谢谢
/* */ #define F_CPU 16000000UL
#include "ch376.h" #include #include #include
#define CH376_DATA_PORT PORTA #define CH376_DATA_PIN PINA #define CH376_DATA_DDR DDRA
#define CH376_CMD_PORT PORTC #define CH376_CMD_PIN PINC #define CH376_CMD_DDR DDRC
#define CH376_A0 PC7 #define CH376_RD PC6 #define CH376_WR PC5 #define CH376_RSTI PC4 #define CH376_INT PC3 #define CH376_CS PC2
////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////// Hardware Access Function //////////////////////////////////// //////////////////////////////////////////////////////////////////////////////////////////////
void CH376PortInit( ) /* 由于使用通用I/O模块并口读写时序,所以进行初始化 */
{ uint8_t i; /* 设置8位并口为输入 */
CH376_DATA_DDR = 0x00; /* 设置CS,WR,RD,A0,RSTI为输出,设置INT#为输入 */
CH376_CMD_DDR |= _BV(CH376_CS)|_BV(CH376_WR)|_BV(CH376_RD)|_BV(CH376_A0)|_BV(CH376_RSTI); CH376_CMD_DDR &= ~_BV(CH376_INT); /* 设置CS,WR,RD默认为高电平 */ CH376_CMD_PORT |= _BV(CH376_CS)|_BV(CH376_WR)|_BV(CH376_RD); /* 复位系统 */ CH376_CMD_PORT |= _BV(CH376_RSTI); _delay_ms(1); CH376_CMD_PORT &= ~_BV(CH376_RSTI); //延时100ms 等待 CH376 复位进入工作状态 for(i=0;i<10;i++) _delay_ms(10);
}
void CH376WriteCmd( uint8_t cmd ) /* 外部定义的被CH376程序库调用的子程序,向CH376写命令 */
{ //_delay_us(5); /* 至少延时2uS */
CH376_CMD_PORT |= _BV(CH376_A0); /* 输出A0=1 打开命令端口 */
CH376_DATA_PORT = cmd; /* 向CH376的并口输出数据 */
CH376_DATA_DDR = 0xFF; /* 并口D0-D7输出 */
/* 输出有效写控制信号, 写CH376芯片的命令端口, CS=0; WR=0; RD=1; */
CH376_CMD_PORT &= ~_BV(CH376_CS)&~_BV(CH376_WR); CH376_CMD_PORT |= _BV(CH376_RD); //_delay_us(0.2); //CH376_DATA_DDR = 0xFF; /* 该操作无意义,仅作延时,CH376要求读写脉冲宽度大于100nS */
/* 输出无效的控制信号, 完成操作CH376芯片, CS=1; WR=1; RD=1; */
CH376_CMD_PORT |= _BV(CH376_CS)|_BV(CH376_WR)|_BV(CH376_RD);
CH376_DATA_DDR = 0x00; /* 禁止数据输出 */
_delay_us(2); /* 至少延时2uS */
}
void CH376WriteData( uint8_t data ) /* 外部定义的被CH376程序库调用的子程序,向CH376写数据 */
{ //_delay_us(5); /* 至少延时2uS */ CH376_CMD_PORT &= ~_BV(CH376_A0); /* 输出A0=0; 打开数据端口 */
CH376_DATA_PORT = data; /* 向CH376的并口输出数据 */
CH376_DATA_DDR = 0xFF; /* 并口D0-D7输出 */ /* 输出有效写控制信号, 写CH376芯片的数据端口, CS=0; WR=0; RD=1; */
CH376_CMD_PORT &= ~_BV(CH376_CS)&~_BV(CH376_WR); CH376_CMD_PORT |= _BV(CH376_RD); //_delay_us(0.2);
//CH376_DATA_DDR = 0xFF; /* 该操作无意义,仅作延时,CH376要求读写脉冲宽度大于100nS */
/* 输出无效的控制信号, 完成操作CH376芯片, CS=1; WR=1; RD=1; */
CH376_CMD_PORT |= _BV(CH376_CS)|_BV(CH376_WR)|_BV(CH376_RD);
CH376_DATA_DDR = 0x00; /* 禁止数据输出 */
_delay_us(2); /* 至少延时1.2uS */
}
uint8_t CH376ReadData( void ) /* 外部定义的被CH376程序库调用的子程序,从CH376读数据 */
{
uint8_t data;
_delay_us(1.5); /* 至少延时1.2uS */ CH376_CMD_PORT &= ~_BV(CH376_A0); /* 输出A0=0; 打开数据端口 */
CH376_DATA_DDR = 0x00; /* 数据输入 */ /* 输出有效读控制信号, 读CH376芯片的数据端口, CS=0; WR=1; RD=0; */ CH376_CMD_PORT &= ~_BV(CH376_CS)&~_BV(CH376_RD); CH376_CMD_PORT |= _BV(CH376_WR);
CH376_DATA_DDR = 0x00; /* 该操作无意义,仅作延时,CH376要求读写脉冲宽度大于100nS */
data = CH376_DATA_PIN; /* 从CH376的并口PA输入数据 */
/* 输出无效的控制信号, 完成操作CH376芯片, CS=1; WR=1; RD=1; */ CH376_CMD_PORT |= _BV(CH376_CS)|_BV(CH376_WR)|_BV(CH376_RD);
return( data );
}
/* 查询CH376中断(INT#低电平) */
uint8_t CH376QueryInterrupt( void )
{ //uint8_t i; //PORTB ^= _BV(PB0); //for(i=0;i<200;i++) // _delay_ms(10);
return( CH376_CMD_PIN & _BV(CH376_INT) ); /* 如果连接了CH376的中断引脚则直接查询中断引脚 */
}
////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////// File Access API //////////////////////////////////// //////////////////////////////////////////////////////////////////////////////////////////////
uint8_t CH376InitHost( void ) /* 初始化CH376 */
{
uint8_t res;
//CH376PortInit( ); /* 接口硬件初始化 */
CH376WriteCmd( CMD_CHECK_EXIST ); /* 测试单片机与CH376之间的通讯接口 */
CH376WriteData( 0x65 );
res = CH376ReadData( );
if ( res != 0x9A ) return( ERR_USB_UNKNOWN ); /* 通讯接口不正常,可能原因有:接口连接异常,其它设备影响(片选不唯一),串口波特率,一直在复位,晶振不工作 */
CH376WriteCmd( CMD_SET_USB_MODE ); /* 设备USB工作模式 */
CH376WriteData( 0x06 );
_delay_us(20);
res = CH376ReadData( );
if ( res == CMD_RET_SUCCESS ) return( USB_INT_SUCCESS );
else return( ERR_USB_UNKNOWN ); /* 设置模式错误 */
}
uint8_t CH376WaitInterrupt( void ) { while ( CH376QueryInterrupt() ); /* 一直等中断 */ return( CH376GetIntStatus( ) ); /* 检测到中断 */ }
uint8_t CH376GetIntStatus( void ) /* 获取中断状态并取消中断请求 */
{
uint8_t s;
CH376WriteCmd( CMD_GET_STATUS );
s = CH376ReadData( );
return( s );
}
uint8_t CH376SendCmdWaitInt( uint8_t cmd ) /* 发出命令码后,等待中断 */
{
CH376WriteCmd( cmd );
return( CH376WaitInterrupt( ) );
}
uint8_t CH376DiskConnect( void ) /* 检查U盘是否连接,不支持SD卡 */
{
if ( CH376QueryInterrupt( ) ) CH376GetIntStatus( ); /* 检测到中断 */
return( CH376SendCmdWaitInt( CMD_DISK_CONNECT ) );
}
uint8_t CH376DiskMount( void ) /* 初始化磁盘并测试磁盘是否就绪 */
{
return( CH376SendCmdWaitInt( CMD_DISK_MOUNT ) );
}
void CH376SetFileName( const char *name ) /* 设置将要操作的文件的文件名 */
{ uint8_t c;
CH376WriteCmd( CMD_SET_FILE_NAME );
c = *name;
CH376WriteData( c );
while ( c ) {
name ++;
c = *name;
if ( c == DEF_SEPAR_CHAR1 || c == DEF_SEPAR_CHAR2 ) c = 0; /* 强行将文件名截止 */
CH376WriteData( c );
}
}
uint8_t CH376FileOpen( void ) /* 在根目录或者当前目录下打开文件或者目录(文件夹) */
{
return( CH376SendCmdWaitInt( CMD_FILE_OPEN ) );
}
uint8_t CH376ReadBlock( uint8_t *buf ) /* 从当前主机端点的接收缓冲区读取数据块,返回长度 */
{
uint8_t s, l;
CH376WriteCmd( CMD_RD_USB_DATA0 );
s = l = CH376ReadData( ); /* 长度 */
if ( l ) {
do {
*buf = CH376ReadData( );
buf ++;
} while ( -- l );
}
return( s );
}
uint8_t CH376ByteLocate( uint32_t offset ) /* 以字节为单位移动当前文件指针 */
{
CH376WriteCmd( CMD_BYTE_LOCATE );
CH376WriteData( (uint8_t)offset );
CH376WriteData( (uint8_t)((uint16_t)offset>>8) );
CH376WriteData( (uint8_t)(offset>>16) );
CH376WriteData( (uint8_t)(offset>>24) );
return( CH376WaitInterrupt() );
}
uint8_t CH376ByteRead( uint8_t *buf, uint16_t reqcount, uint16_t *realcount ) /* 以字节为单位从当前位置读取数据块 */
{
uint8_t s;
if ( realcount ) *realcount = 0; CH376WriteCmd( CMD_BYTE_READ );
//CH376WriteData( (uint8_t)reqcount );
//CH376WriteData( (uint8_t)(reqcount>>8) ); CH376WriteData( 0x00 ); CH376WriteData( 0x02 );
while ( 1 ) { //PORTB |= _BV(PB0);
s = CH376WaitInterrupt(); //s = CH376GetIntStatus(); PORTB |= _BV(PB0);
if ( s == USB_INT_DISK_READ ) {
s = CH376ReadBlock( buf ); /* 从当前主机端点的接收缓冲区读取数据块,返回长度 */
CH376WriteCmd( CMD_BYTE_RD_GO );
buf += s;
if ( realcount ) *realcount += s;
}
/* else if ( s == USB_INT_SUCCESS ) return( s );*/ /* 结束 */
else return( s ); /* 错误 */
}
}