硬汉嵌入式论坛

 找回密码
 立即注册
查看: 971|回复: 5
收起左侧

[技术讨论] STM32G070 调用HAL_I2C_Mem_Read_IT测试疑问

[复制链接]

69

主题

172

回帖

379

积分

高级会员

积分
379
发表于 2024-12-3 10:58:51 | 显示全部楼层 |阅读模式
本帖最后由 lindahnu 于 2024-12-3 11:18 编辑

使用两个板子,在例程I2C_TwoBoards_RestartComIT代码上进行修改:
主机调用HAL_I2C_Mem_Read_IT函数,发送内存地址16位后读10个数据;
从机调用HAL_I2C_Slave_Seq_Receive_IT接收内存地址后再调用HAL_I2C_Slave_Seq_Transmit_IT发送10个数据;

现象:
从机正常接收,给主机发送第1个数据正常,到第2~10个数据时每次第八个时钟拉低了500多个ms才拉高,也就是延时了500多ms才回ack。不知道什么原因?

现在把HAL_I2C_Mem_Read_IT替换成查询模式HAL_I2C_Mem_Read,就没有以上时钟被拉低很久的现象。

这说明HAL_I2C_Mem_Read_IT函数封装哪里有问题?求指导

主机调用代码:
[C] 纯文本查看 复制代码
HAL_I2C_Mem_Read_IT(&hi2c1, (uint16_t)I2C_ADDRESS,, 0x55aa,2,(uint8_t *)aRxBuffer, 10);
替换
HAL_I2C_Mem_Read(&hi2c1, (uint16_t)I2C_ADDRESS,, 0x55aa,2,(uint8_t *)aRxBuffer, 10,1000);


从机调用代码:
[C] 纯文本查看 复制代码
if(HAL_I2C_EnableListen_IT(&hi2c1) != HAL_OK)
{
   Error_Handler();
}

while(uwTransferRequested != 1)
  {
  }

if(HAL_I2C_Slave_Seq_Receive_IT(&hi2c1, (uint8_t *)aRxBuffer, 2, I2C_FIRST_FRAME) != HAL_OK)
{
   Error_Handler();
}

while (HAL_I2C_GetState(&hi2c1) != HAL_I2C_STATE_LISTEN)
{
}

while(uwTransferRequested != 1)
  {
  }

if(HAL_I2C_Slave_Seq_Transmit_IT(&hi2c1, (uint8_t*)aTxBuffer, 10, I2C_LAST_FRAME)!= HAL_OK)
{
   Error_Handler(); 
}

while (HAL_I2C_GetState(&hi2c1) != HAL_I2C_STATE_READY)
{
}


从机回调函数:
[C] 纯文本查看 复制代码
void HAL_I2C_AddrCallback(I2C_HandleTypeDef *hi2c,uint8_t TransferDirection, uint16_t AddrMatchCode)
{
   uwTransferRequested  = 1;
}

void HAL_I2C_SlaveRxCpltCallback(I2C_HandleTypeDef *I2cHandle)
{
   uwTransferRequested =0;
}

void HAL_I2C_SlaveTxCpltCallback(I2C_HandleTypeDef *I2cHandle)
{
   uwTransferRequested =0;
}




回复

使用道具 举报

1万

主题

7万

回帖

11万

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
116226
QQ
发表于 2024-12-3 11:22:36 | 显示全部楼层
官方的例子一直是采用的OD开漏,外置上拉,楼主的是什么方式
回复

使用道具 举报

69

主题

172

回帖

379

积分

高级会员

积分
379
 楼主| 发表于 2024-12-3 12:02:14 | 显示全部楼层
eric2013 发表于 2024-12-3 11:22
官方的例子一直是采用的OD开漏,外置上拉,楼主的是什么方式

[C] 纯文本查看 复制代码
GPIO_InitStruct.Pin = GPIO_PIN_6|GPIO_PIN_7;
GPIO_InitStruct.Mode = GPIO_MODE_AF_OD;
GPIO_InitStruct.Pull = GPIO_PULLUP;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
GPIO_InitStruct.Alternate = GPIO_AF6_I2C1;
HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);
    


回复

使用道具 举报

69

主题

172

回帖

379

积分

高级会员

积分
379
 楼主| 发表于 2024-12-3 13:21:11 | 显示全部楼层
eric2013 发表于 2024-12-3 11:22
官方的例子一直是采用的OD开漏,外置上拉,楼主的是什么方式

使用HAL_I2C_Mem_Read查询模式是没有问题的,一用中断就会出现时钟被拉低的现象
回复

使用道具 举报

69

主题

172

回帖

379

积分

高级会员

积分
379
 楼主| 发表于 2024-12-3 16:28:18 | 显示全部楼层
本帖最后由 lindahnu 于 2024-12-3 16:38 编辑

已经找到原因,对比更新最新的G0代码时漏了开接收中断。
HAL_I2C_Mem_Read_IT函数最后调用I2C_Enable_IRQ(hi2c, I2C_XFER_TX_IT);
在I2C_Mem_ISR_IT里检测TC标志的地方需调用I2C_Disable_IRQ(hi2c, I2C_XFER_TX_IT);I2C_Enable_IRQ(hi2c, I2C_XFER_RX_IT);

主机没开接收中断,没有读RXDR就会拉低时钟线
回复

使用道具 举报

1万

主题

7万

回帖

11万

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
116226
QQ
发表于 2024-12-4 09:38:24 | 显示全部楼层
lindahnu 发表于 2024-12-3 16:28
已经找到原因,对比更新最新的G0代码时漏了开接收中断。
HAL_I2C_Mem_Read_IT函数最后调用I2C_Enable_IRQ( ...

谢谢告知最终原因。
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|小黑屋|Archiver|手机版|硬汉嵌入式论坛

GMT+8, 2025-6-10 15:45 , Processed in 0.588382 second(s), 24 queries .

Powered by Discuz! X3.4 Licensed

Copyright © 2001-2023, Tencent Cloud.

快速回复 返回顶部 返回列表