打印

GD32F330

[复制链接]
751|7
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
恩成|  楼主 | 2023-4-6 11:09 | 只看该作者 |只看大图 回帖奖励 |倒序浏览 |阅读模式
目前想在GD32F330的芯片上实现一个I2C从机发送功能。现在用正点原子的STM32开发板通过按键向GD32发送读取指令,GD32作为从机返回64位信息。
每次复位后,第一读取数据成功,用示波器抓取了电平变化,从机地址正常,数据段内容正常。
但是第二次按键后,只能读到从机地址以及读标志位,从机响应不了。
有人遇到过这样的问题吗。

使用特权

评论回复
沙发
恩成|  楼主 | 2023-4-6 11:35 | 只看该作者
这个是第一次传输的数据,地址正常,数据内容也没问题

83647642e3dcc559a2.jpg (449.76 KB )

83647642e3dcc559a2.jpg

使用特权

评论回复
板凳
恩成|  楼主 | 2023-4-6 11:36 | 只看该作者
第二次传输的时候,就这剩下地址了,GD32作为从机没有响应

使用特权

评论回复
地板
恩成|  楼主 | 2023-4-6 11:38 | 只看该作者
我用的是从机接收中断模式来进行从机数据传输的。
这是我的初始化函数:
void i2c0_config(void)
{
i2c_rcu_config1();
i2c_config1();
//i2c_nvic_config();
//i2c_interrupt();
}

void i2c_rcu_config1(void)
{
    rcu_periph_clock_enable(RCU_GPIOB);
    rcu_periph_clock_enable(RCU_I2C0);
}

void i2c_config1(void)
{
    gpio_af_set(GPIOB,GPIO_AF_1,GPIO_PIN_6);
        gpio_af_set(GPIOB,GPIO_AF_1,GPIO_PIN_7);
        gpio_mode_set(GPIOB, GPIO_MODE_AF, GPIO_PUPD_PULLUP,GPIO_PIN_6);
        gpio_output_options_set(GPIOB, GPIO_OTYPE_OD, GPIO_OSPEED_50MHZ,GPIO_PIN_6);
        gpio_mode_set(GPIOB, GPIO_MODE_AF, GPIO_PUPD_PULLUP,GPIO_PIN_7);
    gpio_output_options_set(GPIOB, GPIO_OTYPE_OD, GPIO_OSPEED_50MHZ,GPIO_PIN_7);
       
        i2c_clock_config(I2C0,100000,I2C_DTCY_2);
        i2c_mode_addr_config(I2C0,I2C_I2CMODE_ENABLE,I2C_ADDFORMAT_7BITS,slaveaddress1);
       
        nvic_priority_group_set(NVIC_PRIGROUP_PRE1_SUB3);
        i2c_enable(I2C0);
        i2c_ack_config(I2C0, I2C_ACK_ENABLE);
        nvic_irq_enable(I2C0_EV_IRQn, 0, 4);
    nvic_irq_enable(I2C0_ER_IRQn, 0, 1);
       
        i2c_interrupt_enable(I2C0, I2C_INT_ERR);
    i2c_interrupt_enable(I2C0, I2C_INT_EV);
    i2c_interrupt_enable(I2C0, I2C_INT_BUF);
       
}

使用特权

评论回复
5
恩成|  楼主 | 2023-4-6 11:39 | 只看该作者
这是我的接收中断函数,基本都是从官方的例程里找的。
void I2C0_EV_IRQHandler(void)
{       

         
    if(i2c_interrupt_flag_get(I2C0, I2C_INT_FLAG_ADDSEND))
        {
        /* clear the ADDSEND bit */
        i2c_interrupt_flag_clear(I2C0, I2C_INT_FLAG_ADDSEND);
        }

        else if((i2c_interrupt_flag_get(I2C0, I2C_INT_FLAG_TBE)) && (!i2c_interrupt_flag_get(I2C0, I2C_INT_FLAG_AERR)))
//        if(i2c_interrupt_flag_get(I2C0, I2C_INT_FLAG_TBE))
                {
                i2c_data_transmit(I2C0, testnum[3]);
                }
        else if(i2c_interrupt_flag_get(I2C0,I2C_INT_FLAG_STPDET))
        {
//        i=0;
        i2c_enable(I2C0);
////        i2ctrasmitable=1;
       
        }
        }
       

/*!
    \brief      this function handles I2C0 error interrupt request exception
*/

void I2C0_ER_IRQHandler(void)
{
  // i2c0_error_irq_handler();
    /* no acknowledge received */
    if(i2c_interrupt_flag_get(I2C0, I2C_INT_FLAG_AERR)) {
        i2c_interrupt_flag_clear(I2C0, I2C_INT_FLAG_AERR);
    }

    /* SMBus alert */
    if(i2c_interrupt_flag_get(I2C0, I2C_INT_FLAG_SMBALT)) {
        i2c_interrupt_flag_clear(I2C0, I2C_INT_FLAG_SMBALT);
    }

    /* bus timeout in SMBus mode */
    if(i2c_interrupt_flag_get(I2C0, I2C_INT_FLAG_SMBTO)) {
        i2c_interrupt_flag_clear(I2C0, I2C_INT_FLAG_SMBTO);
    }

    /* over-run or under-run when SCL stretch is disabled */
    if(i2c_interrupt_flag_get(I2C0, I2C_INT_FLAG_OUERR)) {
        i2c_interrupt_flag_clear(I2C0, I2C_INT_FLAG_OUERR);
    }

    /* arbitration lost */
    if(i2c_interrupt_flag_get(I2C0, I2C_INT_FLAG_LOSTARB)) {
        i2c_interrupt_flag_clear(I2C0, I2C_INT_FLAG_LOSTARB);
    }

    /* bus error */
    if(i2c_interrupt_flag_get(I2C0, I2C_INT_FLAG_BERR)) {
        i2c_interrupt_flag_clear(I2C0, I2C_INT_FLAG_BERR);
    }

    /* CRC value doesn't match */
    if(i2c_interrupt_flag_get(I2C0, I2C_INT_FLAG_PECERR)) {
        i2c_interrupt_flag_clear(I2C0, I2C_INT_FLAG_PECERR);
    }

    /* disable the I2C0 interrupt */
    i2c_interrupt_disable(I2C0, I2C_INT_ERR);
    i2c_interrupt_disable(I2C0, I2C_INT_BUF);
    i2c_interrupt_disable(I2C0, I2C_INT_EV);
}

使用特权

评论回复
6
恩成|  楼主 | 2023-4-6 11:40 | 只看该作者
有大佬遇到过这种问题吗,太难受了

使用特权

评论回复
7
恩成|  楼主 | 2023-4-6 17:20 | 只看该作者
大佬们来点建议吧

使用特权

评论回复
8
恩成|  楼主 | 2023-4-7 15:07 | 只看该作者
问题解决了,无语了,中断在清理外停止标志位后,会关闭I2C中断,所以要再开一次中断才行。

使用特权

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

本版积分规则

4

主题

24

帖子

0

粉丝