新手入门
- 积分
- 13
- 金钱
- 13
- 注册时间
- 2022-4-7
- 在线时间
- 5 小时
|
5金钱
当用DMA处理中断时,接收的字符数组rx_buffer如果用DMA_Usart_Send(rx_buffer, rx_len)发送,可以实现发什么回什么,但是加一个缓存数组memcpy(usart1_tx_buffer, rx_buffer, rx_len),用DMA_Usart_Send(usart1_tx_buffer, rx_len)发送后只有第一帧数据,后面只进入空闲中断但不发送,且debug时发现rx_buffer和usart1_tx_buffer地址对应的内存值相同,也就是说rx_buffer的值也不随着发送的改变而改变,但是是却能够被DMA_Usart_Send函数发送成正确的值,属实令人头大
voi USART1_IRQHandler(void)
{
#if SYSTEM_SUPPORT_OS //使用OS
OSIntEnter();
#endif
uint32_t tmp_flag = 0;
uint32_t temp;
HAL_UART_IRQHandler(&UART1_Handler);
if(USART1 == UART1_Handler.Instance)
{
tmp_flag =__HAL_UART_GET_FLAG(&UART1_Handler,UART_FLAG_IDLE); //获取IDLE标志位
if((tmp_flag != RESET))//idle标志被置位
{
__HAL_UART_CLEAR_IDLEFLAG(&UART1_Handler); //清除标志位
if(ins_flag == 1)
{
HAL_UART_DMAStop(&UART1_Handler); //先停止DMA,暂停接收
temp = __HAL_DMA_GET_COUNTER(&UART1RxDMA_Handler);// 获取DMA未传输个数
rx_len = BUFFER_SIZE - temp; //总数减去未传输个数,得到已接收数据的个数
ins_flag = 0;
recv_end_flag = 1; // 接收完成标志置1
}
HAL_UART_Receive_DMA(&UART1_Handler,rx_buffer,BUFFER_SIZE);//重新打开DMA接收
//memcpy(usart1_tx_buffer, rx_buffer, rx_len);
}
}
#if SYSTEM_SUPPORT_OS //使用OS
OSIntExit();
#endif
}
while(1)
{
delay_ms(100);
if(recv_end_flag == 1) //接收完成标志
{
if(timer!=1) /*由于开启空闲中断的时候会进入一次中断导致第一次会将recv_end_flag置一 触发DMA串口发送
这里加个简单的判断避免下,这种情况应该是H7的HAL底层处理问题导致 ,大家也可以找下问题在分享一下*/
{
memcpy(usart1_tx_buffer, rx_buffer, rx_len);
DMA_Usart_Send(usart1_tx_buffer, rx_len);
DMA_Usart_Send(rx_buffer, rx_len);
//HAL_UART_Transmit(&UART1_Handler,(uint8_t*)rx_buffer,rx_len,100);
rx_len = 0;//清除计数
recv_end_flag = 0;//解除结束计数标志位rx_buffer
// delay_ms(10);
}
else
{
recv_end_flag = 0;//解除结束计数标志位
timer++;
}
}
ins_flag = 1;
}
|
|