123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406 |
- #include "uart.h"
- #include "stdio.h"
- #include "uart.h"
- #include <string.h>
- static INT8U uart1_tx_buf[UART1_TX_LEN] = {0};
- static INT8U uart1_rx_buf[UART1_REC_LEN] = {0};
- static INT8U uart3_tx_buf[UART3_TX_LEN] = {0};
- static INT8U uart3_rx_buf[UART3_REC_LEN] = {0};
- UartFrame_TypeDef Uart1FrameStruct[MAX_MSG_NUM];
- UartFrame_TypeDef Uart3FrameStruct[MAX_MSG_NUM];
- extern OS_EVENT *uart1_mbox;
- extern OS_EVENT *uart3_mbox;
- void uart1_nvic_config(void)
- {
- NVIC_InitTypeDef NVIC_InitStructure;
- // Usart1 NVIC 配置
- NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn; //串口1中断通道
- NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0; //抢占优先级
- NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0; //子优先级
- NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; // IRQ通道使能
- NVIC_Init(&NVIC_InitStructure); //根据指定的参数初始化VIC寄存器
- }
- void uart1_dma_init(void)
- {
- DMA_InitTypeDef DMA_InitStructure;
- if ((u32)UART1_DMA_TXCH > (u32)DMA2) //得到当前stream是属于DMA2还是DMA1
- {
- RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_DMA2, ENABLE); // DMA2时钟使能
- }
- else
- {
- RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_DMA1, ENABLE); // DMA1时钟使能
- }
- DMA_DeInit(UART1_DMA_TXCH);
- /* 配置 DMA Stream */
- DMA_InitStructure.DMA_PeripheralBaseAddr = (u32)(&(USART1->DR)); // DMA外设地址
- DMA_InitStructure.DMA_BufferSize = UART1_TX_LEN; //数据传输量
- DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable; //外设非增量模式
- DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable; //存储器增量模式
- DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte; //外设数据长度:8位
- DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte; //存储器数据长度:8位
- DMA_InitStructure.DMA_Mode = DMA_Mode_Normal; // 使用普通模式
- DMA_InitStructure.DMA_Priority = DMA_Priority_Medium; //中等优先级
- DMA_InitStructure.DMA_FIFOMode = DMA_FIFOMode_Disable;
- DMA_InitStructure.DMA_FIFOThreshold = DMA_FIFOThreshold_Full;
- DMA_InitStructure.DMA_MemoryBurst = DMA_MemoryBurst_Single; //存储器突发单次传输
- DMA_InitStructure.DMA_PeripheralBurst = DMA_PeripheralBurst_Single; //外设突发单次传输
- DMA_InitStructure.DMA_Channel = UART1_DMA; //通道选择
- DMA_InitStructure.DMA_DIR = DMA_DIR_MemoryToPeripheral; //存储器到外设模式
- DMA_InitStructure.DMA_Memory0BaseAddr = (u32)uart1_tx_buf; // DMA 存储器0地址
- DMA_Init(UART1_DMA_TXCH, &DMA_InitStructure); //初始化DMA Stream
- if ((u32)UART1_DMA_RXCH > (u32)DMA2) //得到当前stream是属于DMA2还是DMA1
- {
- RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_DMA2, ENABLE); // DMA2时钟使能
- }
- else
- {
- RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_DMA1, ENABLE); // DMA1时钟使能
- }
- DMA_DeInit(UART1_DMA_RXCH);
- /* 配置 DMA Stream */
- DMA_InitStructure.DMA_PeripheralBaseAddr = (u32)(&(USART1->DR)); // DMA外设地址
- DMA_InitStructure.DMA_BufferSize = UART1_REC_LEN; //数据传输量
- DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable; //外设非增量模式
- DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable; //存储器增量模式
- DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte; //外设数据长度:8位
- DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte; //存储器数据长度:8位
- DMA_InitStructure.DMA_Mode = DMA_Mode_Circular; // 使用循环模式
- DMA_InitStructure.DMA_Priority = DMA_Priority_Medium; //中等优先级
- DMA_InitStructure.DMA_FIFOMode = DMA_FIFOMode_Disable;
- DMA_InitStructure.DMA_FIFOThreshold = DMA_FIFOThreshold_Full;
- DMA_InitStructure.DMA_MemoryBurst = DMA_MemoryBurst_Single; //存储器突发单次传输
- DMA_InitStructure.DMA_PeripheralBurst = DMA_PeripheralBurst_Single; //外设突发单次传输
- /* 配置 RX DMA */
- DMA_InitStructure.DMA_Channel = UART1_DMA; /* 配置接收通道 */
- DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralToMemory; /* 设置从外设到内存 */
- DMA_InitStructure.DMA_Memory0BaseAddr = (u32)uart1_rx_buf; /* 设置内存地址 */
- DMA_Init(UART1_DMA_RXCH, &DMA_InitStructure);
- }
- void uart1_config(void)
- {
- USART_InitTypeDef USART_InitStructure;
- // USART1 初始化设置
- USART_InitStructure.USART_BaudRate = 9600; //波特率设置
- USART_InitStructure.USART_WordLength = USART_WordLength_8b; //字长为8位数据格式
- USART_InitStructure.USART_StopBits = USART_StopBits_1; //一个停止位
- USART_InitStructure.USART_Parity = USART_Parity_No; //无奇偶校验位
- USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; //无硬件数据流控制
- USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; //收发模式
- USART_Init(USART1, &USART_InitStructure); //初始化串口1
- USART_Cmd(USART1, ENABLE); //使能串口1
- }
- void Uart1DMA_Enable(DMA_Stream_TypeDef *DMA_Streamx, u16 count)
- {
- DMA_Cmd(DMA_Streamx, DISABLE); //关闭DMA传输
- while (DMA_GetCmdStatus(DMA_Streamx) != DISABLE)
- {
- } //确保DMA可以被设置
- DMA_SetCurrDataCounter(DMA_Streamx, count); //数据传输量
- DMA_Cmd(DMA_Streamx, ENABLE); //开启DMA传输
- }
- void uart1_init(void)
- {
- uart1_config();
- uart1_dma_init();
- uart1_nvic_config();
- // /* USART DMA enable*/
- USART_DMACmd(USART1, USART_DMAReq_Rx, ENABLE); // 使能串口DMA接收数据
- Uart1DMA_Enable(UART1_DMA_RXCH, UART3_REC_LEN);
- /*configure DMA0 interrupt*/
- USART_ITConfig(USART1, USART_IT_IDLE, ENABLE); //开启空闲中断
- USART_ITConfig(USART1, USART_IT_TC, ENABLE);
- UART1_RX_ENABLE;
- }
- /****************************************************
- * 函 数 名:Uart1_Send_Data
- * 函数功能:串口1发送数据
- * 入口参数:buf 待发送数据 len 数据长度
- * 说 明:
- *****************************************************/
- void Uart1_Send_Data(const u8 *buf, u16 len)
- {
- u8 i;
- UART1_TX_ENABLE; // 485 发送使能
- for (i = 0; i < len; i++) //循环发送数据
- {
- while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET)
- ;
- USART_SendData(USART1, buf[i]);
- }
- while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET)
- ;
- UART1_RX_ENABLE; // 接收使能
- }
- void Uart1_dma_Send_Data(const INT8U *buf, INT16U len)
- {
- // INT16U cnt = 0;
- if (RESET != DMA_GetFlagStatus(UART1_DMA_TXCH, DMA_FLAG_TCIF7))
- {
- DMA_ClearFlag(UART1_DMA_TXCH, DMA_FLAG_TCIF7);
- }
- UART1_TX_ENABLE;
- if (len > UART1_TX_LEN)
- {
- len = UART1_TX_LEN;
- }
- memcpy(uart1_tx_buf, buf, len);
- USART_DMACmd(USART1, USART_DMAReq_Tx, ENABLE); // 使能DMA串口发送数据
- Uart1DMA_Enable(UART1_DMA_TXCH, len);
- }
- void USART1_IRQHandler(void)
- {
- static INT8U u0_index = 0;
- volatile INT8U clear = 0;
- INT8U rec_cnt = 0;
- if (RESET != USART_GetITStatus(USART1, USART_IT_IDLE))
- {
- clear = USART1->SR;
- clear = USART1->DR; // 先读SR, 再读DR, 就是为了消除IDLE中断
- DMA_Cmd(UART1_DMA_RXCH, DISABLE);
- DMA_ClearFlag(UART1_DMA_RXCH, DMA_FLAG_TCIF5);
- rec_cnt = UART1_REC_LEN - DMA_GetCurrDataCounter(UART1_DMA_RXCH); // 获得接收帧帧长 特别注意: 帧长不是DMA_GetCurrDataCounter(DMA2_Stream5)
- memcpy(Uart1FrameStruct[u0_index].buf, uart1_rx_buf, rec_cnt);
- Uart1FrameStruct[u0_index].len = rec_cnt;
- OSMboxPost(uart1_mbox, &Uart1FrameStruct[u0_index]);
- if (u0_index < MAX_MSG_NUM - 1)
- {
- u0_index++;
- }
- else
- {
- u0_index = 0;
- }
- DMA_SetCurrDataCounter(UART1_DMA_RXCH, UART1_REC_LEN);
- DMA_Cmd(UART1_DMA_RXCH, ENABLE);
- }
- else if (RESET != USART_GetITStatus(USART1, USART_IT_TC))
- {
- USART_ClearITPendingBit(USART1, USART_IT_TC); // 清除发送完成标标志位
- UART1_RX_ENABLE; // 485接收使能
- Uart1DMA_Enable(UART1_DMA_RXCH, UART1_REC_LEN); // DMA接收使能
- DMA_Cmd(UART1_DMA_TXCH, DISABLE); // 关闭发送DMA
- DMA_SetCurrDataCounter(UART1_DMA_TXCH, 0); // 清除发送数据长度
- }
- }
- void uart3_nvic_config(void)
- {
- NVIC_InitTypeDef NVIC_InitStructure;
- // Usart3 NVIC 配置
- NVIC_InitStructure.NVIC_IRQChannel = USART3_IRQn; //串口3中断通道
- NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0; //抢占优先级
- NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0; //子优先级
- NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; // IRQ通道使能
- NVIC_Init(&NVIC_InitStructure);
- }
- void uart3_dma_init(void)
- {
- DMA_InitTypeDef DMA_InitStructure;
- if ((u32)UART3_DMA_TXCH > (u32)DMA2)
- {
- RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_DMA2, ENABLE); // DMA2时钟使能
- }
- else
- {
- RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_DMA1, ENABLE); // DMA1时钟使能
- }
- DMA_DeInit(UART3_DMA_TXCH);
- while (DMA_GetCmdStatus(UART3_DMA_TXCH) != DISABLE)
- {
- } //等待DMA可配置
- /* 配置 DMA Stream */
- DMA_InitStructure.DMA_Channel = UART3_DMA; //通道选择
- DMA_InitStructure.DMA_PeripheralBaseAddr = (u32)&USART3->DR; // DMA外设地址
- DMA_InitStructure.DMA_Memory0BaseAddr = (u32)uart3_tx_buf; // DMA 存储器0地址
- DMA_InitStructure.DMA_DIR = DMA_DIR_MemoryToPeripheral; //存储器到外设模式
- DMA_InitStructure.DMA_BufferSize = UART3_TX_LEN; //数据传输量
- DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable; //外设非增量模式
- DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable; //存储器增量模式
- DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte; //外设数据长度:8位
- DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte; //存储器数据长度:8位
- DMA_InitStructure.DMA_Mode = DMA_Mode_Normal; // 使用普通模式
- DMA_InitStructure.DMA_Priority = DMA_Priority_Medium; //中等优先级6
- DMA_InitStructure.DMA_FIFOMode = DMA_FIFOMode_Disable;
- DMA_InitStructure.DMA_FIFOThreshold = DMA_FIFOThreshold_Full;
- DMA_InitStructure.DMA_MemoryBurst = DMA_MemoryBurst_Single; //存储器突发单次传输
- DMA_InitStructure.DMA_PeripheralBurst = DMA_PeripheralBurst_Single; //外设突发单次传输
- DMA_Init(UART3_DMA_TXCH, &DMA_InitStructure); //初始化DMA Stream
- if ((u32)UART3_DMA_RXCH > (u32)DMA2) //得到当前stream是属于DMA2还是DMA1
- {
- RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_DMA2, ENABLE); // DMA2时钟使能
- }
- else
- {
- RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_DMA1, ENABLE); // DMA1时钟使能
- }
- DMA_DeInit(UART3_DMA_RXCH);
- while (DMA_GetCmdStatus(UART3_DMA_RXCH) != DISABLE)
- {
- } //等待DMA可配置
- /* 配置 DMA Stream */
- DMA_InitStructure.DMA_Channel = UART3_DMA; //通道选择
- DMA_InitStructure.DMA_PeripheralBaseAddr = (u32)&USART3->DR; // DMA外设地址
- DMA_InitStructure.DMA_Memory0BaseAddr = (u32)uart3_rx_buf; // DMA 存储器0地址
- DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralToMemory; //外设到存储器模式
- DMA_InitStructure.DMA_BufferSize = UART3_REC_LEN; //数据传输量
- DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable; //外设非增量模式
- DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable; //存储器增量模式
- DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte; //外设数据长度:8位
- DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte; //存储器数据长度:8位
- DMA_InitStructure.DMA_Mode = DMA_Mode_Circular; // 使用循环模式
- DMA_InitStructure.DMA_Priority = DMA_Priority_Medium; //中等优先级
- DMA_InitStructure.DMA_FIFOMode = DMA_FIFOMode_Disable;
- DMA_InitStructure.DMA_FIFOThreshold = DMA_FIFOThreshold_Full;
- DMA_InitStructure.DMA_MemoryBurst = DMA_MemoryBurst_Single; //存储器突发单次传输
- DMA_InitStructure.DMA_PeripheralBurst = DMA_PeripheralBurst_Single; //外设突发单次传输
- DMA_Init(UART3_DMA_RXCH, &DMA_InitStructure);
- }
- void uart3_config(void)
- {
- /* USART3 configure */
- USART_InitTypeDef USART_InitStructure;
- // USART3 初始化设置
- USART_InitStructure.USART_BaudRate = 9600; //波特率设置
- USART_InitStructure.USART_WordLength = USART_WordLength_8b; //字长为8位数据格式
- USART_InitStructure.USART_StopBits = USART_StopBits_1; //一个停止位
- USART_InitStructure.USART_Parity = USART_Parity_No; //无奇偶校验位
- USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; //无硬件数据流控制
- USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; //收发模式
- USART_Init(USART3, &USART_InitStructure); //初始化串口1
- USART_Cmd(USART3, ENABLE); //使能串口3
- }
- void Uart3DMA_Enable(DMA_Stream_TypeDef *DMA_Streamx, u16 count)
- {
- DMA_Cmd(DMA_Streamx, DISABLE); //关闭DMA传输
- while (DMA_GetCmdStatus(DMA_Streamx) != DISABLE)
- {
- } //确保DMA可以被设置
- DMA_SetCurrDataCounter(DMA_Streamx, count); //数据传输量
- DMA_Cmd(DMA_Streamx, ENABLE); //开启DMA传输
- }
- void uart3_init(void)
- {
- uart3_config();
- uart3_dma_init();
- uart3_nvic_config();
- /* USART DMA enable*/
- USART_DMACmd(USART3, USART_DMAReq_Rx, ENABLE); // 使能串口DMA接收数据
- Uart3DMA_Enable(UART3_DMA_RXCH, UART3_REC_LEN);
- /*configure DMA interrupt*/
- USART_ITConfig(USART3, USART_IT_IDLE, ENABLE); //开启空闲中断
- USART_ITConfig(USART3, USART_IT_TC, ENABLE);
- UART3_RX_ENABLE;
- }
- /****************************************************
- * 函 数 名:Uart3_Send_Data
- * 函数功能:串口1发送数据
- * 入口参数:buf 待发送数据 len 数据长度
- * 说 明:
- *****************************************************/
- void Uart3_Send_Data(const INT8U *buf, INT16U len)
- {
- INT8U i;
- UART3_TX_ENABLE; // 485 发送使能
- for (i = 0; i < len; i++) //循环发送数据
- {
- while (USART_GetFlagStatus(USART3, USART_FLAG_TC) == RESET)
- ;
- USART_SendData(USART3, buf[i]);
- }
- while (USART_GetFlagStatus(USART3, USART_FLAG_TC) == RESET)
- ;
- UART3_RX_ENABLE; // 接收使能
- }
- void Uart3_dma_Send_Data(const INT8U *buf, INT16U len)
- {
- if (DMA_GetFlagStatus(UART3_DMA_TXCH, DMA_FLAG_TCIF3) != RESET)
- {
- DMA_ClearFlag(UART3_DMA_TXCH, DMA_FLAG_TCIF3);
- }
- UART3_TX_ENABLE; // 485 发送使能
- if (len > UART3_TX_LEN)
- {
- len = UART3_TX_LEN;
- }
- memcpy(uart3_tx_buf, buf, len);
- USART_DMACmd(USART3, USART_DMAReq_Tx, len);
- Uart3DMA_Enable(UART3_DMA_TXCH, len);
- }
- void USART3_IRQHandler(void)
- {
- static INT8U u3_index = 0;
- volatile INT8U clear = 0;
- INT8U rec_cnt = 0;
- if (RESET != USART_GetITStatus(USART3, USART_IT_IDLE))
- {
- clear = USART3->SR;
- clear = USART3->DR; // 先读SR, 再读DR, 就是为了消除IDLE中断
- DMA_Cmd(UART3_DMA_RXCH, DISABLE);
- DMA_ClearFlag(UART3_DMA_RXCH, DMA_FLAG_TCIF1);
- rec_cnt = UART3_REC_LEN - DMA_GetCurrDataCounter(UART3_DMA_RXCH);
- memcpy(Uart3FrameStruct[u3_index].buf, uart3_rx_buf, rec_cnt);
- Uart3FrameStruct[u3_index].len = rec_cnt;
- OSMboxPost(uart3_mbox, &Uart3FrameStruct[u3_index]);
- if (u3_index < MAX_MSG_NUM - 1)
- {
- u3_index++;
- }
- else
- {
- u3_index = 0;
- }
- DMA_SetCurrDataCounter(UART3_DMA_RXCH, UART3_REC_LEN);
- DMA_Cmd(UART3_DMA_RXCH, ENABLE);
- }
- else if (RESET != USART_GetITStatus(USART3, USART_IT_TC))
- {
- USART_ClearITPendingBit(USART3, USART_IT_TC);
- UART3_RX_ENABLE;
- Uart3DMA_Enable(UART3_DMA_RXCH, UART3_REC_LEN); // DMA接收使能
- DMA_Cmd(UART3_DMA_TXCH, DISABLE); // 关闭发送DMA
- DMA_SetCurrDataCounter(UART3_DMA_TXCH, 0); // 清除发送数据长度
- }
- }
|