对头~~~放慢速度试试,或SDA/SCL上加100P以内的电容.
如果时序是模拟出来的,那么SCL的跳变时机很重要~~~
"芯片无应答信号(ACK)"好象这样的问题很常见,我用PC的并口模拟I2C时 也发现了此问题. 主要是第9个脉冲的问题. 一般要多延时测试多次才能得到ACK信号. 因为从设备可能在验证数据的真伪,验证完正确后才送出ACK信号.
这是我的PC端源码: HRESULT CVIFUNC I2C_GetAck(void) { HRESULT __result = S_FALSE; int i; for (i = 0; i < I2C_waitAckDelay; i ++) { if (I2C_GetSDA() == 0) //释放数据总线读数据总线 { __result = S_OK; break; } } I2C_SetSCL();//拉高时钟(必须在SDA=1时)??? I2C_ClrSCL();//拉低时钟 I2C_ClrSDA();//保证SDA=SCL=0///(拉低SDA便于发送停止位) return __result;//SDA=1,SCL=0 } unsigned char CVIFUNC I2C_GetSDA (void) { unsigned char data; HotTimer_Start ();//在XP下启动由菜农同志封装的uS级定时器 data = inp (Hot_I2CISPDataPortAddress);//读数据口地址的内容 data |= (1 << I2C_wrSDA);//SDA=1 outp (Hot_I2CISPDataPortAddress, data);//写数据口1个字节 do { data = inp (Hot_I2CISPDataPortAddress + I2C_rdAddrOff);//读状态口地址的内容 data &= (1 << I2C_rdSDA);//只取出SDA位!!!!注意没~号 } while ((data == 0) && HotTimer_GetTime () < 0.000014);//最多测试14uS return (unsigned char)data; }
|
|