串口在工作中经常用到,今天我们从零开始学习stm32的串口编程(利用库函数)。
先从最简单的情况开始,假设我们要实现的功能就是串口发送一个字节,不考虑接收,也不考虑中断。
那么要解决两个问题:
1 串口的初始化
2 发送一个字节
对于1,我们看看代码。
<span style="font-size:18px;">//bound 表示波特率
void uart_init(u32 bound)
{
GPIO_InitTypeDef GPIO_InitStructure;
USART_InitTypeDef USART_InitStructure;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1|RCC_APB2Periph_GPIOA, ENABLE);
//使能USART1和GPIOA的时钟
//USART1_TX PA.9
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9; //PA.9
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; //推挽输出
GPIO_Init(GPIOA, &GPIO_InitStructure); //初始化PA9
//USART1_RX PA.10
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;//浮空输入
GPIO_Init(GPIOA, &GPIO_InitStructure); //初始化PA10
//USART 的设置
USART_DeInit(USART1); //复位串口1
USART_InitStructure.USART_BaudRate = bound;//波特率
USART_InitStructure.USART_WordLength = USART_WordLength_8b;//字长为8位
USART_InitStructure.USART_StopBits = USART_StopBits_1;//1位停止位
USART_InitStructure.USART_Parity = USART_Parity_No;//无奇偶校验
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
//无硬件流控
USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; //收发模式
USART_Init(USART1, &USART_InitStructure);
USART_Cmd(USART1, ENABLE); //串口使能
}</span>
这样就完成了基本设置。
对于2,我们用下面的代码,假如发送的字节是0x20,
<span style="font-size:18px;">USART_SendData(USART1, 0x20);//发送数据0x20
while(USART_GetFlagStatus(USART1,USART_FLAG_TC)!=SET);//等待发射结束</span>
这样就实现了最基本的发送功能。
现在引出这样一个问题,怎样使用Printf函数往串口发送数据?其实解决方法有很多,这里给出一种方法(也是参考网上的)
我们只需要添加这样一段代码:
<span style="font-size:18px;">#pragma import(__use_no_semihosting)
struct __FILE
{
int handle;
};
FILE __stdout;
//定义_sys_exit()以避免使用半主机模式
_sys_exit(int x)
{
x = x;
}
//重定义fputc()函数
int fputc(int ch, FILE *f)
{
while(USART_GetFlagStatus(USART1,USART_FLAG_TC)==RESET);
USART_SendData(USART1,(uint8_t)ch);
return ch;
}</span>
为什么要这样写,具体原因我先不管,先把问题提出来:
1.为什么这样写,每一条语句都是什么意思?
2.printf()函数的定义在哪里?(我在Keil中没有找到)如果没有定义,是不是已经由IDE做成了库,那么库文件在哪里?对于没有操作系统的裸板开发,用户调用的“标准C库”是从哪里来的?是开发环境自带的吗?
main函数如下:
<span style="font-size:18px;">int main(void)
{
u8 i = 0;
delay_init(); //延时函数初始化
uart_init(9600); //串口初始化,波特率9600
while(1)
{
delay_ms(500);
printf("我是好学生 %d\r\n\r\n",i);
++i;
}
}</span>
测试结果如图: