I2C_SCL 时钟抖动问题之“if条件判断分支” 软件优化
一开始,我先给出一个比较常见的GPIO模拟的I2C的I2C_writeByte的代码,代码是从南京沁恒CH450的网站上download下来的推荐代码。
void CH450_I2c_WrByte(unsigned char dat) //写一个字节数据
{
unsigned char i;
CH450_SDA_D_OUT; /* 设置SDA为输出方向 */
for(i=0;i!=8;i++) // 输出8位数据
{
if(dat&0x80) {CH450_SDA_SET;}
else {
CH450_SDA_CLR;
}
DELAY_0_1US; // 可选延时,这边对应的为一个指令周期
CH450_SCL_SET;
dat<<=1;
DELAY_0_1US; // 可选延时,这边对应的为一个指令周期
CH450_SCL_CLR;
}
CH450_SDA_D_IN; /*设置SDA为输入方向 */
CH450_SDA_SET;
DELAY_0_1US;
CH450_SCL_SET; //接收应答
DELAY_0_1US;
CH450_SCL_CLR;
}
使用keil的逻辑分析工具,查看I2C波形,SCL一个周期内放大,发现仿真输出结果有差异。
SDA为高变低的时候,CLK从之前拉高到之后拉高的周期时间,经历了14个指令周期(如上图所示,水平方向,1Grid=0.5us,即24M条件下的一个指令周期)
SCL从拉高,保持高,到拉低:5个指令周期
SCL从拉低(保持低)~SDA拉低,7个指令周期
SCL继续保持低~SCL拉高:2个指令周期<