在處理UART數據的時候,DMA是一種非常靈活、高效的方式。
※補記:USART_DR 串口數據寄存器是一個雙寄存器,包含了TDR和RDR,對它讀操作,讀取的是RDR寄存器的值,對它的寫操作,實際上是寫到TDR寄存器;當向該寄存器寫數據的時候,串口就會自動發送,當收到收據的時候,也是存在該寄存器內。


關于讀寫:
__STATIC_INLINE uint8_t LL_USART_ReceiveData8(USART_TypeDef *USARTx);/*
讀取接收寄存器USARTx_DR中8位數據,接收即所得。返回值最大為0xFF
若使能校驗位,接收的最高位MSB將由硬件自動進行校驗。
*/
__STATIC_INLINE uint16_t LL_USART_ReceiveData9(USART_TypeDef *USARTx);/*
讀取接收寄存器USARTx_DR中9位數據(當字節長9,接收即所得)。返回值最大為0x1FF
若使能校驗位,接收的最高位MSB將由硬件自動進行校驗。
*/
__STATIC_INLINE void LL_USART_TransmitData9(USART_TypeDef *USARTx, uint16_t Value);/*
向發送寄存器寫入9位數據。當使能校驗位,發送時最高位MSB自動替換成校驗值
*/
__STATIC_INLINE void LL_USART_TransmitData8(USART_TypeDef *USARTx, uint8_t Value)/*
向發送寄存器寫入8位數據。當使能校驗位,發送時最高位MSB自動替換成校驗值
*/
·
API:
__STATIC_INLINE void LL_USART_EnableDMAReq_RX(USART_TypeDef *USARTx);/*
使能接收DMA,啟用后DR有數據時將允許發送DMA請求;具體見示例用法
*/
__STATIC_INLINE void LL_USART_DisableDMAReq_RX(USART_TypeDef *USARTx);/*
禁用接收DMA
*/
__STATIC_INLINE uint32_t LL_USART_IsEnabledDMAReq_RX(USART_TypeDef *USARTx);/*
檢測是否使能接收DMA
*/
__STATIC_INLINE void LL_USART_EnableDMAReq_TX(USART_TypeDef *USARTx);/*
使能發送DMA
*/
__STATIC_INLINE void LL_USART_DisableDMAReq_TX(USART_TypeDef *USARTx);/*
禁用發送DMA
*/
__STATIC_INLINE uint32_t LL_USART_IsEnabledDMAReq_TX(USART_TypeDef *USARTx);/*
檢測是否使能發送DMA
*/
/**************************************************/
__STATIC_INLINE uint32_t LL_USART_DMA_GetRegAddr(USART_TypeDef *USARTx);/*
返回UART模塊數據寄存器DR地址;無論是否啟用DMA均可用
*/
/ 結力期末考分界線 */
配置使用DMA收發:
1.在CubeMX中:



+在項目設置中調整為使用LL
2.生成代碼
此時在生成代碼已實現了串口DMA的初始化設置并生成了相應的DMA中斷句柄。接下來通過代碼實現功能。示例為一個簡單的功能,將串口接收到的數據再通過串口發出。
3.配置
①在main.h中定義全局變量test_data:
uint8_t test_data;
②在usart.c中引入變量
extern uint8_t test_data;
③在usart.c中進行設置
※通道配置為非循環模式時,傳輸結束后(即傳輸計數變為0)將不再產生DMA操作。要開始新的DMA傳輸,需要3個步驟:在關閉DMA通道的情況下,在DMA_CNDTRx寄存器中重新寫入傳輸數目(有需要則需重新配置地址),然后重新開啟DMA。
//RX DMA配置
LL_DMA_SetPeriphAddress(DMA1, LL_DMA_CHANNEL_5,LL_USART_DMA_GetRegAddr(USART1));//連接外設寄存器USART1- >DR
LL_DMA_SetMemoryAddress(DMA1, LL_DMA_CHANNEL_5, (uint32_t)&test_data);//連接數據存儲地址
LL_DMA_SetDataLength(DMA1, LL_DMA_CHANNEL_5, 1);/*設置傳輸的數據長度,由于是一字節一傳所以此處為1,
若數據為n字節則會在接收到的字節數量達到n的時候,才傳輸結束。*/
LL_USART_EnableDMAReq_RX(USART1);//使能RX接收DMA
LL_DMA_EnableIT_TC(DMA1, LL_DMA_CHANNEL_5);//使能DMA通道的傳輸完成中斷功能;當傳輸量達到數據長度將引發中斷
LL_DMA_EnableChannel(DMA1, LL_DMA_CHANNEL_5);//開啟DMA傳輸,此時若RX讀取到數據寫入DR將傳輸至MemoryAddress
//
//TX DMA配置
LL_DMA_SetPeriphAddress(DMA1, LL_DMA_CHANNEL_4, LL_USART_DMA_GetRegAddr(USART1)); //連接外設寄存器USART1- >DR
LL_DMA_SetMemoryAddress(DMA1, LL_DMA_CHANNEL_4, (uint32_t)&test_data); //連接數據存儲地址
LL_DMA_EnableIT_TC(DMA1, LL_DMA_CHANNEL_4); //使能DMA中斷
LL_USART_EnableDMAReq_TX(USART1); //使能TX接收DMA
/* USER CODE END USART1_Init 1 */
④中斷處理函數:
void DMA1_Channel5_IRQHandler(void)
{ //RX中斷調用
/* USER CODE BEGIN DMA1_Channel5_IRQn 0 */
if(LL_DMA_IsActiveFlag_TC5(DMA1))//判斷是否由DMA傳輸完成引發中斷
{
LL_DMA_DisableChannel(DMA1, LL_DMA_CHANNEL_5);//關閉通道,以在之后開啟新的DMA傳輸
LL_DMA_SetMemoryAddress(DMA1, LL_DMA_CHANNEL_4, (uint32_t)&test_data); //TX連接數據存儲地址
LL_DMA_SetDataLength(DMA1, LL_DMA_CHANNEL_4, 1);//設置TX數據長度
LL_DMA_ClearFlag_TC5(DMA1);//清除中斷標志,使能下一次RX中斷
LL_DMA_EnableChannel(DMA1, LL_DMA_CHANNEL_4);//從數據位置向TX啟動一次DMA;傳輸完成后調用TX的DMA中斷
}
/* USER CODE END DMA1_Channel5_IRQn 0 */
}
void DMA1_Channel4_IRQHandler(void)
{ //TX中斷調用
/* USER CODE BEGIN DMA1_Channel4_IRQn 0 */
if(LL_DMA_IsActiveFlag_TC4(DMA1))//判斷是否由DMA傳輸完成引發中斷
{
LL_DMA_ClearFlag_TC4(DMA1); //清除中斷標志
LL_DMA_DisableChannel(DMA1, LL_DMA_CHANNEL_4); //關閉通道,以在之后開啟新的DMA傳輸
LL_DMA_SetMemoryAddress(DMA1, LL_DMA_CHANNEL_5, (uint32_t)&test_data); //RX連接數據存儲地址
LL_DMA_EnableChannel(DMA1, LL_DMA_CHANNEL_5);//再次啟動RX DMA功能
}
/* USER CODE END DMA1_Channel4_IRQn 0 */
}
以上代碼即可實現功能。
聲明:本文內容及配圖由入駐作者撰寫或者入駐合作網站授權轉載。文章觀點僅代表作者本人,不代表電子發燒友網立場。文章及其配圖僅供工程師學習之用,如有內容侵權或者其他違規問題,請聯系本站處理。
舉報投訴
-
寄存器
+關注
關注
31文章
5608瀏覽量
129975 -
TDR
+關注
關注
1文章
77瀏覽量
21003 -
中斷處理
+關注
關注
0文章
96瀏覽量
11480 -
UART接口
+關注
關注
0文章
124瀏覽量
16372 -
數據存儲器
+關注
關注
1文章
70瀏覽量
18146
發布評論請先 登錄
相關推薦
熱點推薦
STM32 串口使用IDLE中斷+DMA接收(HAL庫函數)
STM32 串口使用IDLE中斷+DMA接收(HAL庫函數)一、開發環境單片機型號:STM32H743IIT6工程配置環境:
發表于 12-02 21:06
?42次下載
STM32---UART使用DMA數據傳輸
當預先不知道要接收的數據時,如何使用 DMA 在 UART 上讀取數據的信息。在STM32中,通常有以下幾種模式:輪詢模式程序必須輪詢狀態位以檢查是否已收到新字符并以足夠快的速度讀取它以獲得所有字節
發表于 12-03 10:06
?8次下載
STM32CubeMX_UART_printf_接收中斷_DMA空閑中斷_LPUART
文章目錄前言STM32CubeMX新建F767工程UART配置生成代碼串口發送printf支持串口接收中斷DMA空閑
發表于 12-06 18:36
?6次下載
STM32 HAL CubeMX 串口IDLE接收空閑中斷+DMA
關于DMA原理部分講解,及CubeMx配置部分,請參考該文章【STM32】HAL庫 STM32CubeMX教程十一—DMA (串口
發表于 12-20 19:39
?31次下載
STM32L431 寄存器配置 USART+DMA發送+中斷接收
用的外設是PA9 PA10DMA選擇的是DMA2_Channel6代碼中還用了DMA傳輸完成中斷,用來配
發表于 12-24 19:09
?20次下載
STM32CubeMx配置DMA+串口空閑中斷+FreeRTOS,完美處理串口數據。
。使用DMA輔助處理串口的數據,能夠大幅緩解單片機的運行壓力,提高串口數據的處理能力。使用CubeMx配置串口+DMA+FreeRTOS,以下內容僅展示了主要涉及到的串口和DMA的
發表于 12-24 19:11
?53次下載
STM32U59 SPI DMA發送未產生傳輸完成中斷問題分析
某客戶發現修改代碼后,STM32U59 SPI DMA 發送未產生傳輸完成中斷,但修改的代碼跟 SPI 以及 DMA 毫無關聯。
HAL庫無法實現UART的DMA傳輸真是這樣嗎?
使用STM32CubeMx進行圖形化配置,并生成基于HAL庫的初始代碼,要實現UART收發功能的DMA傳輸的話,除了安排好的收發緩沖內存外,
DMA帶中斷的內存到內存傳輸
要使用中斷配置 DMA,請按照內存到內存模式部分中詳述的步驟進行操作。 在System Core 》 NVIC中啟用DMA1 Channel 1 Global Interrupt如下圖
發表于 03-23 15:23
?4381次閱讀
STM32 UART配置中斷DMA傳輸
評論