思路
(1)引腳配置–PA9 (Tx) ----PA10 (Rx)
(2)串口配置 (數據協議:起始位–數據位–奇偶校驗–停止位; 波特率)
(3)查看功能是否正常----回顯函數 將下位機接收的數據發送到上位機(串口助手)顯示
寄存器
//引腳配置 串口配置
void usart_config(u32 baud)//形參爲波特率
{
u32 div_m,div_f;//div_m--USARTDIV的整數部分 ---div_f 是小數部分
float usart_div;// USARTDIV是什麼? 這是波特率配置重點,我的筆記上次已經講過
RCC->APB2ENR |=(0X01<<2)|(0X01<<14);//開時鐘 GPIOA USART1
//PA9--¸查看原理圖 與英文數據手冊 該管腳複用功能爲USART1_Tx 故 應該配置 複用推輓輸出 模式
GPIOA->CRH &=~(0X0F<<4);
GPIOA->CRH |=(0X0B<<4);
//PA10--浮空或上拉輸入模式
GPIOA->CRH &=~(0X0F<<8);
GPIOA->CRH |=(0X04<<8);
//串口配置
//配置字長--該位爲0,則一個起始位,8個數據位 ;;該位爲1,則一個起始位,9個數據位
USART1->CR1 &=~(0x01<<12);
//配置爲0 不使用奇偶校驗
USART1->CR1 &=~(0x01<<10);
//使能串口的發送與接收
USART1->CR1 |=(0x01<<3)|(0x01<<2);
//配置停止位 00:1個停止位;; 01:0.5個停止位;; 10:2個停止位;; 11:1.5個停止位;
USART1->CR2 &=~(0x03<<12);
//波特率配置
usart_div=72000000.0/(16*baud);
//整數部分
div_m=(u32)usart_div;
//小數部分
div_f=(u32)((usart_div-div_m)*16);
//USART_BRR寄存器 0-3 存儲USARTDIV 的小數部分 4-15保存USARTDIV的整數部分
USART1->BRR =div_m<<4|div_f;
//最重要是一步 配置完成一定要使能USART
USART1->CR1 |=(0x01<<13);
}
//回顯函數
void echo_usart(void)
{
u8 data;
//USART的狀態寄存器 等待接收數據
while((USART1->SR &(0x01<<5))==0);
//如果收到數據 就把數據賦值給data變量
//USART_DR 數據寄存器 保存發送或接受的數據
data=USART1->DR;
//等待數據轉移到移位寄存器
while((USART1->SR &(0x01<<7))==0);
//將之前接收的數據放入寄存器等待發出
USART1->DR=data;
}
//打印函數 將數據顯示到上位機(串助手上)
int fputc(int c, FILE * stream)
{
while(((USART1->SR) &(0x01<<7))==0);
USART1->DR=(u8)c;
return c;
}
庫函數
void usart_init (void)
{
//定義結構體
GPIO_InitTypeDef GPIO_InitStructure;
USART_InitTypeDef USART_InitStructure;
//開時鐘
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE);
//GPIO配置 PA9 複用推輓
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
//初始化
GPIO_Init(GPIOA, &GPIO_InitStructure);
//GPIO配置 PA10 寄存器版是浮空輸入 這裏配置上拉輸入模式 效果都一樣
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;
//初始化
GPIO_Init(GPIOA, &GPIO_InitStructure);
//串口配置
USART_InitStructure.USART_BaudRate = 9600;//波特率
USART_InitStructure.USART_WordLength = USART_WordLength_8b;//8字節
USART_InitStructure.USART_Parity = USART_Parity_No;//不使用奇偶校驗
USART_InitStructure.USART_StopBits = USART_StopBits_1;//停止位
USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;//輸入輸出使能
//初始化
USART_Init(USART1, &USART_InitStructure);
//使能USART1
USART_Cmd(USART1, ENABLE);//ʹÄÜ
}
//回顯函數
void echo_usart(void)
{
u8 val=0xff;
// 檢查指定的USART標誌 USART_FLAG_RXNE :接收數據寄存器不爲空標誌
while(USART_GetFlagStatus(USART1,USART_FLAG_RXNE)==RESET);
//將數據傳給val
val=USART_ReceiveData(USART1);
//將收到是數據發出
USART_SendData(USART1,val);
}
//打印函數
int fputc(int ch, FILE *f)
{
// 檢查指定的USART標誌 USART_FLAG_RXNE :接收數據寄存器不爲空標誌
while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET);
USART_SendData(USART1, (uint8_t) ch);
return ch;
}
結果顯示 123456爲主函數 printf輸出 666爲 串口回顯