各位大虾:我用ATMEGA16L操做24C16写入数据时正常。但读出来的时候就不正常了,在读操作中其他操作正常返回代码但在发送了读命令字后,24C16返回一个信号。我在发送响应信号的时候,24c16就一直没发送数据回来了。附上我的程序,希望各位大虾们帮我分析分析。 #define START_TWI TWCR=(1<<TWINT)|(1<<TWSTA)|(1<<TWEN) #define SEND_TWI TWCR=(1<<TWINT)|(1<<TWEN) #define STOP_TWI TWCR=(1<<TWINT)|(1<<TWSTO)|(1<<TWEN) #define RSTART_TWI TWCR=(1<<TWINT)|(1<<TWSTA)|(1<<TWEN)
#define ACK TWCR=(1<<TWINT)|(1<<TWEA)|(1<<TWEN) #define NO_ACK TWCR=(1<<TWINT)|(1<<TWEN) #define TWI_STATUE TWSR&0xf8 #define TWINT_SET TWCR&0x80 #define W_COMMAD 0xa0 #define R_COMMAD 0xa1 #define TIME 100 /******************************* 读24c16 *******************************/ uint R_24C16(uint addr) { uchar addrl,addrh,time; uint r_data; addrl=(uchar)addr; addr>>=8; addrh=(uchar)addr; addrh<<=1; addrh=addrh|W_COMMAD; time=TIME; while(time--) { START_TWI; //发送start信号START_TWI while(!(TWINT_SET))NOP(); if(TWI_STATUE!=0x08)continue;//start信号已经发出 TWDR=addrh; //发送写命令字 SEND_TWI; while(!(TWINT_SET))NOP(); if(TWI_STATUE!=0x18)continue; //写命令字已经发出 TWDR=addrl; //发送低字地址节数据 SEND_TWI; while(!(TWINT_SET))NOP(); //低字节地址数据已经发出 if(TWI_STATUE!=0x28)continue; RSTART_TWI; //重启 while(!(TWINT_SET))NOP(); if(TWI_STATUE!=0x10)continue;//重启信号已经发出 TWDR=(addrh|0x01);//读命令字 SEND_TWI; while(!(TWINT_SET))NOP(); if(TWI_STATUE!=0x40)continue; //读命令字已经发出 /********************************************************** 从这里开始就不正常了,发送了ACK后TWINT位就一直不变高。一直在等待 *************************************************************/ ACK;//产生应答 while(!(TWINT_SET))NOP(); //程序一直在这里循环了没接收到数据 LED_ON; if(TWI_STATUE!=0x50)continue; //接收到数据并产生应答 r_data=(uint)TWDR;//读取数据 NO_ACK;//不产生应答 while(!(TWINT_SET))NOP(); if(TWI_STATUE!=0x58)continue;//接收到数据不产生应答信号 r_data<<=8; r_data=(r_data|(uint)TWDR); STOP_TWI; break; } return r_data; } |