DMA双缓冲停不下来,普通模式可以.

2019-07-20 18:49发布

为了试验双缓冲模式,就拿USART测试,刚开始是USART1,现在是USART3,同样的问题.

    USART_Cmd(USART3, ENABLE);  //使能串口1
    RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_DMA1, ENABLE);
    DMA_DeInit(DMA1_Stream4);
    DMA_StructInit(&DMA_InitStructure);
    DMA_InitStructure.DMA_Channel = DMA_Channel_7;
    DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t)&USART3->DR; //数据传输的外设首地址
    DMA_InitStructure.DMA_Memory0BaseAddr = (uint32_t)Buffer0; //自己定义待发送数组的首地址,要强制转换为32位
    DMA_InitStructure.DMA_DIR = DMA_DIR_MemoryToPeripheral; //数据传输方向选择为内存->外设
    DMA_InitStructure.DMA_BufferSize = 4; //传输数据大小为8,大小要配合定义的数组类型和外设数据类型,否则会丢失或补充数据
    DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable; //外设地址寄存器自动增加禁止,因为这里只用到了 DR 数据寄存器
    DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable; //内存地址自增允许,因为要读取一个数组
    DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte; //外设的数据大小,因为 USART3_DR 数据寄存器为8位,故选Byte
    DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte; //这里也选 Byte
    DMA_InitStructure.DMA_Mode = DMA_Mode_Normal; //在普通DMA时候,DMA_Mode_Normal就是传一次,DMA_Mode_Circular,循环传输,但是在双缓冲下,怎么都是不停传.
    DMA_InitStructure.DMA_Priority = DMA_Priority_Low; //优先级为 High
    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_DoubleBufferModeConfig(DMA1_Stream4, (uint32_t)Buffer1, DMA_Memory_0);
    DMA_DoubleBufferModeCmd(DMA1_Stream4, ENABLE);

    NVIC_InitStructure.NVIC_IRQChannel = DMA1_Stream4_IRQn;
    NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x00;//抢占优先级0
    NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x00;//子优先级0
    NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;//使能外部中断通道
    NVIC_Init(&NVIC_InitStructure);//配置

    DMA_Init(DMA1_Stream4, &DMA_InitStructure);
    /*DMA 中断开*/
    DMA_ClearITPendingBit(DMA1_Stream4, DMA_IT_TCIF4);
    DMA_ITConfig(DMA1_Stream4, DMA_IT_TC, ENABLE);
    USART_DMACmd(USART3, USART_DMAReq_Tx, ENABLE);
    DMA_Cmd(DMA1_Stream4, ENABLE); 

在中断内,通过判断,时候传够20次传输,就结束,结果发现没效果.

[mw_shl_code=c,true] if(DMA_GetITStatus(DMA1_Stream4, DMA_IT_TCIF4) == SET) { DMA_ClearITPendingBit(DMA1_Stream4, DMA_IT_TCIF4); if(Buffer0[0] != 0xB0) { if(DMA_GetCurrentMemoryTarget(DMA1_Stream4)) { //现在访问是Buufer1,所以写Buffer0. for(i = 0; i < 4; i++) { Buffer0++; } } else { for(i = 0; i < 4; i++) { Buffer1--; } } } else { DMA_DoubleBufferModeCmd(DMA1_Stream4, DISABLE); // USART_DMACmd(USART3,USART_DMAReq_Tx,DISABLE); } }[/mw_shl_code] 如果不关闭USART_DMAReq_Tx就停不下来,如果关闭,最后一次传输漏了两个字节.怎么办.


友情提示: 此问题已得到解决,问题已经关闭,关闭后问题禁止继续编辑,回答。