STM32F4 hal I2C 中断主机
时间: 2024-12-31 21:15:52 浏览: 16
### STM32F4 HAL I2C 中断主机通信
对于STM32F4系列微控制器,在使用HAL库进行I2C中断方式下的主机通信时,主要涉及初始化设置、发送请求以及处理接收到的数据。下面提供一段完整的示例代码来展示如何利用HAL库完成这些操作。
#### 初始化配置
首先需要通过STM32CubeMX工具生成基础项目框架并开启相应的外设资源,确保已经启用了I2C接口及其对应的GPIO引脚功能,并选择了中断模式作为传输机制[^1]。
```c
// 在stm32f4xx_hal_msp.c 文件中添加如下函数用于初始化和释放I2C GPIO 资源
void HAL_I2C_MspInit(I2C_HandleTypeDef* hi2c){
/* USER CODE BEGIN I2C1_MspInit 0 */
/* USER CODE END I2C1_MspInit 0 */
__HAL_RCC_GPIOB_CLK_ENABLE();
/**I2C1 GPIO Configuration
PB6 ------> I2C1_SCL
PB7 ------> I2C1_SDA
*/
GPIO_InitStruct.Pin = GPIO_PIN_6|GPIO_PIN_7;
GPIO_InitStruct.Mode = GPIO_MODE_AF_OD;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_VERY_HIGH;
GPIO_InitStruct.Alternate = GPIO_AF4_I2C1;
HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);
/* Peripheral clock enable */
__HAL_RCC_I2C1_CLK_ENABLE();
/* I2C1 interrupt Init */
HAL_NVIC_SetPriority(I2C1_EV_IRQn, 5, 0);
HAL_NVIC_EnableIRQ(I2C1_EV_IRQn);
}
void HAL_I2C_MspDeInit(I2C_HandleTypeDef* hi2c){
if(hi2c->Instance==I2C1){
/* USER CODE BEGIN I2C1_MspDeInit 0 */
/* USER CODE END I2C1_MspDeInit 0 */
/* Peripheral clock disable */
__HAL_RCC_I2C1_CLK_DISABLE();
/**I2C1 GPIO Configuration
PB6 ------> I2C1_SCL
PB7 ------> I2C1_SDA
*/
HAL_GPIO_DeInit(GPIOB, GPIO_PIN_6|GPIO_PIN_7);
/* I2C1 interrupt Deinit */
HAL_NVIC_DisableIRQ(I2C1_EV_IRQn);
}
}
```
#### 发送与接收数据
接着是在主程序里编写具体的收发逻辑:
```c
#include "main.h"
#define SLAVE_ADDRESS 0x68 // 设备地址,比如 MPU6050 的默认地址为 0x68
uint8_t txBuffer[] = {0x00}; // 发送给从设备的命令字节或其他数据
uint8_t rxBuffer[1]; // 接受来自从设备返回的一个字节的结果
/* 定义全局变量存储状态信息 */
volatile uint8_t transferCompleteFlag = RESET;
int main(void)
{
/* Reset of all peripherals, Initializes the Flash interface and Systick. */
HAL_Init();
SystemClock_Config(); // 配置系统时钟
MX_GPIO_Init(); // 初始化GPIO
MX_I2C1_Init(); // 初始化I2C
while (transferCompleteFlag != SET) {
// 主循环等待直到一次完整的事务结束
}
// 这里可以加入更多业务逻辑...
}
/**
* @brief Master Transmits data to Slave then receives a byte from it.
* @param None
* @retval None
*/
static void StartCommunication(void)
{
/* 清除标志位准备下一轮通讯 */
transferCompleteFlag = RESET;
/* 启动写入过程向指定地址写入txBuffer中的内容 */
HAL_StatusTypeDef status = HAL_I2C_Master_Transmit_IT(&hi2c1, SLAVE_ADDRESS << 1, txBuffer, sizeof(txBuffer));
if(status != HAL_OK){
Error_Handler(__FILE__, __LINE__);
}else{
/* 如果成功启动,则继续监听事件以获取响应 */
while(transferCompleteFlag == RESET){};
/* 成功完成后再次清除标志位以便下次使用 */
transferCompleteFlag = RESET;
/* 开始读取一个字节的数据 */
status = HAL_I2C_Master_Receive_IT(&hi2c1, SLAVE_ADDRESS << 1, rxBuffer, sizeof(rxBuffer));
if(status != HAL_OK){
Error_Handler(__FILE__, __LINE__);
}else{
/* 继续监听事件直至读取完毕 */
while(transferCompleteFlag == RESET){}
/* 打印接收到的内容 */
printf("Received Data: %X\n",rxBuffer[0]);
}
}
}
/* 当每次完成一次成功的传输后会触发此回调函数 */
void HAL_I2C_MasterTxCpltCallback(I2C_HandleTypeDef *hi2c)
{
if(hi2c->Instance == I2C1){
transferCompleteFlag = SET;
}
}
/* 当每次完成一次成功的接收后也会触发这个回调函数 */
void HAL_I2C_MasterRxCpltCallback(I2C📐⚗
⚗⚗
阅读全文