STM32 DMA内存到内存传输仅触发一次

STM32 DMA内存到内存传输仅触发一次,stm32,dma,Stm32,Dma,我正在使用STM32F103,试图使用DMA从一个阵列复制到另一个阵列。传输在第一次工作时,会命中DMA1\u Channel1\u IRQHandler中的断点,但对DMA\u Cmd(DMA1\u Channel1,ENABLE)的后续调用无效,且不会命中断点。未设置错误标志DMA1\U标志TE1。是否有其他需要设置/重置的内容,以便再次运行传输 #include "stm32f10x.h" #define ARRAYSIZE 800 volatile uint32_t status =

我正在使用STM32F103,试图使用DMA从一个阵列复制到另一个阵列。传输在第一次工作时,会命中
DMA1\u Channel1\u IRQHandler
中的断点,但对
DMA\u Cmd(DMA1\u Channel1,ENABLE)
的后续调用无效,且不会命中断点。未设置错误标志DMA1\U标志TE1。是否有其他需要设置/重置的内容,以便再次运行传输

#include "stm32f10x.h"

#define ARRAYSIZE 800
volatile uint32_t status = 0;
volatile uint32_t i;


int main(void)
{
    uint32_t source[ARRAYSIZE];
    uint32_t destination[ARRAYSIZE];
    for (i=0; i<ARRAYSIZE;i++)
        source[i]=i;

    RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1, ENABLE);

    DMA_InitTypeDef  DMA_InitStructure;
    DMA_DeInit(DMA1_Channel1);

    DMA_InitStructure.DMA_M2M = DMA_M2M_Enable;
    DMA_InitStructure.DMA_Mode = DMA_Mode_Normal;
    DMA_InitStructure.DMA_Priority = DMA_Priority_Medium;
    DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte;
    DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte;
    DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;
    DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Enable;
    DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralSRC;
    DMA_InitStructure.DMA_BufferSize = ARRAYSIZE;
    DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t)source;
    DMA_InitStructure.DMA_MemoryBaseAddr = (uint32_t)destination;

    DMA_Init(DMA1_Channel1, &DMA_InitStructure);
    DMA_ITConfig(DMA1_Channel1, DMA_IT_TC, ENABLE);

    NVIC_InitTypeDef NVIC_InitStructure;
    NVIC_InitStructure.NVIC_IRQChannel = DMA1_Channel1_IRQn;
    NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
    NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
    NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
    NVIC_Init(&NVIC_InitStructure);

    status = 1;

    while (1)
      {
        if(status == 1)
        {
           status = 0;

           DMA1_Channel1->CNDTR = ARRAYSIZE;
           DMA1_Channel1->CPAR = (uint32_t)source;
           DMA1_Channel1->CMAR = (uint32_t)destination;
           DMA_ClearFlag(DMA1_FLAG_GL1);
           DMA_ClearFlag(DMA1_FLAG_TC1);

           DMA_Cmd(DMA1_Channel1, DISABLE);
           DMA_Cmd(DMA1_Channel1, ENABLE);
        }
      }
}

void DMA1_Channel1_IRQHandler(void)
{
  if(DMA_GetITStatus(DMA1_IT_TC1))
  {
    status=1;
    DMA_ClearITPendingBit(DMA1_IT_GL1);
  }
}
#包括“stm32f10x.h”
#定义阵列800
易失性uint32_t状态=0;
挥发性uint32_t i;
内部主(空)
{
uint32_t源[阵列化];
uint32_t目的地[排列];
对于(i=0;iCNDTR=ARRAYSIZE;
DMA1_通道1->CPAR=(uint32_t)源;
DMA1\u信道1->CMAR=(uint32\u t)目的地;
DMA_ClearFlag(DMA1_FLAG_GL1);
DMA_ClearFlag(DMA1_FLAG_TC1);
DMA_Cmd(DMA1_信道1,禁用);
DMA_Cmd(DMA1_信道1,启用);
}
}
}
无效DMA1\U通道1\U IRQHandler(无效)
{
if(DMA_GetITStatus(DMA1_IT_TC1))
{
状态=1;
DMA_ClearITPendingBit(DMA1_IT_GL1);
}
}

在设置其寄存器之前禁用DMA,然后再启用。根据(第287页)DMA_CNDTRx只能在禁用频道时写入。DMA_CMARx也是如此。

如果在if块中将状态设置为0,程序将不会第二次进入。您想进行连续、循环DMA传输还是自己启动它?我没有注意到isr中的状态设置,前面评论的第一部分与此无关或者,在设置寄存器之前将
DMA_Cmd(DMA1_Channel1,DISABLE);
移动到行中修复了问题,DMA事务按预期连续运行。