高中生
最后登录1970-1-1
在线时间 小时
注册时间2016-3-27
|
我用模拟I2C与ZLG7290通信,无法接收到正确的数据,收到的数据经常是0xff;下面是我的代码,请大神们帮忙解决一下,小弟万分感激!!!!
问题:读出的数据不正确,有时候会有变化,有时候没有。小弟考虑硬件没什么大问题,主要是F429这个速率会不会影响模拟I2C的通信,这个问题我卡了半个月,一直没有解决,求大神帮忙
//定义SCL SDA管脚
#define SCL_H GPIOH->BSRRL = GPIO_Pin_4
#define SCL_L GPIOH->BSRRH = GPIO_Pin_4
#define SDA_H GPIOA->BSRRL = GPIO_Pin_5
#define SDA_L GPIOH->BSRRH = GPIO_Pin_5
#define SCL_read GPIOH->IDR & GPIO_Pin_4
#define SDA_read GPIOH->IDR & GPIO_Pin_5
//IO口初始化
void I2C_GPIO_Config(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOH, ENABLE);//使能按键使用的引脚时钟
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_4|GPIO_Pin_5;//配置SCL引脚
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;
GPIO_InitStru cture.GPIO_OType = GPIO_OType_OD;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL;
GPIO_Init(GPIOH,&GPIO_InitStructure);
SCL_H;
SDA_H;
}
//函数调用 这部分在网上download的 以前开发项目可以使用(在STM32107开发过)
void IIC_Delay(u16 times)
{
u16 loop,loop1;
for(loop=0;loop<times;loop++)
for(loop1=times;loop1>0;loop1--);
}
void IIC_SetSclPin(void)
{
SCL_H;
}
void IIC_ClrSclPin(void)
{
SCL_L;
}
void IIC_SetSdaPin(void)
{
//GPIO_WriteBit(GPIOB,GPIO_Pin_9,Bit_SET);
SDA_H;
}
void IIC_ClrSdaPin(void)
{
//GPIO_WriteBit(GPIOB,GPIO_Pin_9,Bit_RESET);
SDA_L;
}
bool IIC_GetSdaStus(void)
{
bool tmp;
/*if(GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_9)&0x01) tmp=TRUE;
else tmp=FALSE;*/
if (SDA_read)
tmp=1;
else tmp=0;
return tmp;
}
bool IIC_CheckACK(void)
{
return IIC_GetSdaStus();
}
void IIC_SetScl(bool HLow)
{
HLow?IIC_SetSclPin():IIC_ClrSclPin();
}
void IIC_SetSda(bool HLow)
{
HLow?IIC_SetSdaPin():IIC_ClrSdaPin();
}
void IIC_Start(void)
{
IIC_SetScl(LOW);
// Delay(DelayTime);
IIC_Delay(IIC_DELAYTIME);
// SDA(Hight);
IIC_SetSda(HIGHT);
// Delay(DelayTime);
IIC_Delay(IIC_DELAYTIME);
// SCL(Hight);
IIC_SetScl(HIGHT);
// Delay(DelayTime);
IIC_Delay(IIC_DELAYTIME);
// SDA(Low);
IIC_SetSda(LOW);
// Delay(DelayTime);
IIC_Delay(IIC_DELAYTIME);
// SCL(Low);
IIC_SetScl(LOW);
}
void IIC_Stop(void)
{
IIC_SetSda(LOW);
IIC_Delay(IIC_DELAYTIME);
IIC_SetScl(HIGHT);
IIC_Delay(IIC_DELAYTIME);
IIC_SetSda(HIGHT);
IIC_Delay(IIC_DELAYTIME);
IIC_SetScl(LOW);
}
bool IIC_Send(u8 ucVal) //I2C发送一个字节
{
bool Ack;
u16 AckLoop;
u8 i;
for(i=0;i<8;i++)
{
IIC_SetScl(LOW);
IIC_Delay(IIC_DELAYTIME);
IIC_SetSda((ucVal & 0x80)?TRUE:FALSE);
IIC_Delay(IIC_DELAYTIME);
IIC_SetScl(HIGHT);
IIC_Delay(IIC_DELAYTIME);
ucVal<<= 1;
}
IIC_SetScl(LOW);
IIC_Delay(IIC_DELAYTIME);
IIC_SetSda(HIGHT);
IIC_Delay(IIC_DELAYTIME);
IIC_SetScl(HIGHT);
Ack = IIC_NOACK;
for(AckLoop=0;AckLoop<ACKCHECKTIME;AckLoop++) //260us
{
if(!IIC_GetSdaStus())
{
Ack = IIC_ACK;
break;
}
IIC_Delay(IIC_DELAYTIME);
}
IIC_SetScl(LOW);
return Ack; //return success=0 / failure=1
}
u8 IIC_Read(bool bACK)
{
u8 Data;
u8 i;
Data = 0;
for(i=0;i<8;i++)
{
Data <<= 1;
IIC_SetScl(LOW);
IIC_Delay(IIC_DELAYTIME);
IIC_SetSda(HIGHT);
IIC_Delay(IIC_DELAYTIME);
IIC_SetScl(HIGHT);
IIC_Delay(IIC_DELAYTIME);
if(IIC_GetSdaStus())
Data |= 1;
else
Data &= 0xfe;
}
IIC_SetScl(LOW);
IIC_Delay(IIC_DELAYTIME);
IIC_SetSda(bACK);
IIC_Delay(IIC_DELAYTIME);
IIC_SetScl(HIGHT);
IIC_Delay(IIC_DELAYTIME);
IIC_SetScl(LOW);
return Data;
}
bool IIC_ByteWrite(u8 DeviceAdd,u8 address,u8 ucVal)
{
// I2C_SDA_OUT();
IIC_Start();
if(IIC_Send(DeviceAdd|((address>>7)&0x0e)))//NACK
{
return IIC_NOACK;
}
IIC_Send((u8)(address&0xff));
IIC_Send(ucVal);
IIC_Stop();
IIC_Delay(IIC_DELAYTIME);
IIC_Delay(IIC_DELAYTIME);
IIC_Delay(20*IIC_DELAYTIME);
return IIC_ACK;
}
u8 IIC_ByteRead(u8 DeviceAdd,u8 address)
{
u8 value;
IIC_Start();
IIC_Send(DeviceAdd|((address>>7)&0x0e));
IIC_Send((u8)(address&0xff));
IIC_Stop();
IIC_Start();
IIC_Send(DeviceAdd|0x01);
value=IIC_Read(IIC_NOACK);
IIC_Stop();
IIC_Delay(IIC_DELAYTIME);
IIC_Delay(IIC_DELAYTIME);
IIC_Delay(IIC_DELAYTIME);
return value;
}
bool IIC_BytesWrite(u8 DeviceAdd,u8 address,u8 *buf,u16 nByte) //
{
int lp=0;
for(lp=0;lp<nByte;lp++)
{
IIC_ByteWrite(DeviceAdd,lp+address,*buf++);
}
return TRUE;
}
bool IIC_BytesRead(u8 DeviceAdd,u8 address,u8 *buf,u16 nByte) // 从器件读地址 从器件内存单元地址 要写的数据地址 要写的数据字节 返回0 写数据成功 1在写数据过程中从器件回响NAK
{
int lp=0;
for(lp=0;lp<nByte;lp++)
{
*buf++=IIC_ByteRead(DeviceAdd,lp+address);
}
return TRUE;
}
//读取数据
gKey.KeyVar = IIC_ByteRead(0x70, 0x01);
问题:读出的数据不正确,有时候会有变化,有时候没有。小弟考虑硬件没什么大问题,主要是F429这个速率会不会影响模拟I2C的通信,这个问题我卡了半个月,一直没有解决,求大神帮忙
|
|