在STM32F103上实现USART通信

STM32F103是一款经典的32位ARM Cortex-M3微控制器,以其高性能、低功耗和丰富的外设资源广泛应用于各种嵌入式系统中。下面我将详细介绍如何在STM32F103上使用USART接口进行串口通信,帮助你更好地理解STM32的串口配置和数据传输过程。

一、STM32F103的USART接口概述

STM32F103系列微控制器集成了多个USART接口(如USART1、USART2、USART3等),这些接口支持全双工串行通信,能够以异步方式发送和接收数据。UART接口广泛应用于微控制器与外部设备(如传感器、显示器、PC等)之间的通信。

二、USART接口的硬件连接

在STM32F103上,每个UART接口都有固定的引脚用于发送(TX)和接收(RX)数据。例如:
USART1:TX引脚为PA9,RX引脚为PA10。
USART2:TX引脚为PA2,RX引脚为PA3。
USART3:TX引脚为PB10,RX引脚为PB11。
在硬件连接时,需要将这些引脚连接到目标设备的对应串口引脚上,并确保电源和地线连接正确。
在这里插入图片描述

三、串口配置

1. 启用时钟

在STM32中,UART接口需要时钟支持,GPIO模块需要时钟信号来驱动其内部逻辑电路。

RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
2. GPIO引脚配置

配置USART1的TX(PA9)和RX(PA10)引脚。

GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, &GPIO_InitStructure);

GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;
GPIO_Init(GPIOA, &GPIO_InitStructure);
3. USART1配置

初始化USART1,设置其通信参数。

USART_InitTypeDef USART_InitStructure;
USART_InitStructure.USART_BaudRate = 9600;
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
USART_InitStructure.USART_Mode = USART_Mode_Tx | USART_Mode_Rx;
USART_InitStructure.USART_Parity = USART_Parity_No;
USART_InitStructure.USART_StopBits = USART_StopBits_1;
USART_InitStructure.USART_WordLength = USART_WordLength_8b;
USART_Init(USART1, &USART_InitStructure);

参数:

  1. 波特率(Baud Rate)
    含义:数据传输速率。
    常见值:9600、19200、38400、115200。
  2. 字长(Word Length)
    含义:每次传输的数据位数。
    常见值:8位(USART_WordLength_8b)、9位(USART_WordLength_9b)。
  3. 停止位(Stop Bits)
    含义:数据帧结束的标记。
    常见值:1位(USART_StopBits_1)、2位(USART_StopBits_2)。
  4. 校验位(Parity)
    含义:用于数据校验。
    常见值:无校验(USART_Parity_No)、奇校验(USART_Parity_Odd)、偶校验(USART_Parity_Even)。
  5. 硬件流控制(Flow Control)
    含义:控制数据传输的速率。
    常见值:无(USART_HardwareFlowControl_None)、RTS/CTS(USART_HardwareFlowControl_RTS_CTS)。
  6. 工作模式(Mode)
    含义:定义USART的工作模式。
    常见值:发送(USART_Mode_Tx)、接收(USART_Mode_Rx)。
4. 启用USART1

通过USART_Cmd函数将USART1的使能位设置为1,使USART1开始工作。

USART_Cmd(USART1, ENABLE);
5. 发送数据

发送数据时,将数据写入USART数据寄存器

void Serial_SendByte(uint8_t Byte)
{
	USART_SendData(USART1, Byte);
	while (USART_GetFlagStatus(USART1, USART_FLAG_TXE) == RESET);//需要判断TXE标志位的状态。0,数据还没有被转移到移位寄存器;1,数据已经被转移到移位寄存器。当TXE标志位为1时,就说明可以发送下一个数据了
}

在这里插入图片描述

6. 接收数据(两种方式)
  1. 查询方式就是通过不断的查询RXNE标志位,通过判断RXNE位的状态来确定数据是否接收。配置串口RX引脚,在串口模式中添加USART_Mode_RX模式,上面已经完成
uint8_t USART_ReceiveByte(void)
{
    while(USART_GetFlagStatus(USART1, USART_FLAG_RXNE) == RESET); // 等待RXNE标志位置1
    return (uint8_t)USART_ReceiveData(USART1); // 读取数据并返回
}
  1. 中断方式就是通过配置接收输出控制通道,配置NVIC,在中断服务子函数里进行数据的接收

启用RXNE中断:

USART_ITConfig(USART1, USART_IT_RXNE, ENABLE); // 启用RXNE中断

配置NVIC中断优先级:

NVIC_InitTypeDef NVIC_InitStructure;
NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn; // 选择USART1中断
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1; // 抢占优先级
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1; // 子优先级
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; // 使能中断
NVIC_Init(&NVIC_InitStructure);

中断服务函数(接收数据并重新将数据发送到pc端显示)

void USART1_IRQHandler(void)
{
    if(USART_GetITStatus(USART1, USART_IT_RXNE) != RESET) // 检查RXNE中断标志位
    {
        uint8_t Data = USART_ReceiveData(USART1); // 读取数据寄存器

        // 将接收到的数据重新发送回去(回显)
        while(USART_GetFlagStatus(USART1, USART_FLAG_TXE) == RESET); // 等待发送缓冲区为空
        USART_SendData(USART1, Data); // 发送数据

        USART_ClearITPendingBit(USART1, USART_IT_RXNE); // 清除中断标志位
    }
}

在这里插入图片描述

四、总结

通过上述步骤,你可以在STM32F103上实现USART串口通信。USART接口的灵活性和易用性使其成为嵌入式系统中常用的通信方式之一。掌握USART的配置和使用,将为你的嵌入式项目开发提供强大的支持。

Logo

openvela 操作系统专为 AIoT 领域量身定制,以轻量化、标准兼容、安全性和高度可扩展性为核心特点。openvela 以其卓越的技术优势,已成为众多物联网设备和 AI 硬件的技术首选,涵盖了智能手表、运动手环、智能音箱、耳机、智能家居设备以及机器人等多个领域。

更多推荐