STM32实现printf输出到串口

文章介绍了如何在单片机中使用printf函数重定向输出到串口,以及如何通过DMA提升传输速度,同时探讨了DMA直接替换可能导致的问题和解决方法,提出了USART1_DMA_printf函数以兼顾效率和便利性。

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

背景

printf是学习C语言时常用的函数,可以将想要显示的数字、字符串等显示在屏幕上

但单片机没有屏幕,于是便希望将结果输出到串口

本文提供两种实现方案(传统的printf函数重定向和DMA实现printf)

printf函数重定向

printf的底层操作实际上就是使用fputc函数一个一个输出字符到屏幕上,所以我们只需要将fputc函数进行修改,使其功能变为通过串口输出一个字符即可实现printf的重定向

具体代码如下

int fputc(int ch,FILE *f)
{
	HAL_UART_Transmit(&huart1, (uint8_t *)&ch, 1, 0xffff);
	return ch;
}

随后在main函数里面调用printf函数即可,方法与C语言完全一致

DMA实现

DMA能够大大提升串口的传输速度,既然能够实现printf的重定向,能否和DMA结合,在调用方便的基础上,提高传输速度呢?

仿造printf重定向

如果简单地对上面的代码进行替换,改成下面这种形式

int fputc(int ch,FILE *f)
{
	HAL_UART_Transmit_DMA(&huart1,(uint8_t*)&ch,1);	  
	return ch;
}

这个时候如果你想使用这个新的printf输出“Hello world!”

那么你会发现串口只会一直输出H,串口助手接到的就会是HHHHH...

这是因为DMA传输的速度取决于串口发送的速度,在串口发送H的时候,后面的ello world!都会调用fputc函数,而这时DMA仍然在进行H的发送,所以导致最后只发送了一个H

如果在fputc函数里面加上一句延时,例如HAL_Delay(1),就又可以正常地进行工作

但是这和我们之前使用DMA的目的背道而驰,所以需要采用新的解决方案

构建新函数

构造如下函数,调用即可实现使用DMA输出到串口

void USART1_DMA_printf(const char *format,...)
{
	uint16_t len;
	va_list args;	
	va_start(args,format);
	len = vsnprintf((char*)UartTxBuf,sizeof(UartTxBuf)+1,(char*)format,args);
	va_end(args);
	HAL_UART_Transmit_DMA(&huart1, UartTxBuf, len);
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值