歡迎來到Linux教程網
Linux教程網
Linux教程網
Linux教程網
您现在的位置: Linux教程網 >> UnixLinux >  >> Linux編程 >> Linux編程

STM32串口寄存器操作

//USART.C
 
/*********************************************************************************************************/
 /*  USART 收發  */
 /*  陳鵬 20110611*/

 #include "SYSTEM.H"
 #include "GPIO_INIT.H"
 #include "USART.H"
 

//定義串口通道號最大值
 #define UART_ChMax  1
 

 

//UART外設結構指針
 static const  USART_TypeDef * USARTxN[5] = {USART1,USART2,USART3,UART4,UART5};
 

//相關UART狀態結構
 typedef struct
 {
 FlagStatus  NewDataFlag;//接收到新數據
 FlagStatus  BuffFull;  //接收Buff滿
 FlagStatus  IntRx;  //是否開啟中斷接收
 u8 *RxBuff;//接收Buff指針
 u16  RxBuffSize;//接收緩沖區大小,一幀數據大小
 u16 UartRxCnt;//接收數據計數器
 } UartRx_TypeDef;
 

//UART1  接收狀態結構
 static UartRx_TypeDef UartRx[UART_ChMax + 1];
 

//////////////////////////////////////////////////////////////////
 //加入以下代碼,支持printf函數,而不需要選擇use MicroLIB 
 #if 1
 #pragma import(__use_no_semihosting)           
 //標准庫需要的支持函數               
 struct __FILE
 {
 int handle;
 /* Whatever you require here. If the only file you are using is */
 /* standard output using printf() for debugging, no file handling */
 /* is required. */
 };
 /* FILE is typedef’ d in stdio.h. */
 FILE __stdout;     
 //定義_sys_exit()以避免使用半主機模式   
 _sys_exit(int x)
 {
 x = x;
 }
 //重定義fputc函數
 int fputc(int ch, FILE *f)
 {     
 UARTx_SendByte(0,(u8)ch);     
 return ch;
 }
 #endif
 //end
 //////////////////////////////////////////////////////////////////
 

 

 

/*************************************************************************************************************************
 * 函數  :  u8 UARTx_Init(u8 ch,u8 SYS_CLK,u32 Speed,u8 RX_Int)
 * 功能  :  串口初始化
 * 參數  :  ch:通道選擇,0->usart1;SYS_CLK當前系統時鐘,Speed:串口速度,RX_Int:是否時能中斷接受
 * 返回  :  0:成功,1:失敗
 * 依賴  :  底層宏定義
 * 作者  :  陳鵬
 * 時間  :  20120403
 * 最後修改時間 : 20120403
 * 說明  : USART1~UART5,對應通道0~4
 *************************************************************************************************************************/
 u8 UARTx_Init(u8 ch,u8 SYS_CLK,u32 Speed,u8 RX_Int)
 {
 USART_TypeDef *UARTx = (USART_TypeDef *)USARTxN[ch];  //獲取對應通道硬件基址指針
 u32 clock;
 u8 irq_n;
 float fclk;
 

if(ch > UART_ChMax)
 return 1;  //端口號超出范圍
 //初始化UART IO
 DeviceClockEnable(DEV_AFIO,ENABLE);//復用功能AFIO時鐘使能
 switch (ch)
 {
 case 0:  //通道0,USART1 ,TX:PA9;RX:PA10
 {
 DeviceClockEnable(DEV_GPIOA,ENABLE);//GPIO A 時鐘使能
 DeviceClockEnable(DEV_USART1,ENABLE);//USART 1 時鐘使能
 GPIOx_Init(GPIOA,BIT9,AF_PP, SPEED_10M); 
//PA09,TXD只能設置成復用推挽輸出
 GPIOx_Init(GPIOA,BIT10,IN_FLOATING,IN_IN);  //浮空輸入
 DeviceReset(DEV_USART1);//復位串口1
 irq_n =  IRQ_USART1;//串口1中斷號
 }break;
 case 1:  //通道1,USART2 ,TX:PA2;RX:PA3
 {
 DeviceClockEnable(DEV_GPIOA,ENABLE);//GPIO A 時鐘使能
 DeviceClockEnable(DEV_USART2,ENABLE);//USART 2 時鐘使能
 GPIOx_Init(GPIOA,BIT2,AF_PP, SPEED_10M); 
//PA2,TXD只能設置成復用推挽輸出
 GPIOx_Init(GPIOA,BIT3,IN_FLOATING,IN_IN);  //浮空輸入
 DeviceReset(DEV_USART2);//復位串口2
 irq_n =  IRQ_USART2;//串口2中斷號
 }break;
 case 2:  //通道2,USART3 ,TX:PD8;RX:PD9
 {
 DeviceClockEnable(DEV_GPIOD,ENABLE);//GPIO D 時鐘使能
 DeviceClockEnable(DEV_USART3,ENABLE);//USART 3 時鐘使能
 GPIOx_Init(GPIOD,BIT8,AF_PP, SPEED_10M); 
//PD8,TXD只能設置成復用推挽輸出
 GPIOx_Init(GPIOD,BIT9,IN_FLOATING,IN_IN);  //浮空輸入
 DeviceReset(DEV_USART3);//復位串口3
 irq_n =  IRQ_USART3;//串口3中斷號
 }break;
 case 3:  //通道3,UART4 ,TX:PC10;RX:PC11
 {
 DeviceClockEnable(DEV_GPIOC,ENABLE);//GPIO C 時鐘使能
 DeviceClockEnable(DEV_UART4,ENABLE);//UART 4 時鐘使能
 GPIOx_Init(GPIOC,BIT10,AF_PP, SPEED_10M);  //PC10,TXD只能設置成復用推挽輸出
 GPIOx_Init(GPIOD,BIT11,IN_FLOATING,IN_IN);  //浮空輸入
 DeviceReset(DEV_UART4);//復位串口3
 irq_n =  IRQ_UART4;//串口3中斷號
 }break;
 case 4:  //通道4,UART5 ,TX:PC12;RX:PD2
 {
 DeviceClockEnable(DEV_GPIOC,ENABLE);//GPIO C 時鐘使能
 DeviceClockEnable(DEV_GPIOD,ENABLE);//GPIO D 時鐘使能
 DeviceClockEnable(DEV_UART5,ENABLE);//UART 5 時鐘使能
 GPIOx_Init(GPIOC,BIT12,AF_PP, SPEED_10M);  //PC12,TXD只能設置成復用推挽輸出
 GPIOx_Init(GPIOD,BIT2,IN_FLOATING,IN_IN);  //浮空輸入
 DeviceReset(DEV_UART5);//復位串口3
 irq_n =  IRQ_UART5;//串口3中斷號
 }break;
 default : return 1;//端口號超出范圍,返回錯誤
 }
 //設置波特率分頻系數
 clock = SYS_CLK * 1000000;//USART1時鐘
 if(ch > 0)
 clock /= 2;  //USART2,3,4,5時鐘
 fclk = (float)clock / 16.0 / Speed;//計算波特率分頻系數
 clock = (u16)fclk;//得到波特率分頻系數整數部分

 UARTx->BRR =  clock << 4;//設置波特率整數部分
 fclk -= clock;//得到波特率分頻系數小數部分
 fclk *= 16;
 UARTx->BRR |= 0xf & (u16)fclk;//設置波特率小數部分
 //配置UART
 UARTx->CR1 = 0x2000;//使能USART,1個開始位,8位數據
 UARTx->CR1 |= 0x8;//置TE = 1;發送使能;發送第一個空閒位
 UARTx->CR1 |= 0x04;//RE = 1;接收使能
 SetUartRxBuff(ch,0,NULL);//設置串口接收緩沖區
 UARTx_ClearRxInt(ch);  //清除串口接收中斷標志
 if(RX_Int)
 {
 UARTx->CR1 |= 0x20;//RXNEIE = 1,開RXNE中斷,即開啟接收中斷
 NVIC_IntEnable(irq_n,1);//開啟USART1全局中斷
 UartRx[ch].IntRx = SET;//中斷接收標志有效
 }
 else
 {
 NVIC_IntEnable(irq_n,0);
//關閉USART全局中斷
 UartRx[ch].IntRx = RESET;//中斷接收標志無效
 }
 UARTx_SendByte(0,'S');//發送一字節數據
 return 0;  //初始化成功,返回0
 }

Copyright © Linux教程網 All Rights Reserved