打印

STM32用I2C读IAQengine

[复制链接]
7527|43
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
ustb_cc|  楼主 | 2013-1-22 13:11 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
实验室需要做一个空气质量检测的节点,选用了IAQengine传感器测量室内CO2浓度。
附上代码:
#define IAQ_READ_ADDRESS   0xB5
void IAQengine_Read(u8 *pBuffer, u8 NumByteToRead)
{
/* Wait when the bus is busy */
while(I2C_GetFlagStatus(I2C1, I2C_FLAG_BUSY));

/* Generate start condition */
I2C_GenerateSTART(I2C1, ENABLE);
printf("step 1");

/* Test on EV5 and clear it (cleared by reading SR1 then writing to DR) */
while(!I2C_CheckEvent(I2C1,I2C_EVENT_MASTER_MODE_SELECT));

/* Send IAQ address for read */
I2C_Send7bitAddress(I2C1, IAQ_READ_ADDRESS, I2C_Direction_Receiver);
printf("step 2");

/* Test on EV6 and clear it */
while(!I2C_CheckEvent(I2C1,I2C_EVENT_MASTER_RECEIVER_MODE_SELECTED));
printf("step 3");


while(NumByteToRead)
{
  if(NumByteToRead == 1)
  {
   /* Disable Acknowledgement */
   I2C_AcknowledgeConfig(I2C1, DISABLE);
   /* Generate stop condition */
   I2C_GenerateSTOP(I2C1, ENABLE);
  }

  /* Wait for the byte to be received */
  while(I2C_GetFlagStatus(I2C1, I2C_FLAG_RXNE) == RESET);

  *pBuffer = I2C_ReceiveData(I2C1);
  pBuffer++;
  NumByteToRead--;
  printf("step 4");
}
问题:
程序运行后,“Step 3”死活不出来,也就是主机发送地址后,从机没有应答。不知道原因出在哪?
我看网上好多例子都是首先主机作为发送者,发送从机的片内地址,然后主机再作为接受者开始接受数据。但是这款传感器好像没有片内地址,一共就7个寄存器。所以也就没有主机发送数据的过程。不知道问题是不是出在这里。。。。。
第一次发帖,希望各位高手能够帮帮我,先谢谢了!

沙发
ustb_cc|  楼主 | 2013-1-22 13:13 | 只看该作者
IAQengine的手册3.3M,但是论坛限制附件大小1M,我发不上来。。。。。

使用特权

评论回复
板凳
sunnyhey| | 2013-2-4 16:19 | 只看该作者
我也是这样问题,很是纠结,楼主解决后麻烦分享下哈。。。

使用特权

评论回复
地板
ustb_cc|  楼主 | 2013-3-7 14:51 | 只看该作者
sunnyhey 发表于 2013-2-4 16:19
我也是这样问题,很是纠结,楼主解决后麻烦分享下哈。。。

年前的项目,之前一直没能读出数据来,年后实验室要重新拾起这个项目。对于iAQengine,我用硬件I2C和模拟I2C的方法都试过了,都是发送完地址后没有应答。模拟I2C程序我还在PCF8563上试过了,是能够读写的。郁闷啊,不知道问题到底出在哪里。不知道你解决了吗?

使用特权

评论回复
5
ustb_cc|  楼主 | 2013-3-7 14:55 | 只看该作者
附上模拟I2C的代码:
/* Private macro -------------------------------------------------------------*/
#define SCLL                                   GPIOB->BRR = GPIO_Pin_6
#define SCLH                                GPIOB->BSRR = GPIO_Pin_6                                               
#define SDAL                                GPIOB->BRR = GPIO_Pin_7
#define SDAH                                GPIOB->BSRR = GPIO_Pin_7

#define SDA_STATE                        GPIOB->IDR&GPIO_Pin_7

enum I2C_REPLY {I2C_NACK = 0, I2C_ACK = 1};

enum I2C_STATE {I2C_READY = 0, I2C_BUSY = 1, I2C_ERROR = 2};
/* Private functions ---------------------------------------------------------*/
u8 I2C_Start(void);
void I2C_Stop(void);
void I2C_Ack(u8);
u8 I2C_Wait_Ack(void);
void I2C_SendByte(u8);
u8 I2C_ReceiveByte(void);
*******************************************************************************/
void IAQ_Init(void)
{
        GPIO_InitTypeDef GPIO_InitStructure;

        //配置I2C1_SCL(PB6)和I2C1_SDA(PB7)开漏输出
        GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6 | GPIO_Pin_7;
        GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
        GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_OD;
        GPIO_Init(GPIOB, &GPIO_InitStructure);
}
*******************************************************************************/
u8 I2C_Start(void)
{
        SDAH;
        SCLH;
        delay_us(5);
        if(!SDA_STATE) {
                printf("I2C is busy!\r\n");
                return I2C_BUSY;        
        }
        SDAL;
        delay_us(5);
        SCLL;
        delay_us(5);
        if(SDA_STATE) {
                printf("I2C is error!\r\n");
                return I2C_ERROR;
        }
        return I2C_READY;
}
*******************************************************************************/
void I2C_Stop(void)
{
        SDAL;
        delay_us(5);
        SCLH;
        delay_us(5);
        SDAH;
        delay_us(5);
}
*******************************************************************************/
void I2C_Ack(u8 i)
{
        if(i)
                SDAL;                                //ACK
        else                                       
                SDAH;                                //NACK
        delay_us(2);
        SCLH;
        delay_us(2);
        SCLL;
        delay_us(2);
}
*******************************************************************************/
u8 I2C_Wait_Ack(void)
{
        u8 ucErrTime = 0;
        SDAH;
        delay_us(2);
        SCLH;
        delay_us(2);
        while(SDA_STATE)
        {
                ucErrTime++;
                if(ucErrTime > 250)
                {
                        I2C_Stop();
                        printf("I2C NACK!\r\n");
                        return I2C_NACK;
                }
        }
        SCLL;
        delay_us(2);
        return I2C_ACK;
}
*******************************************************************************/
void I2C_SendByte(u8 d)
{
        u8 i;

        SCLL;
        delay_us(2);
        for(i=0x80;i!=0;i/=2)
        {
                  if(i&d)
                           SDAH;
                  else
                           SDAL;
                delay_us(2);
                  SCLH;
                  delay_us(2);
                  SCLL;
                  delay_us(2);
        }
}
*******************************************************************************/
u8 I2C_ReceiveByte(void)
{
        u8 i, d=0;
        SDAH;
        SCLL;
        delay_us(2);
        for(i=0x80;i!=0;i/=2)
        {
                  SCLH;
                delay_us(2);
                if(SDA_STATE)
                           d |= i;
                 SCLL;
                  delay_us(2);
        }
        return d;
}
*******************************************************************************/
u8 IAQ_Read(u8 *pBuffer, u8 NumByteToRead)
{
       
        if(I2C_Start()) {
                printf("Start error!\r\n");
                return 1;
        }
       
        I2C_SendByte(0xB5);

        if(!I2C_Wait_Ack()) {
                printf("No Ack after send address!\r\n");
                return 2;
        }

        while(NumByteToRead--) {
                        *pBuffer++ = I2C_ReceiveByte();
                        if(NumByteToRead)
                                I2C_Ack(1);
                        else
                                I2C_Ack(0);       
        }
        return 0;
}

使用特权

评论回复
6
ustb_cc|  楼主 | 2013-3-7 15:27 | 只看该作者
本帖最后由 ustb_cc 于 2013-3-7 15:29 编辑

附上逻辑分析仪的时序:
C:\Users\Joe\Pictures\IAQengine.png

使用特权

评论回复
7
xinzhaodadi| | 2013-8-5 11:28 | 只看该作者
本帖最后由 xinzhaodadi 于 2013-8-5 11:31 编辑

按照IAQ 的时序来没问题的!上面有一点请大家注意,就是协议操作和读写PCF8563等有点不同,大家要仔细看。另外,如果协议读写错误破坏其内部协议,可能就麻烦了,大家用注意啊,呵呵

使用特权

评论回复
8
ARM_VvN| | 2013-9-2 19:41 | 只看该作者
我也遇到了这个问题,不知道楼主是否完成了。看帖子时间也不短了

使用特权

评论回复
9
jidafengyu| | 2013-12-18 20:41 | 只看该作者
ustb_cc 发表于 2013-1-22 13:13
IAQengine的手册3.3M,但是论坛限制附件大小1M,我发不上来。。。。。

求手册啊 !!!!!!

使用特权

评论回复
10
annacoming| | 2013-12-20 10:30 | 只看该作者
jidafengyu 发表于 2013-12-18 20:41
求手册啊 !!!!!!

您好!请把您的联系方式给我,我发手册给您。我的联系方式如下qq:572605982

使用特权

评论回复
11
xinnuojin0909| | 2014-2-19 17:53 | 只看该作者
我这儿有资料,是厂家,聊聊,谁要。

使用特权

评论回复
12
xinnuojin0909| | 2014-2-19 17:54 | 只看该作者
jidafengyu 发表于 2013-12-18 20:41
求手册啊 !!!!!!

我有IAQ-engine的资料,怎么给你,我是厂家,gaopt@sensors.com.cn  邮件我。或电话,13911654935  高先生

使用特权

评论回复
13
xinnuojin0909| | 2014-2-19 17:55 | 只看该作者
ARM_VvN 发表于 2013-9-2 19:41
我也遇到了这个问题,不知道楼主是否完成了。看帖子时间也不短了

我有IAQ-engine的资料,怎么给你,我是厂家,gaopt@sensors.com.cn  邮件我。或电话,13911654935  高先生

使用特权

评论回复
14
xinnuojin0909| | 2014-2-19 17:56 | 只看该作者
xinzhaodadi 发表于 2013-8-5 11:28
按照IAQ 的时序来没问题的!上面有一点请大家注意,就是协议操作和读写PCF8563等有点不同,大家要仔细看。 ...

我有IAQ-engine的资料,怎么给你,我是厂家,gaopt@sensors.com.cn  邮件我。或电话,13911654935  高先生

使用特权

评论回复
15
xinnuojin0909| | 2014-2-19 17:57 | 只看该作者
ustb_cc 发表于 2013-3-7 15:27
附上逻辑分析仪的时序:

我有IAQ-engine的资料,怎么给你,我是厂家,gaopt@sensors.com.cn  邮件我。或电话,13911654935  高先生

使用特权

评论回复
16
kong1025| | 2014-5-6 10:04 | 只看该作者
ustb_cc 发表于 2013-3-7 14:55
附上模拟I2C的代码:
/* Private macro -------------------------------------------------------------*/ ...

完整的代码有不 急用啊

使用特权

评论回复
17
zdxyydy| | 2014-8-27 21:41 | 只看该作者
本帖最后由 zdxyydy 于 2014-8-27 21:50 编辑

我也遇到问题了, iaq 有应答,可是后面读的数据感觉不对啊, status字节一直是0xff,求完整手册,感谢!!! Email: strawberry_xxx@163.com

使用特权

评论回复
18
asdy00000| | 2014-9-1 10:55 | 只看该作者
本帖最后由 asdy00000 于 2014-9-1 15:54 编辑
zdxyydy 发表于 2014-8-27 21:41
我也遇到问题了, iaq 有应答,可是后面读的数据感觉不对啊, status字节一直是0xff,求完整手册,感谢!!!  ...


应该是您的数据格式处理不对。

我调试的没有应答是怎么回事啊?
IIC_Start();                     
IIC_Send_Byte(0XB5);           
sign=IIC_Wait_Ack();
会不会是我的硬件有问题啊?STM32的PA6和PA7的I/O口不能耐压5V,那上拉电阻那应该怎么样连接?!

使用特权

评论回复
19
电子过客| | 2014-9-1 14:38 | 只看该作者
kong1025 发表于 2014-5-6 10:04
完整的代码有不 急用啊

你的IAQ 弄出来了吗 ,我刚上手没头绪

使用特权

评论回复
20
bear1| | 2014-9-1 14:44 | 只看该作者
这个问题st到现在还没有解决啊?

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

1

主题

5

帖子

0

粉丝