STM32串口编写流程

本文详细介绍了在STM32微控制器上进行串口初始化的步骤,包括时钟使能、GPIO配置、USART参数设置、中断配置以及中断优先级设定。还展示了如何编写串口初始化函数MY_USART_INIT(),并提供了串口接收中断服务函数USART1_IRQHandler()的实现,用于实现数据的收发和中断标志的清除。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

串口相关寄存器:
USART_SR 状态寄存器(里面的一些标志位类似51的TI,RI)
USART_DR 数据寄存器(类似SBUF)
USART_BRR 波特率寄存器(波特率寄存器,15:4位定义了USARTDIV的整数部分,3:0位定义了USARTDIV的小数部分)
波特率=fpclock(1,2)/(16*USARTDIV)
USART_CR1 设置一些发送或接收使能,以及一些中断使能
编写串口程序的步骤:
1.串口时钟使能,GPIO时钟使能,
使能串口对应的APB总线,以及GPIO对应的AHB总线
2.串口资源映射
3.设置GPIO端口模式 //GPIO_InitStruct
4.串口初始化, //USART_InitStruct
5.使能串口 //USART_Cmd其实就是配置CR1寄存器
6.配置中断 //设置串口的中断方式
7.设置中断优先级, //NVIC_InitStruct
在设置抢占优先级和子优先级之前需要先在主函数比较靠前的地方设置分组
8.写串口中断服务函数
9.串口传输状态获取USART_Flags 以及解挂(清除标志位)

void MY_USART_INIT()
{
	GPIO_InitTypeDef GPIO_InitStruct;
	USART_InitTypeDef USART_InitStruct;
	NVIC_InitTypeDef NVIC_InitStruct;
	
	//1.使能GPIOA和USART1
	RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA,ENABLE);
	RCC_APB2PeriphClockCmd (RCC_APB2Periph_USART1,ENABLE);
	
	//2.串口资源映射
	GPIO_PinAFConfig(GPIOA,GPIO_PinSource9,GPIO_AF_USART1); //GPIOA9复用为USART1
	GPIO_PinAFConfig(GPIOA,GPIO_PinSource10,GPIO_AF_USART1); //GPIOA10复用为USART1
	
	//3.GPIO端口模式设置,模式设置为复用
	GPIO_InitStruct.GPIO_Pin = GPIO_Pin_9 | GPIO_Pin_10;
	GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AF;
	GPIO_InitStruct.GPIO_OType = GPIO_OType_PP;
	GPIO_InitStruct.GPIO_PuPd = GPIO_PuPd_UP;
	GPIO_InitStruct.GPIO_Speed = GPIO_High_Speed;
	GPIO_Init (GPIOA,&GPIO_InitStruct);
	
	//4.串口参数初始化
	USART_InitStruct.USART_BaudRate = 115200;
	USART_InitStruct.USART_HardwareFlowControl=USART_HardwareFlowControl_None;
	USART_InitStruct.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; 
	USART_InitStruct.USART_Parity = USART_Parity_No;
	USART_InitStruct.USART_StopBits = USART_StopBits_1;
	USART_InitStruct.USART_WordLength = USART_WordLength_8b;	
	USART_Init(USART1,&USART_InitStruct);
	
	//5.使能串口
	USART_Cmd(USART1, ENABLE);
	
	//6.配置中断
	USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);//设置接收缓冲器非空中断
	
	//7.中断优先级的设置,设置之前要先在主函数比较靠前的位置设置分组
	NVIC_InitStruct.NVIC_IRQChannel= USART1_IRQn;
	NVIC_InitStruct.NVIC_IRQChannelCmd = ENABLE;
	NVIC_InitStruct.NVIC_IRQChannelPreemptionPriority = 1;	//抢占优先级
	NVIC_InitStruct.NVIC_IRQChannelSubPriority = 1;			//子优先级
	NVIC_Init(&NVIC_InitStruct);
		
	
}
//中断服务函数,没有入口参数,没有返回
void USART1_IRQHandler(void)
{
	u16 REC = 0;
	if(USART_GetITStatus(USART1, USART_IT_RXNE)==1)		//证明一下是缓冲器非空产生
	{	
		REC = USART_ReceiveData(USART1);
		USART_SendData(USART1,REC);
		while(USART_GetFlagStatus(USART1,USART_FLAG_TC)==0);//等待发送完成
	}
	USART_ClearITPendingBit(USART1,USART_IT_RXNE);
}
### STM32串口通信的设计步骤与流程 STM32串口通信功能基于其通用同步/异步收发器(USART),能够实现与其他设备的数据交换。以下是设计STM32串口通信的主要步骤以及对应的流程说明: #### 1. 配置系统时钟 在使用STM32的USART外设之前,需要先初始化系统的时钟源。通常情况下,会启用外部晶振并设置PLL来提供稳定的时钟频率[^1]。 ```c RCC_OscInitTypeDef RCC_OscInitStruct = {0}; RCC_ClkInitTypeDef RCC_ClkInitStruct = {0}; // 初始化时钟配置 RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSE; RCC_OscInitStruct.HSEState = RCC_HSE_ON; HAL_RCC_OscConfig(&RCC_OscInitStruct); // 设置系统时钟为72MHz RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_SYSCLK | RCC_CLOCKTYPE_PCLK1 | RCC_CLOCKTYPE_PCLK2; RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK; RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1; RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV2; RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1; HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_2); ``` #### 2. 配置GPIO引脚 为了使能USART的功能,需将相应的TX和RX引脚配置为复用模式,并设置合适的上下拉电阻[^2]。 ```c GPIO_InitTypeDef GPIO_InitStruct = {0}; __HAL_RCC_GPIOA_CLK_ENABLE(); // 启用GPIOA时钟 (假设USART1位于PA9/PA10) // TX Pin (PA9) GPIO_InitStruct.Pin = GPIO_PIN_9; GPIO_InitStruct.Mode = GPIO_MODE_AF_PP; // 复用推挽输出 GPIO_InitStruct.Pull = GPIO_NOPULL; GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_HIGH; GPIO_InitStruct.Alternate = GPIO_AF7_USART1; // USART1 Alternate Function HAL_GPIO_Init(GPIOA, &GPIO_InitStruct); // RX Pin (PA10) GPIO_InitStruct.Pin = GPIO_PIN_10; GPIO_InitStruct.Mode = GPIO_MODE_INPUT; // 输入模式 GPIO_InitStruct.Pull = GPIO_PULLUP; // 上拉输入 HAL_GPIO_Init(GPIOA, &GPIO_InitStruct); ``` #### 3. 初始化USART模块 通过调用`HAL_UART_Init()`函数完成USART硬件参数的设定,包括波特率、数据位数、停止位及校验方式等[^1]。 ```c UART_HandleTypeDef huart1; huart1.Instance = USART1; huart1.Init.BaudRate = 115200; // 波特率为115200bps huart1.Init.WordLength = UART_WORDLENGTH_8B; // 数据长度为8位 huart1.Init.StopBits = UART_STOPBITS_1; // 单停止位 huart1.Init.Parity = UART_PARITY_NONE; // 无奇偶校验 huart1.Init.Mode = UART_MODE_TX_RX; // 收发双向模式 huart1.Init.HwFlowCtl = UART_HWCONTROL_NONE; // 关闭硬件流控 if (HAL_UART_Init(&huart1) != HAL_OK) { Error_Handler(); } ``` #### 4. 编写发送接收逻辑 利用中断或者DMA机制可以提高程序效率,在此仅展示简单的轮询方法用于基础测试。 ```c uint8_t data_to_send[] = "Hello from STM32!"; HAL_UART_Transmit(&huart1, data_to_send, sizeof(data_to_send), HAL_MAX_DELAY); // 发送字符串 uint8_t received_data[20]; HAL_UART_Receive(&huart1, received_data, sizeof(received_data), HAL_MAX_DELAY); // 接收数据 ``` #### 5. 调试验证 借助虚拟终端软件观察实际传输效果,确认双方握手正常且未发生丢包现象[^3]。 --- ### 流程图概述 以下是一个简化版的STM32串口通信开发流程图描述: 1. **启动阶段**: 开启必要的电源与时钟资源。 2. **端口映射**: 定义哪些物理管脚对应于特定的USART实例。 3. **属性定义**: 明确帧格式的各项指标。 4. **驱动加载**: 将预编写的固件烧录至目标板卡。 5. **运行检验**: 进行初步连通性和功能性检测。 ![STM32 Serial Communication Flowchart](https://example.com/stm32_serial_flow.png) *(假想链接)* ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

___Crystal

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值