先查看用户手册,找到USART外设对应的DMA通道

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 |
#define BUF_LEN 64U uint8_t g_dma_rx_finish; char g_dma_rx_buf[BUF_LEN]; //用于DMA数据接收 char g_dma_tx_buf[BUF_LEN]; //用于DMA数据发送 char g_uart0_rx_buf[BUF_LEN]; //DMA数据接收完成,及时拷贝出去,在中断外部处理数据 void uart0_dma_init(void)//DMA发送接收初始化 { dma_parameter_struct dma_init_struct; /* enable DMA clock */ rcu_periph_clock_enable(RCU_DMA); /* initialize DMA channel1 */ dma_deinit(DMA_CH1); dma_struct_para_init(&dma_init_struct); dma_init_struct.direction = DMA_MEMORY_TO_PERIPHERAL; dma_init_struct.memory_addr = (uint32_t)g_dma_tx_buf; dma_init_struct.memory_inc = DMA_MEMORY_INCREASE_ENABLE; dma_init_struct.memory_width = DMA_MEMORY_WIDTH_8BIT; dma_init_struct.number = BUF_LEN; dma_init_struct.periph_addr = USART_TDATA(USART0); dma_init_struct.periph_inc = DMA_PERIPH_INCREASE_DISABLE; dma_init_struct.periph_width = DMA_PERIPHERAL_WIDTH_8BIT; dma_init_struct.priority = DMA_PRIORITY_ULTRA_HIGH; dma_init(DMA_CH1, &dma_init_struct); /* initialize DMA channel2 */ dma_deinit(DMA_CH2); dma_init_struct.direction = DMA_PERIPHERAL_TO_MEMORY; dma_init_struct.memory_addr = (uint32_t)g_dma_rx_buf; dma_init_struct.memory_inc = DMA_MEMORY_INCREASE_ENABLE; dma_init_struct.memory_width = DMA_MEMORY_WIDTH_8BIT; dma_init_struct.number = BUF_LEN; dma_init_struct.periph_addr = USART_RDATA(USART0); dma_init_struct.periph_inc = DMA_PERIPH_INCREASE_DISABLE; dma_init_struct.memory_width = DMA_PERIPHERAL_WIDTH_8BIT; dma_init_struct.priority = DMA_PRIORITY_ULTRA_HIGH; dma_init(DMA_CH2, &dma_init_struct); /* configure DMA mode */ dma_circulation_disable(DMA_CH1); dma_memory_to_memory_disable(DMA_CH1); dma_circulation_disable(DMA_CH2); dma_memory_to_memory_disable(DMA_CH2); /* USART DMA enable for reception */ usart_dma_receive_config(USART0, USART_DENR_ENABLE); /* enable DMA channel2 */ dma_channel_enable(DMA_CH2); /* USART DMA enable for transmission */ usart_dma_transmit_config(USART0, USART_DENT_ENABLE); /* enable DMA channel1 */ dma_channel_enable(DMA_CH1); } void uart0_init(uint32_t baud) { /* enable COM GPIO clock */ rcu_periph_clock_enable(RCU_GPIOA); /* enable USART clock */ rcu_periph_clock_enable(RCU_USART0); /* connect port to USARTx_Tx */ gpio_af_set(GPIOA, GPIO_AF_1, GPIO_PIN_9); /* connect port to USARTx_Rx */ gpio_af_set(GPIOA, GPIO_AF_1, GPIO_PIN_10); /* configure USART Tx as alternate function push-pull */ gpio_mode_set(GPIOA, GPIO_MODE_AF, GPIO_PUPD_PULLUP, GPIO_PIN_9); gpio_output_options_set(GPIOA, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, GPIO_PIN_9); /* configure USART Rx as alternate function push-pull */ gpio_mode_set(GPIOA, GPIO_MODE_AF, GPIO_PUPD_PULLUP, GPIO_PIN_10); gpio_output_options_set(GPIOA, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, GPIO_PIN_10); /* USART configure */ usart_deinit(USART0); usart_baudrate_set(USART0, baud); usart_stop_bit_set(USART0, USART_STB_1BIT); //设置停止位 usart_word_length_set(USART0, USART_WL_8BIT); //设置数据字长度 usart_parity_config(USART0, USART_PM_NONE); //设置奇偶校验位 usart_receive_config(USART0, USART_RECEIVE_ENABLE); usart_transmit_config(USART0, USART_TRANSMIT_ENABLE); usart_interrupt_enable(USART0, USART_INT_IDLE); usart_enable(USART0); uart0_dma_init(); nvic_irq_enable(USART0_IRQn, 1); } //本方法只适用发送字符串,不能发送0x00 void usart0_dma_send(char* buf) { memset(g_dma_tx_buf, 0x00, sizeof(g_dma_tx_buf)); strcpy(g_dma_tx_buf, buf); dma_channel_disable(DMA_CH1); dma_transfer_number_config(DMA_CH1, (uint32_t)strlen(g_dma_tx_buf)); /* enable DMA channel1 */ dma_channel_enable(DMA_CH1); } /* ********************************************************************************************************* * 函 数 名: USART0_IRQHandler * 功能说明: 串口0中断接收函数 * 形 参: 无 * 返 回 值: 无 ********************************************************************************************************* */ void USART0_IRQHandler(void) { uint8_t rx_num; if (RESET != usart_interrupt_flag_get(USART0, USART_INT_FLAG_IDLE)) { usart_interrupt_flag_clear(USART0, USART_INT_FLAG_IDLE); if (g_dma_rx_finish == 0) //数据没有处理完成,不接收新的字符 { dma_channel_disable(DMA_CH2); rx_num = sizeof(g_dma_rx_buf) - dma_transfer_number_get(DMA_CH2); memcpy(g_uart0_rx_buf, g_dma_rx_buf, rx_num); /* 转存数据到待处理数据缓冲区*/ memset(g_dma_rx_buf, 0x00, sizeof(g_dma_rx_buf)); /* 重新设置DMA传输 */ dma_memory_address_config(DMA_CH2, (uint32_t)g_dma_rx_buf); dma_transfer_number_config(DMA_CH2, sizeof(g_dma_rx_buf)); dma_channel_enable(DMA_CH2); /* 开启DMA传输 */ g_dma_rx_finish = 1; } } } |