21ic问答首页 - SWM34S DMA接收不定长数据问题
SWM34S DMA接收不定长数据问题
xlhhao2023-12-27
本帖最后由 xlhhao 于 2023-12-27 09:40 编辑
使用的是SWM34S ,在官方 SimplUART_DMA_RX 例程上修改。目的是想实现DMA接收不定长数据。 使用UART 超时中断。DMA设置单次,长度1024个字节。 在UART超时中断中再次重新初始化DMA配置接收
问题现象如下: 第一次通过串口发送数据16个数据。 数据能准确接收到buffer中. 第二次再发送16数据,新接收数据则存放在 buffer+16位置。也就是说DMA未被重新初始化。仍然还是保持上一次DMA的接收状态。
相关代码如下:
void rs485_init(void)
{
PORT_Init(PORTB, PIN13, PORTB_PIN13_UART2_RX, 1); /* GPIOB.13 配置为 UART2 输入引脚 */
PORT_Init(PORTB, PIN11, PORTB_PIN11_UART2_TX, 0); /* GPIOB.11 配置为 UART2 输出引脚 */
UART_InitStructure UART_initStruct;
UART_initStruct.Baudrate = RS485_BAUD;
UART_initStruct.DataBits = UART_DATA_8BIT;
UART_initStruct.Parity = UART_PARITY_NONE;
UART_initStruct.StopBits = UART_STOP_1BIT;
UART_initStruct.RXThreshold = 3;
UART_initStruct.RXThresholdIEn = 0;
UART_initStruct.TXThreshold = 3;
UART_initStruct.TXThresholdIEn = 0;
UART_initStruct.TimeoutTime = 10;
UART_initStruct.TimeoutIEn = 1; //超时中断
UART_Init(UART2, &UART_initStruct);
UART_Open(UART2);
UART_INTClr(UART2, UART_IT_RX_TOUT);
}
void rs485rx_dma_config(void)
{
DMA_InitStructure DMA_initStruct;
DMA_initStruct.Mode = DMA_MODE_SINGLE;
DMA_initStruct.Unit = DMA_UNIT_BYTE;
DMA_initStruct.Count= 1024; // DMA 搬运个数
DMA_initStruct.SrcAddr = (uint32_t)&UART2->DATA;
DMA_initStruct.SrcAddrInc = 0;
DMA_initStruct.DstAddr = (uint32_t)RX_Buffer;
DMA_initStruct.DstAddrInc = 1; // Scatter-Gather 模式
DMA_initStruct.Handshake = DMA_CH0_UART2RX;
DMA_initStruct.Priority = DMA_PRI_LOW;
DMA_initStruct.INTEn = 0;
DMA_CH_Init(DMA_CH0, &DMA_initStruct);
DMA_CH_Open(DMA_CH0);
}
//接收超时中断,
void UART2_Handler(void)
{
if(UART_INTStat(UART2, UART_IT_RX_TOUT))
{
DMA_CH_Close(DMA_CH0);
rs485rx_dma_config(); //在此处重置DMA会不成功
UART_INTClr(UART2, UART_IT_RX_TOUT);
}
}
使用的是SWM34S ,在官方 SimplUART_DMA_RX 例程上修改。目的是想实现DMA接收不定长数据。 使用UART 超时中断。DMA设置单次,长度1024个字节。 在UART超时中断中再次重新初始化DMA配置接收
问题现象如下: 第一次通过串口发送数据16个数据。 数据能准确接收到buffer中. 第二次再发送16数据,新接收数据则存放在 buffer+16位置。也就是说DMA未被重新初始化。仍然还是保持上一次DMA的接收状态。
相关代码如下:
void rs485_init(void)
{
PORT_Init(PORTB, PIN13, PORTB_PIN13_UART2_RX, 1); /* GPIOB.13 配置为 UART2 输入引脚 */
PORT_Init(PORTB, PIN11, PORTB_PIN11_UART2_TX, 0); /* GPIOB.11 配置为 UART2 输出引脚 */
UART_InitStructure UART_initStruct;
UART_initStruct.Baudrate = RS485_BAUD;
UART_initStruct.DataBits = UART_DATA_8BIT;
UART_initStruct.Parity = UART_PARITY_NONE;
UART_initStruct.StopBits = UART_STOP_1BIT;
UART_initStruct.RXThreshold = 3;
UART_initStruct.RXThresholdIEn = 0;
UART_initStruct.TXThreshold = 3;
UART_initStruct.TXThresholdIEn = 0;
UART_initStruct.TimeoutTime = 10;
UART_initStruct.TimeoutIEn = 1; //超时中断
UART_Init(UART2, &UART_initStruct);
UART_Open(UART2);
UART_INTClr(UART2, UART_IT_RX_TOUT);
}
void rs485rx_dma_config(void)
{
DMA_InitStructure DMA_initStruct;
DMA_initStruct.Mode = DMA_MODE_SINGLE;
DMA_initStruct.Unit = DMA_UNIT_BYTE;
DMA_initStruct.Count= 1024; // DMA 搬运个数
DMA_initStruct.SrcAddr = (uint32_t)&UART2->DATA;
DMA_initStruct.SrcAddrInc = 0;
DMA_initStruct.DstAddr = (uint32_t)RX_Buffer;
DMA_initStruct.DstAddrInc = 1; // Scatter-Gather 模式
DMA_initStruct.Handshake = DMA_CH0_UART2RX;
DMA_initStruct.Priority = DMA_PRI_LOW;
DMA_initStruct.INTEn = 0;
DMA_CH_Init(DMA_CH0, &DMA_initStruct);
DMA_CH_Open(DMA_CH0);
}
//接收超时中断,
void UART2_Handler(void)
{
if(UART_INTStat(UART2, UART_IT_RX_TOUT))
{
DMA_CH_Close(DMA_CH0);
rs485rx_dma_config(); //在此处重置DMA会不成功
UART_INTClr(UART2, UART_IT_RX_TOUT);
}
}
赞0
已更新,,现在可以通过DMA可以接收任意长度的字符串了
https://gitee.com/synwit-co-ltd/SWM341_Lib
QQ截图20240104195510.jpg (116.81 KB )
下载附件
2024-1-4 19:57 上传
评论
2024-01-04
您需要登录后才可以回复 登录 | 注册