第一章 串口硬件引腳分析
STM32F407 的串口資源非常豐富,功能也很強勁。 STM32F407 最多可提供 6 路串口,有分數波特率發生器、支持同步單線通信和半雙工單線通訊、支持 LIN、 支持調制解調器操作、 智能卡協議和 IrDA SIR ENDEC 規范、具有 DMA收發功能等,具體詳細信息可以查看官方的數據手冊。
第二章 串口復用引腳介紹
串口寄存器介紹在手冊第26章
GPIO口復用功能引腳配置
F407串口對應的引腳
配置復用功能的寄存器
串口時鐘頻率配置分析
第三章 串口1配置示例
Usart.c代碼示例:
#include "usart.h"
/*
函數功能:串口1初始化
函數形參:
u32 clock :時鐘頻率(默認*1000000HZ) 注意:APB1最大時鐘頻率為42MHZ APB2最大時鐘頻率為84MHZ
u32 baud :波特率
硬件連接:
PA9--->TX
PA10-->RX
*/
void USART1_Init(u32 clock,u32 baud)
{
/*1. 開時鐘*/
RCC->AHB1ENR|=1<<0; //使能PORTA時鐘
RCC->APB2ENR|=1<<4; //使能USART1時鐘
/*2. 復位串口時鐘*/
RCC->APB2RSTR|=1<<4; //使能USART1復位時鐘
RCC->APB2RSTR&=~(1<<4); //關閉USART1復位時鐘
/*3. 配置GPIO口模式*/
GPIOA->MODER&=~(0x3<<9*2); //清除模式
GPIOA->MODER|=0x2<<9*2; //配置復用功能模式
GPIOA->MODER&=~(0x3<<10*2); //清除模式
GPIOA->MODER|=0x2<<10*2; //配置復用功能模式
GPIOA->OTYPER&=~(0x1<<9); //0表示推挽輸出
GPIOA->OSPEEDR&=~(0x3<<9*2); //清除之前配置
GPIOA->OSPEEDR|=0x2<<9*2; //50MHZ輸出速度
GPIOA->PUPDR&=~(0x3<<10*2); //清除之前配置
GPIOA->PUPDR|=0x1<<10*2; //配置上拉
GPIOA->AFR[1]&=~(0xF<<4*1); //清除PA9配置
GPIOA->AFR[1]|=0x7<<4*1; //配置PA9復用功能模式為串口1
GPIOA->AFR[1]&=~(0xF<<4*2); //清除PA10配置
GPIOA->AFR[1]|=0x7<<4*2; //配置PA10復用功能模式為串口1
/*4. 配置USART-CR寄存器*/
USART1->BRR=(clock*1000000)/baud;//配置波特率
USART1->CR1|=1<<3; //使能發送
USART1->CR1|=1<<2; //使能接收,并開始搜尋RX引腳上的起始位
USART1->CR1|=1<<13; //USART模塊使能。
}
/*
函數功能:串口字符串發送
函數形參:
USART_TypeDef *USARTx :串口的類型 (USART1 USART2 USART3)
u8 *str:將要發送的字符串
*/
void USARTxSendString(USART_TypeDef *USARTx,u8 *str)
{
while(*str!='?')
{
USARTx->DR=*str;
while(!(USARTx->SR&1<<7)){} //等待發送完成
str++;
}
}
復制代碼
Usart.h代碼示例
#ifndef USART_H
#define USART_H
#include "stm32f4xx.h"
void USART1_Init(u32 clock,u32 baud);
void USARTxSendString(USART_TypeDef *USARTx,u8 *str);
#endif
復制代碼
Main.c代碼示例
#include "stm32f4xx.h" // Device header
#include "led.h"
#include "delay.h"
#include "key.h"
#include "usart.h"
//////////////////////////////////////////////////////////////////////////////////
int main(void)
{
u8 key,i,c;
LED_Init();
KEY_Init();
USART1_Init(84,115200);
while(1)
{
key=ScanKeyVal(0);
if(key)
{
i=!i;
LED0(i);
LED1(i);
USARTxSendString(USART1,"嵌入式開發!rn");
}
if(USART1->SR&1<<5) //接收到數據
{
c=USART1->DR;
USART1->DR=c; //將接收到的數據原路返回
}
}
}
復制代碼
第四章 串口標準輸入輸出重定向
Usart.c文件增加代碼:
/*
函數功能:重寫printf底層函數接口
*/
int fputc(int c,FILE *stream)
{
USART1->DR=c; //發送一個字符
while(!(USART1->SR&1<<7)){}
return c;
}
/*
函數功能:重新scanf底層函數接口
*/
int fgetc(FILE *stream)
{
while(!(USART1->SR&1<<5)){}
return USART1->DR;
}
復制代碼
Main.c代碼示例
#include "stm32f4xx.h" // Device header
#include "led.h"
#include "delay.h"
#include "key.h"
#include "usart.h"
int main(void)
{
u8 i;
u8 buff[100];
LED_Init();
KEY_Init();
USART1_Init(84,115200);
while(1)
{
i=!i;
LED0(i);
LED1(i);
printf(" STM32F407串口測試!rn");
printf("請輸入數據按回車鍵結束: (串口軟件需要勾選發送新行)rn");
scanf("%s",buff);
printf("你輸入的數據為:%srnrnrn",buff);
}
}
復制代碼
第五章 配置串口中斷接收
第一步需要先編寫設置中斷優先級的函數:
sys.c代碼示例
#include "sys.h"
/*
函數功能:設置NVIC中斷控制器優先級
函數形參:
IRQn_Type IRQn:中斷線
uint32_t PreemptPriority:搶占優先級
uint32_t SubPriority:次優先級
*/
void SetNVICPriorityGrouping(IRQn_Type IRQn,uint32_t PreemptPriority, uint32_t SubPriority)
{
uint32_t Priority;
NVIC_SetPriorityGrouping(NVIC_PriorityGroup_2); //設置優先級分組,每個工程只能設置一次
Priority=NVIC_EncodePriority(NVIC_PriorityGroup_2,PreemptPriority,SubPriority); //編碼優先級
NVIC_SetPriority(IRQn,Priority); //設置優先級
NVIC_EnableIRQ(IRQn);
}
復制代碼
Sys.h文件代碼示例:
#ifndef _SYS_H
#define _SYS_H
#include "stm32f4xx.h"
/*中斷控制器分組*/
#define NVIC_PriorityGroup_0 ((uint32_t)0x700) /*!< 0 bits for pre-emption priority
4 bits for subpriority */
#define NVIC_PriorityGroup_1 ((uint32_t)0x600) /*!< 1 bits for pre-emption priority
3 bits for subpriority */
#define NVIC_PriorityGroup_2 ((uint32_t)0x500) /*!< 2 bits for pre-emption priority
2 bits for subpriority */
#define NVIC_PriorityGroup_3 ((uint32_t)0x400) /*!< 3 bits for pre-emption priority
1 bits for subpriority */
#define NVIC_PriorityGroup_4 ((uint32_t)0x300) /*!< 4 bits for pre-emption priority
0 bits for subpriority */
void SetNVICPriorityGrouping(IRQn_Type IRQn,uint32_t PreemptPriority, uint32_t SubPriority);
#endif
復制代碼
Usart.c文件示例
#include "usart.h"
/*
函數功能:串口1初始化
函數形參:
u32 clock :時鐘頻率(默認*1000000HZ) 注意:APB1最大時鐘頻率為42MHZ APB2最大時鐘頻率為84MHZ
u32 baud :波特率
硬件連接:
PA9--->TX
PA10-->RX
*/
void USART1_Init(u32 clock,u32 baud)
{
/*1. 開時鐘*/
RCC->AHB1ENR|=1<<0; //使能PORTA時鐘
RCC->APB2ENR|=1<<4; //使能USART1時鐘
/*2. 復位串口時鐘*/
RCC->APB2RSTR|=1<<4; //使能USART1復位時鐘
RCC->APB2RSTR&=~(1<<4); //關閉USART1復位時鐘
/*3. 配置GPIO口模式*/
GPIOA->MODER&=~(0x3<<9*2); //清除模式
GPIOA->MODER|=0x2<<9*2; //配置復用功能模式
GPIOA->MODER&=~(0x3<<10*2); //清除模式
GPIOA->MODER|=0x2<<10*2; //配置復用功能模式
GPIOA->OTYPER&=~(0x1<<9); //0表示推挽輸出
GPIOA->OSPEEDR&=~(0x3<<9*2); //清除之前配置
GPIOA->OSPEEDR|=0x2<<9*2; //50MHZ輸出速度
GPIOA->PUPDR&=~(0x3<<10*2); //清除之前配置
GPIOA->PUPDR|=0x1<<10*2; //配置上拉
GPIOA->AFR[1]&=~(0xF<<4*1); //清除PA9配置
GPIOA->AFR[1]|=0x7<<4*1; //配置PA9復用功能模式為串口1
GPIOA->AFR[1]&=~(0xF<<4*2); //清除PA10配置
GPIOA->AFR[1]|=0x7<<4*2; //配置PA10復用功能模式為串口1
/*4. 配置USART-CR寄存器*/
USART1->BRR=(clock*1000000)/baud;//配置波特率
USART1->CR1|=1<<3; //使能發送
#ifdef USART1_INTERRUPT
USART1->CR1|=1<<5; //開啟串口接收中斷
SetNVICPriorityGrouping(USART1_IRQn,1,3); //設置中斷優先級
#endif
USART1->CR1|=1<<2; //使能接收,并開始搜尋RX引腳上的起始位
USART1->CR1|=1<<13; //USART模塊使能。
}
/*
函數功能:串口字符串發送
函數形參:
USART_TypeDef *USARTx :串口的類型 (USART1 USART2 USART3)
u8 *str:將要發送的字符串
*/
void USARTxSendString(USART_TypeDef *USARTx,u8 *str)
{
while(*str!='?')
{
USARTx->DR=*str;
while(!(USARTx->SR&1<<7)){} //等待發送完成
str++;
}
}
/*
函數功能:重寫printf底層函數接口
*/
int fputc(int c,FILE *stream)
{
USART1->DR=c; //發送一個字符
while(!(USART1->SR&1<<7)){}
return c;
}
/*
函數功能:重新scanf底層函數接口
*/
int fgetc(FILE *stream)
{
while(!(USART1->SR&1<<5)){}
return USART1->DR;
}
/*
函數功能:串口1的中斷服務函數
*/
void USART1_IRQHandler(void)
{
u8 data;
if(USART1->SR&1<<5)
{
data=USART1->DR;
USART1->DR=data;
}
}
復制代碼
審核編輯:湯梓紅
聲明:本文內容及配圖由入駐作者撰寫或者入駐合作網站授權轉載。文章觀點僅代表作者本人,不代表電子發燒友網立場。文章及其配圖僅供工程師學習之用,如有內容侵權或者其他違規問題,請聯系本站處理。
舉報投訴
-
寄存器
+關注
關注
31文章
5343瀏覽量
120348 -
STM32F407
+關注
關注
15文章
187瀏覽量
29455 -
串口配置
+關注
關注
0文章
5瀏覽量
1631
發布評論請先 登錄
相關推薦
【STM32F407開發板用戶手冊】第13章 STM32F407啟動過程詳解
【STM32F407開發板用戶手冊】第13章 STM32F407啟動過程詳解
發表于 11-23 18:06
?73次下載
【STM32F407開發板用戶手冊】第14章 STM32F407的電源,復位和時鐘系統
【STM32F407開發板用戶手冊】第14章 STM32F407的電源,復位和時鐘系統
發表于 12-02 16:21
?42次下載
【STM32F407開發板用戶手冊】第1章?? 初學STM32F407的準備工作
【STM32F407開發板用戶手冊】第1章?? 初學STM32F407的準備工作
發表于 12-04 13:36
?75次下載
【STM32F407開發板用戶手冊】第21章 STM32F407的NVIC中斷分組和配置(重要)
【STM32F407開發板用戶手冊】第21章 STM32F407的NVIC中斷分組和配置(重要)
發表于 12-04 13:51
?21次下載
【STM32F407開發板用戶手冊】第8章 STM32F407的終極調試組件Event Recorder
【STM32F407開發板用戶手冊】第8章 STM32F407的終極調試組件Event Recorder
發表于 12-04 14:21
?19次下載
【STM32F407開發板用戶手冊】第19章 STM32F407的GPIO應用之按鍵FIFO
【STM32F407開發板用戶手冊】第19章 STM32F407的GPIO應用之按鍵FIFO
發表于 12-05 15:21
?39次下載
STM32F407入門開發: 位帶操作
STM32F407的位帶操作可以實現類似51單片機中寄存器的操作方法,操作GPIO口代碼簡潔方便。 關于位段的操作在Cortex-M3M4權威指南里有詳細描述:
評論