完善资料让更多小伙伴认识你,还能领取20积分哦, 立即完善>
数据环形缓冲区:
#define FIFO_BUF_SIZE 512 //必须是2的幂次方 #define FIFO_BUF_SIZE_MASK (FIFO_BUF_SIZE - 1) typedef struct { uint32 head; //头指针 uint32 tail; //尾指针 uint8 buf[FIFO_BUF_SIZE]; //缓冲区 } fifo_buf_t; 缓冲区接口: status_t fifo_empty(fifo_buf_t* fifo) //判断缓冲区是否为空 { if (fifo->tail == fifo->head) // empty { return OK; } return ER; } status_t fifo_full(fifo_buf_t* fifo) //判断缓冲区是否为满 { if (((fifo->tail + 1) & FIFO_BUF_SIZE_MASK) == fifo->head) // full { return OK; } return ER; } status_t fifo_put(fifo_buf_t* fifo, uint8 c) //往缓冲区放一个字节 { if (fifo_full(fifo) == OK) // full { return ER; } fifo->buf[fifo->tail] = c; fifo->tail ++; fifo->tail &= FIFO_BUF_SIZE_MASK; return OK; } status_t fifo_get(fifo_buf_t* fifo, uint8* c) //往缓冲区取一个字节 { if (fifo_empty(fifo) == OK) // empty { return ER; } *c = fifo->buf[fifo->head]; fifo->head ++; fifo->head &= FIFO_BUF_SIZE_MASK; return OK; } 串口应用设计原理是: 数据收,接收中断会把数据丢到缓冲区,应用调用读接口,从接收缓冲区里读数据。 数据发,应用调用写接口,写数据到到发送缓冲区里,然后启动发送完成中断,在中断里会判断发送缓冲区是否有数据,有就发送,没有就关闭发送完成中断。 typedef struct //串口结构体 { USART_TypeDef* USARTx; fifo_buf_t tx_fifo; //发送缓冲区 fifo_buf_t rx_fifo; //接口缓冲区 } uart_driver_t; static uart_driver_t uart_driver_list[UART_MAX]; void UART_TxIntCallback(int fd) { if ((fd < 0) || (fd >= UART_MAX)) { return; } uart_driver_t* puart = &uart_driver_list[fd]; if (USART_GetITStatus(puart->USARTx, USART_IT_TC) != RESET) { uint8 c; if (fifo_get(&puart->tx_fifo, &c) == OK) { USART_SendData(puart->USARTx, c); } else { USART_ITConfig(puart->USARTx, USART_IT_TC, DISABLE); } } } void UART_RxIntCallback(int fd) { if ((fd < 0) || (fd >= UART_MAX)) { return; } uart_driver_t* puart = &uart_driver_list[fd]; if (USART_GetITStatus(puart->USARTx, USART_IT_RXNE) != RESET) { uint8 c; c = USART_ReceiveData(puart->USARTx); fifo_put(&puart->rx_fifo, c); } //溢出 if (USART_GetFlagStatus(puart->USARTx, USART_FLAG_ORE) == SET) { uint8 c; c = USART_ReceiveData(puart->USARTx); (void)c; USART_ClearFlag(puart->USARTx, USART_FLAG_ORE); } } static void UART_TxStartup(int fd) { if ((fd < 0) || (fd >= UART_MAX)) { return; } uart_driver_t* puart = &uart_driver_list[fd]; USART_ITConfig(puart->USARTx, USART_IT_TC, ENABLE); } int UART_Write(int fd, uint8 *buf, int len) { if ((fd < 0) || (fd >= UART_MAX)) { return ER; } int i; uart_driver_t* puart = &uart_driver_list[fd]; if ((buf == NULL) || (len == 0)) { return ER; } if (fifo_full(&puart->tx_fifo) == OK) { return 0; } SYS_ENTER_CRITICAL(); for (i = 0;i < len;i ++) { if (fifo_put(&puart->tx_fifo, buf) == ER) { break; } } SYS_EXIT_CRITICAL(); UART_TxStartup(fd); return i; } int UART_Read(int fd, uint8 *buf, int len) { if ((fd < 0) || (fd >= UART_MAX)) { return ER; } int i; uart_driver_t* puart = &uart_driver_list[fd]; if ((buf == NULL) || (len == 0)) { return ER; } if (fifo_empty(&puart->rx_fifo) == OK) { return 0; } SYS_ENTER_CRITICAL(); for (i = 0;i < len;i ++) { if (fifo_get(&puart->rx_fifo, &buf) == ER) { break; } } SYS_EXIT_CRITICAL(); return i; } static void UART_MspDeInit(int fd) { //硬件释放 } static void UART_MspInit(int fd) { //硬件初始化 } void UART_DeInit(int fd) { UART_MspDeInit(fd); } void UART_Init(int fd, uint32 BaudRate, uint16 StopBits, uint16 Parity) { if ((fd < 0) || (fd >= UART_MAX)) { return; } USART_InitTypeDef USART_InitStructure; uart_driver_t* puart = &uart_driver_list[fd]; /* uart fifo */ memset(&puart->tx_fifo, 0, sizeof(fifo_buf_t)); memset(&puart->rx_fifo, 0, sizeof(fifo_buf_t)); UART_MspInit(fd); /* USART mode config */ USART_InitStructure.USART_BaudRate = BaudRate; //115200; USART_InitStructure.USART_WordLength = ((Parity == USART_Parity_No) ? USART_WordLength_8b : USART_WordLength_9b); USART_InitStructure.USART_StopBits = StopBits; //USART_StopBits_1; USART_InitStructure.USART_Parity = Parity; //USART_Parity_No; USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; USART_Init(puart->USARTx, &USART_InitStructure); USART_ITConfig(puart->USARTx, USART_IT_RXNE, ENABLE); USART_ClearFlag(puart->USARTx, USART_FLAG_TC); //清除发送完成标志 USART_Cmd(puart->USARTx, ENABLE); } |
|
|
|
只有小组成员才能发言,加入小组>>
调试STM32H750的FMC总线读写PSRAM遇到的问题求解?
1874 浏览 1 评论
X-NUCLEO-IHM08M1板文档中输出电流为15Arms,15Arms是怎么得出来的呢?
1658 浏览 1 评论
1143 浏览 2 评论
STM32F030F4 HSI时钟温度测试过不去是怎么回事?
759 浏览 2 评论
ST25R3916能否对ISO15693的标签芯片进行分区域写密码?
1720 浏览 2 评论
1963浏览 9评论
STM32仿真器是选择ST-LINK还是选择J-LINK?各有什么优势啊?
788浏览 4评论
STM32F0_TIM2输出pwm2后OLED变暗或者系统重启是怎么回事?
610浏览 3评论
628浏览 3评论
stm32cubemx生成mdk-arm v4项目文件无法打开是什么原因导致的?
590浏览 3评论
小黑屋| 手机版| Archiver| 电子发烧友 ( 湘ICP备2023018690号 )
GMT+8, 2025-1-11 06:22 , Processed in 0.861349 second(s), Total 77, Slave 61 queries .
Powered by 电子发烧友网
© 2015 bbs.elecfans.com
关注我们的微信
下载发烧友APP
电子发烧友观察
版权所有 © 湖南华秋数字科技有限公司
电子发烧友 (电路图) 湘公网安备 43011202000918 号 电信与信息服务业务经营许可证:合字B2-20210191 工商网监 湘ICP备2023018690号