|
.h中的声明:
#include <stdio.h>
#include <stdarg.h>
int my_printf_1(const char *fmt, ...) __attribute__ ((format (printf,1,2)));// 按 printf 函数的格式
int my_printf_x(UART_HandleTypeDef *huart,const char *fmt, ...) __attribute__ ((format (printf, 2,3)));// 按 printf 函数的格式
.c中的实现:
static char printf_buff[256];
int my_printf_1(const char *fmt, ...)
{
int length;
va_list ap;
va_start(ap, fmt);//将ap初始化为变参数栈的栈顶指针
length=vsnprintf((char *)printf_buff,sizeof(printf_buff), fmt, ap);//将指针ap传递给vsprintf做格式化处理
va_end(ap);
HAL_UART_Transmit(&huart1, (uint8_t *)printf_buff, length, 0xffff);
return 0;
}
int my_printf_x(UART_HandleTypeDef *huart,const char *fmt, ...)
{
int length;
va_list ap;
va_start(ap, fmt);//将ap初始化为变参数栈的栈顶指针
length=vsnprintf((char *)printf_buff,sizeof(printf_buff), fmt, ap);//将指针ap传递给vsprintf做格式化处理
va_end(ap);
HAL_UART_Transmit(huart, (uint8_t *)printf_buff, length, 0xffff);
return 0;
}
说明:
1.头文件中有__attribute__((format(printf, a, b)))这种写法,默认情况下编译器检查不出可变参数的类型或者个数是否正确,这就导致使用变参函数的时候,若稍不注意写错了参数,很难被发现和定位,__attribute__((format(printf, a, b)))的作用就是用来解决这个问题,它用于函数声明,作用是提示编译器检查函数调用的过程中,可变参数部分按照printf的规则进行检查,若参数的个数或者类型不匹配,编译过程中将会发出警告,这就使得前面提到的问题在编译期间就能发现。
2.函数my_printf_1() 固定使用串口1,函数my_printf_x() 则通过传参任意指定串口,大家根据需要 两个函数 任选其一即可;
|
|